-
Notifications
You must be signed in to change notification settings - Fork 93
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Add product discounts (OCC-31) #136
Comments
I'd recommend checking out the Nwazet commerce implementation of promotions, that was built for our electronics business, at least for inspiration on abstractions:
|
What do you think, should this be in a separate project? Like |
A separate feature, yes. A separate module, not necessarily. The one thing that would speak for a separate module: In the end, you'll always be able to move the necessary files to a new project before you finish 😉 |
If it's practical to have a separate module, go for it. |
So far, I've separated into different modules only if the code is independent and has a (re)use case outside of the module. The currency stuff for instance, is generic and useful outside of the commerce module. For feature areas, we have Orchard features that are designed exactly for this. The project could also be reorganized into feature area folders if it becomes too untidy with the current organization. Separate modules don't seem to address any user scenario. |
Note: see #9 for general discussions about various types of promotions. This issue is a subset of that.
Concept
Let's start with simple discounts associated with a specific product. The discount would be described with a separate
DiscountPart
. Abstraction should be similar to how prices are done in OCC. So there should be anIPromotionProvider
that describes the service that interacts with theShoppingCartItem
(e.g. applies the discount from its content item'sDiscountPart
) and anIPromotionService
that resolves and applies the promotion providers.DiscountPart Fields or Properties
int
/NumericField
) a percentage discount to be applied to the product price.How should rounding be handled? (for reference here is what Nwazet did)
Amount
) a flat number to be subtracted from the price (ofc result can't be negative)DateTime
/DateTimeField
) if the current time is lower, the discount is ignored.DateTime
/DateTimeField
) if the current time is higher, the discount is ignored.int
/NumericField
) if the quantity is lower, the discount is ignored.int
/NumericField
) if the quantity is higher, the discount is ignored (0 should be treated as infinite).You shouldn't be able to have both Percentage and Amount (use handler).
Services
IPromotionService
should haveTask<IList<ShoppingCartItem>> AddPromotionsAsync(IList<ShoppingCartItem> items);
(like price). This should sort and select the applicableIPromotionProvider
s, call theApplyingPromotion
event (see below), then apply the resulting promo(s) on the shopping cart item.IPromotionProvider
should also have similar members as its price counterpart, just for promotions. There should be one implementation that usesDiscountPart
, e.g.DiscountProvider
.Event
ApplyingPromotion
: extension point for changing the promo providers' order, or removing some or all of them before they are applied to the shopping cart item.Others
PrioritizedPrice
to store the old price before the promo was applied. That can be used as a crossed-out price on the product page and cart.IPromotionProvider
applied? I guess it has to be used inPricePartDisplayDriver
andPriceVariantsPartDisplayDriver
for display; and inShoppingCartController.AddItem
to finalize the offer. In the future we may have otherIPromotionProvider
that works on already added cart items (e.g. coupon codes), but we don't have to prepare for that just yet.This is just speculation, if you can find a better approach, go for it.
Tests
Include unit tests with dummy service implementations. Refer to
OrchardCore.Commerce.Tests.PriceTests
for inspiration.Jira issue
The text was updated successfully, but these errors were encountered: