Press n or j to go to the next uncovered block, b, p or k for the previous block.
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 | 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 1x 8x 8x 8x 8x 8x 8x 8x 8x 8x 8x 8x 1x 1x 1x 1x 7x 7x 8x 1x 1x 1x 1x 1x 1x 1x 6x 6x 8x 1x 1x 5x 5x 5x 5x 5x 5x 5x 5x 5x 4x 4x 4x 4x 4x 4x 4x 4x 4x 4x 4x 4x 3x 3x 3x 3x 3x 3x 3x 3x 3x 1x 1x | export const dynamic = "force-dynamic";
import { NextRequest, NextResponse } from 'next/server';
import {
withAuth,
withErrorHandling,
successResponse,
validationErrorResponse,
ApiSuccessResponse,
ApiErrorResponse } from "@/lib/api";
import { RouteContext } from "@/lib/api/middleware";
import { prisma } from "@/lib/prisma";
import {
mergeAnonymousCartToUser,
transformDbCartToCartItems,
validateCartItems,
ConflictItem } from "@/lib/cart";
import { applyCartMerge } from "@/lib/cart/cart-merge";
import { Session } from "next-auth";
interface CartMergeResponse {
success: boolean;
merged: number;
conflicts: number;
conflictDetails: ConflictItem[];
message: string;
}
/**
* POST /api/cart/merge
*
* Merges anonymous cart (from cookie) into user's database cart
* Called after user logs in
*
* Request body:
* {
* anonymousItems: CartItem[] // Items from anonymous cart cookie
* }
*/
async function handlePost(
request: NextRequest,
_context: RouteContext | undefined,
session: Session
): Promise<NextResponse<ApiSuccessResponse<CartMergeResponse> | ApiErrorResponse>> {
const { anonymousItems } = await request.json();
const userId = session.user.id;
const deviceId = request.headers.get("x-device-id") || "default";
// Validate input
if (!Array.isArray(anonymousItems)) {
return validationErrorResponse(
"Invalid request: anonymousItems must be an array"
);
}
// If no anonymous items, just return success
if (anonymousItems.length === 0) {
return successResponse({
success: true,
merged: 0,
conflicts: 0,
conflictDetails: [],
message: "No anonymous items to merge"});
}
// Validate cart items
if (!validateCartItems(anonymousItems)) {
return validationErrorResponse("Invalid cart items format");
}
// Fetch user's current cart from database
const userCartDb = await prisma.cart.findMany({
where: { userId },
include: {
product: {
include: {
images: {
orderBy: { order: "asc" }}}}}});
// Transform database cart to CartItem format
const userCartItems = transformDbCartToCartItems(userCartDb);
// Merge the carts
const { merged, conflicts, message } = mergeAnonymousCartToUser(
anonymousItems,
userCartItems
);
// Apply merge to database
await applyCartMerge(userId, merged, deviceId);
// Prepare response
return successResponse({
success: true,
merged: merged.length,
conflicts: conflicts.length,
conflictDetails: conflicts,
message});
}
export const POST = withErrorHandling(withAuth(handlePost));
|