mglaman / commerce_cart_api

Original sandbox WIP for the module now on Drupal.org. Do not fork. Patches accepted on Drupal.org
https://www.drupal.org/project/commerce_cart_api
9 stars 1 forks source link

Requirements #16

Open gabesullice opened 5 years ago

gabesullice commented 5 years ago

It'd be great to have a clearly defined set of requirements for a decoupled cart API.

Like:

Are all of these requirements? Can some of them be removed? Did I miss constraints?

What's the data model? What entity types are involved? A user entity. A cart entity (with bundles?), an order item entity?

How do those entities relate to one another? Via entity reference fields? Something else?

From there, I'd love to work out a spec for a cart API. Rather than starting from the implementation, that would help me know how I could best help you.

A spec would make it more clear to me what public JSON:API PHP APIs are needed than reverse engineering an experimental implementation.

I'm sure that what is easiest to get working today is not a 1:1 match to what would be easiest with an explicitly designed API.

mglaman commented 5 years ago

Thanks for writing this up. I will work to clarify and extend as needed.

mglaman commented 5 years ago

Here is step 1 to define the data model and workflow. I am working backwards to get to a user story like statement

Cart / Order Data model

A cart is an order which is in a draft state and has the cart boolean marked as true. The latter option is part of our CartProvider and CartManager APIs. Cart can be considered as a module that provides access control and management to non-elevated users.

An order has the following entity references:

An order item represents something that has been purchased and belongs to one order. The order item's bundle defines what purchasable entity type_ it references. An order item may not reference any purchasable entities. The default purchasable entity available is there Product Variation entity. Although any entity implementing PurchasableEntityInterface is allowed. We rely heavily upon the PurchasableEntityInterface class for order item relationships to products.

NOTE we do not have any kind of validation ensuring that the order item type references a class implementing this class. Only in Drupal's form validation. I should open an issue for this.

Add to cart flow and processes

This is an outline of the add to cart flow, and understanding how a purchasable entity becomes attached to a cart as an order item.

Notes:

  1. Determine the proper store based on the purchased entity. We take the stores the purchasable entity belongs to and verify it can be purchased from the current store. If it cannot be purchased from this store, this is an unprocessable request.
  2. We then create an order item from the purchasable entity, using the order item's storage method ::createFromPurchasableEntity. This created an order item with the bundle requested by the purchasable entity. The unit price is set from the purchasable entity's price.
  3. The order item's price is resolved to allow for price calculation, overriding the default base price from the purchasable entity.
  4. The order type is resolved by the order item type.
  5. The CartProvider is used to check if a cart exists for the resolved order type and current store.
  6. If a cart does not exist, one is created of the resolved type for the current store.
  7. The order item is then added to the cart using the CartManager
  8. The CartManager handles combining existing order items to update their quantity, if requested, versus creating duplicate order items. It also fires an event to allow users to react to an add to cart event.

We do not just directly call Order::addItem or Order::get('order_items)::appendItem()

Relevant PHP interfaces we use for interacting with carts.

mglaman commented 5 years ago

Here is a go at writing down some constraints for the operations

Constraints

NOTE while this is out of the box behavior, generally a site should be configured to prevent multiple carts. Such as re-assigning an order if the store changes, or ignoring if changing stores is not expected behavior. However multiple carts can be a requirement, such as B2B scenarios.

Non requirements, documented for clarity: