df1f32c23d
- Added `credentials: "include"` to fetch requests in LoginOtpPage and RegisterPage for cookie handling. - Introduced `eateryId` in PaymentPage to manage cart context. - Updated ProductCardProps and ShopCardProps to include `eateryId`. - Enhanced PaymentSummaryCard to accept `eateryId` prop. - Modified ShopCard to set `eateryId` in cart context on click. - Implemented menu item management in MenuItemsTab with add, edit, and delete functionalities. - Created new API functions for handling reviews and cart operations. - Updated GraphQL queries and mutations for menu items and cart management. - Added loading states and error handling in ProductGrid and ReviewModal. - Enhanced local storage management for cart and eatery ID.
79 lines
2.0 KiB
TypeScript
79 lines
2.0 KiB
TypeScript
import type { GqlCart } from "./cart.types";
|
|
|
|
async function cartFetch<T>(
|
|
query: string,
|
|
variables?: Record<string, unknown>,
|
|
): Promise<T> {
|
|
const res = await fetch("/api/cart/graphql", {
|
|
method: "POST",
|
|
headers: { "Content-Type": "application/json" },
|
|
credentials: "include",
|
|
body: JSON.stringify({ query, variables }),
|
|
});
|
|
|
|
if (!res.ok) {
|
|
const body = await res.json().catch(() => null);
|
|
const message =
|
|
Array.isArray(body) && body[0]?.message
|
|
? (body[0].message as string)
|
|
: `Cart API error: ${res.status}`;
|
|
throw new Error(message);
|
|
}
|
|
|
|
return res.json() as Promise<T>;
|
|
}
|
|
|
|
export async function createCart(eateryId: string): Promise<string> {
|
|
const data = await cartFetch<{ createCart: string }>(
|
|
`mutation createCart($eateryId: String) {
|
|
createCart(eateryId: $eateryId)
|
|
}`,
|
|
{ eateryId },
|
|
);
|
|
return data.createCart;
|
|
}
|
|
|
|
export async function getCart(cartId: string): Promise<GqlCart> {
|
|
const data = await cartFetch<{ getCart: GqlCart }>(
|
|
`query getCart($cartId: String) {
|
|
getCart(cartId: $cartId) {
|
|
id
|
|
userId
|
|
eateryId
|
|
items { productId quantity }
|
|
}
|
|
}`,
|
|
{ cartId },
|
|
);
|
|
return data.getCart;
|
|
}
|
|
|
|
// quantity > 0: add; quantity < 0: decrease/remove (backend uses Redis hincrby)
|
|
export async function addItem(
|
|
cartId: string,
|
|
menuItemId: string,
|
|
quantity: number,
|
|
): Promise<GqlCart> {
|
|
const data = await cartFetch<{ addItem: GqlCart }>(
|
|
`mutation addItem($cartId: String, $menuItemId: String, $quantity: BigInteger) {
|
|
addItem(cartId: $cartId, menuItemId: $menuItemId, quantity: $quantity) {
|
|
id
|
|
userId
|
|
eateryId
|
|
items { productId quantity }
|
|
}
|
|
}`,
|
|
{ cartId, menuItemId, quantity },
|
|
);
|
|
return data.addItem;
|
|
}
|
|
|
|
// Backend has no removeItem — zero out via negative addItem
|
|
export async function removeItem(
|
|
cartId: string,
|
|
menuItemId: string,
|
|
currentQuantity: number,
|
|
): Promise<GqlCart> {
|
|
return addItem(cartId, menuItemId, -currentQuantity);
|
|
}
|