Problem/Motivation
The cart provider defines several methods for getting carts:
getCartId()getCart()getCartIds()getCarts()
For whatever reason, it is only possible to specify the store, for the "singular" methods (i.e for retrieving a single cart), but there's no way to restrict the carts collection by store.
Additionally, the query performed by loadCartData() should always have a "store_id" condition, and if no store is provided, we should default to the current store to match what's currently done in getCartId()/getCart().
| Comment | File | Size | Author |
|---|---|---|---|
| #26 | interdiff_25-26.txt | 4.96 KB | jsacksick |
| #26 | 3179466-26.patch | 12.67 KB | jsacksick |
| #11 | 3179466-11.cart_provider_by_store.patch | 11.93 KB | rszrama |
| #9 | interdiff_7-9.txt | 3.06 KB | jsacksick |
| #9 | 3179466-9.patch | 11.49 KB | jsacksick |
Comments
Comment #2
jsacksick commentedComment #3
jsacksick commentedTests need to be expanded, and we probably need a change record, attaching a patch to validate the approach first.
Comment #4
jsacksick commentedComment #5
jsacksick commentedComment #6
jsacksick commentedComment #7
jsacksick commentedComment #8
jsacksick commentedComment #9
jsacksick commentedComment #10
jsacksick commentedComment #11
rszrama commentedOnly thing missing was a documentation update for CartProvider::cartData. Only bummer about the patch is the inconsistency in ordering of the store vs. account parameters, but I understand our hands are tied on CartProvider::createCart() to preserve BC. 😬
Patch attached updates the property docs at the top, should still commit fine - no other code was changed. fwiw, in my single store site, this obviously works as expected. I haven't tried it in a multi-store setup but don't see why it shouldn't work.
Comment #12
jsacksick commentedYeah, I agree, but there's no way we can change this now unfortunately!
Thank you for the documentation update!
I'm still wondering whether we should default to the current store in
loadCartData()(instead of not applying the store filter if no store is passed), because any implementation callinggetCarts()would now only get carts for the current store (if no store is passed), instead of getting carts for all stores...Do you think that's a valid concern?
Comment #13
mglamanI think anyone with multistore is a small portion of users. And those who have used multiple stores use them across domains. So this change improves their experience - developer and QA creating carts between domains locally.
We can pop a change record and anyone with custom code and understand why
Comment #15
jsacksick commentedCommitted! Thanks everyone :).
Comment #17
krystalcode commentedSome assumptions here. It's ok that you make such decisions and changes, however, could you at least be highlighting them in the release notes when you introduce backward-breaking changes? Make the life of developers easier when updating.
Comment #18
ocastle commentedI'd agree with @krystalcode.
This also breaks modules like commerce_api and commerce_marketplace and there is now no way of requesting all carts for a single user.
I understand the idea to 'improve' the cart provider, but this changes its functionality for no real reason, significantly reducing its flexibility.
We should have at least added additional methods such as
getAllCartsandgetAllCartIdsand move the default fallback store outside ofloadCartDatato keep some flexibility.Comment #19
krystalcode commentedIf anybody relies on the previous behavior, I will be fixing the regression on Commerce Cart Advanced where I'll be keeping the previous behavior i.e. return all carts unless a specific store is explicitly requested.
Comment #20
jsacksick commented@ocastle, @krystalcode: I concede that a change like this would have deserve a change record at the very least.
It's also true that the issue title / summary doesn't properly describe what was done and why...
While we probably fixed issues occurring in a multi store / multi domain setup... We probably neglected the side effects for the marketplace usecase...
I'm wondering how we can satisfy all of the use cases properly and whether there's a way to partially revert some of the changes introduced here.
What I would like to get is proper bug reports that describe the expected behavior and the bug encountered so I can do something about it...
Thus far, 2 issues were created (#3193126: Unable to place an order which is very confusing and #3184614: Multi-Cart NOT supported: products from secondary stores are NOT displayed which doesn't clearly describe the issue either...
DId we break only the /cart page, or is there more than that?
@ocastle: could you help with filling a proper bug report / updating the existing one?
Comment #21
krystalcode commented@jsacksick
I think the best is that caller of the cart provider should be deciding which carts to fetch rather than the provider deciding internally. That is the cart view, for example, should have a way to say give me only the carts for this store or all carts. I can create an issue with a proposal later when I can.
Comment #22
ocastle commented@krystalcode let me know if you need some additional information for the issue. happy to help.
Comment #23
bojanz commentedLet's reopen this issue.
This is a major BC break and needs to be reverted. It basically removes the ability to list carts belonging to multiple stores.
Comment #24
krystalcode commentedOk, let's keep it here.
I've thought a bit about this and I don't think we actually need a new solution, we just need the previous behavior.
- If a site has only one store, then there's no problem, all carts will be loaded and they are all from the same store.
- If a site is a multi-domain site, it could be handy to default to the current store as that would be determined by the current domain, but then there must be custom code or through contrib to associate each store with a domain and I feel that whoever is providing that should be responsible for customizing the cart controller to their needs. There could even be multi-domain sites with multiple stores per domain, let them deal with that as they need.
- If a site is a marketplace i.e. multiple stores, then it's actually desired to have carts from multiple stores displayed.
I think we can keep the ability to provide a specific store, even though that requires other modules that extend the cart provider to be updated - that's ok. And just load all carts if no specific store was requested.
Comment #25
jsacksick commentedThe main problem with the "old" behavior is that it isn't really consistent.
getCart()andgetCartId()both accept an optional $store parameter, but notgetCarts()andgetCartIds().Now that we've introduced this extra $store parameter to
getCarts()andgetCartIds()I think we should still keep that... But then obviously we can't default to the current store since that'd be similar to keeping thestore_idcondition inloadCartData().Is it ok to be inconsistent and not default to the current store there?
Now, regarding the actual issue we were attempting to address in the first place, modifying the cart provider was probably not the right approach.
An alternative solution would be to add a contextual store filter to the cart view that defaults to the current store...
Note that we could also somehow introduce a setting that we'd rely on in the cart controller that determines whether or not we should pass the current store to
getCarts().The attached patch partially reverts the commit (We still can optionally pass a store to
getCartIds()andgetCarts()but it no longer defaults to the current store. (loadCartData()doesn't filter on the store anymore.Comment #26
jsacksick commentedThe attached patch fixes phpcs violations, and also update the test to remove the unnecessary store type + store creation since we already have a store available.
Comment #27
zenimagine commented@jsacksick I just tested the patch but I don't have the behavior before the last update at all. I have a marketplace and if I add products from 2 different stores, it will create a single shopping cart.
Before it work properly and it create 2 shopping carts.
I have the Drupal Commerce and Commerce Markerplace modules.
I hope that Drupal Commerce can finally manage marketplaces properly.
Comment #28
jsacksick commentedWell then maybe it's due to another change, and not the patch from here...
Wondering if somehow, the change from #3143382: AddToCartForm should reference the destination cart when building the order item is affecting this.
A marketplace can be implemented very differently depending on the use-case... It isn't our main focus and it'll be the responsibility of the Commerce marketplace module to implement it as required to satisfy the usecase addressed by the module.
On the Commerce core side we should ensure this is possible, but we'll never implement the marketplace usecase directly in core.
Comment #29
rszrama commentedCreated #3193580-3: Add a cart settings form to filter the cart page to the current store as a follow-up issue to reenact the behavior we were trying to prioritize, which is the more clear use case of a multi-store site where 1 store = 1 domain and carts should not be visible off-domain.
Comment #30
ocastle commentedPatch #26 fixes the issue for me and restores the ability to load all users carts at once.
I believe it still adds the functionality that this issue was trying to solve, but i'm not in a position to confirm this.
Comment #31
zenimagine commented@ocastle Is the patch working for you ? I tested it and it does not allow you to create multiple shopping carts. If I add products from multiple stores, I only have one shopping cart. It should display a shopping cart by store. Do you use Commerce Marketplace ?
Comment #32
jsacksick commented@zenimagine: I doubt this change is related.. This allows getting carts from multiple stores again, without defaulting to the current store. Have you tried reverting the other change I linked?
Comment #34
jsacksick commentedCommitted the patch from #26, thanks for the feedbacks/testing.
Comment #35
ocastle commented@zenimagine The patch restored the original setup on cart provider which mainly affected my commerce_api implementation.
I do use commerce marketplace but not the UI and I know the result you're expecting, but agree with @jsacksick, not sure this patch would have changed that. Might be worth opening issue on commerce_marketplace?
Comment #36
londova commentedYes, it works,
I have separate cart for each store as it was previously.
Thank You.