Skip to content

Commit

Permalink
useOptimisticCart: optimistically calculate totalQuantity (#2459)
Browse files Browse the repository at this point in the history
  • Loading branch information
scottdixon authored Aug 21, 2024
1 parent 2e504df commit 1b217cd
Show file tree
Hide file tree
Showing 3 changed files with 68 additions and 2 deletions.
5 changes: 5 additions & 0 deletions .changeset/moody-pots-juggle.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
'@shopify/hydrogen': patch
---

useOptimisticCart: optimistically calculate totalQuantity
55 changes: 54 additions & 1 deletion packages/hydrogen/src/cart/optimistic/useOptimisticCart.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -625,14 +625,67 @@ describe('useOptimisticCart', () => {
expect(optimisticCart).toStrictEqual({...EMPTY_CART, isOptimistic: true});
});
});

describe('Total quantity', () => {
it('updates the total quantity when adding a line', async () => {
addPendingCartAction({
action: CartForm.ACTIONS.LinesAdd,
inputs: {
lines: [
{
merchandiseId: '1',
quantity: 1,
selectedVariant: {
id: '1',
},
},
],
},
});

const optimisticCart = useOptimisticCart(EMPTY_CART);
expect(optimisticCart.totalQuantity).toStrictEqual(1);
});

it('updates the total quantity when removing a line', async () => {
addPendingCartAction({
action: CartForm.ACTIONS.LinesRemove,
inputs: {
lineIds: [
'gid://shopify/CartLine/53b449e1-6f6d-47ca-94e4-748a055b45e8?cart=Z2NwLXVzLWNlbnRyYWwxOjAxSFdOR0hESkVBUEtQVkoyMFJFMUhTRDFU',
],
},
});

const optimisticCart = useOptimisticCart(CART_WITH_TWO_LINES);
expect(optimisticCart.totalQuantity).toStrictEqual(1);
});

it('updates the total quantity when updating a line', async () => {
addPendingCartAction({
action: CartForm.ACTIONS.LinesUpdate,
inputs: {
lines: [
{
id: 'gid://shopify/CartLine/53b449e1-6f6d-47ca-94e4-748a055b45e8?cart=Z2NwLXVzLWNlbnRyYWwxOjAxSFdOR0hESkVBUEtQVkoyMFJFMUhTRDFU',
quantity: 2,
},
],
},
});

const optimisticCart = useOptimisticCart(CART_WITH_LINE);
expect(optimisticCart.totalQuantity).toStrictEqual(2);
});
});
});

const EMPTY_CART = {
updatedAt: '2024-04-29T18:05:42Z',
id: 'gid://shopify/Cart/Z2NwLXVzLWNlbnRyYWwxOjAxSFdOR0hESkVBUEtQVkoyMFJFMUhTRDFU',
checkoutUrl:
'https://checkout.hydrogen.shop/cart/c/Z2NwLXVzLWNlbnRyYWwxOjAxSFdOR0hESkVBUEtQVkoyMFJFMUhTRDFU?key=1b6ea717bf3c3bbe68fd26e20c991267',
totalQuantity: 1,
totalQuantity: 0,
buyerIdentity: {
countryCode: 'US',
customer: null,
Expand Down
10 changes: 9 additions & 1 deletion packages/hydrogen/src/cart/optimistic/useOptimisticCart.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -29,18 +29,20 @@ export type OptimisticCart<T = CartReturn> = T extends undefined | null
lines: {
nodes: Array<OptimisticCartLine>;
};
totalQuantity?: number;
} & Omit<PartialDeep<CartReturn>, 'lines'>
: Omit<T, 'lines'> & {
isOptimistic?: boolean;
lines: {
nodes: Array<OptimisticCartLine<T>>;
};
totalQuantity?: number;
};

/**
* @param cart The cart object from `context.cart.get()` returned by a server loader.
*
* @returns A new cart object augmented with optimistic state. Each cart line item that is optimistically added includes an `isOptimistic` property. Also if the cart has _any_ optimistic state, a root property `isOptimistic` will be set to `true`.
* @returns A new cart object augmented with optimistic state for `lines` and `totalQuantity`. Each cart line item that is optimistically added includes an `isOptimistic` property. Also if the cart has _any_ optimistic state, a root property `isOptimistic` will be set to `true`.
*/
export function useOptimisticCart<
DefaultCart = {
Expand Down Expand Up @@ -150,5 +152,11 @@ export function useOptimisticCart<
optimisticCart.isOptimistic = isOptimistic;
}

// Calculate the total quantity of the optimistic cart
optimisticCart.totalQuantity = cartLines.reduce(
(sum, line) => sum + line.quantity,
0,
);

return optimisticCart;
}

0 comments on commit 1b217cd

Please sign in to comment.