Use Cases

Panduan Praktis Building an E-Commerce Site dengan Claude Code

Panduan praktis tentang building an e-commerce site menggunakan Claude Code dengan contoh kode dunia nyata.

ECサイトpembangunanにClaude Codeを使う

ECサイト 商品manajemen、カート、決済、在庫manajemen、注文manajemen dan 多く 機能 diperlukan.Claude Code 使えば、これら 機能 一貫 設計 efisien pembangunan bisa dilakukan.

商品データモデル

> Next.js dengan ECサイト bangun.
> 商品daftar・詳細・カート・checkout halaman dan 、
> Stripe決済 integrasikan.在庫manajemen juga 含めて。
// src/types/product.ts
export interface Product {
  id: string;
  name: string;
  slug: string;
  description: string;
  price: number;
  compareAtPrice?: number;
  images: string[];
  category: string;
  variants: ProductVariant[];
  stock: number;
  isActive: boolean;
}

export interface ProductVariant {
  id: string;
  name: string;       // 例: "Mサイズ / ブルー"
  sku: string;
  price: number;
  stock: number;
  attributes: Record<string, string>;
}

export interface CartItem {
  productId: string;
  variantId?: string;
  quantity: number;
  price: number;
}

implementasi カート機能

// src/stores/cart-store.ts
import { create } from 'zustand';
import { persist } from 'zustand/middleware';

interface CartState {
  items: CartItem[];
  addItem: (item: CartItem) => void;
  removeItem: (productId: string) => void;
  updateQuantity: (productId: string, quantity: number) => void;
  clearCart: () => void;
  totalPrice: () => number;
  totalItems: () => number;
}

export const useCartStore = create<CartState>()(
  persist(
    (set, get) => ({
      items: [],
      addItem: (item) =>
        set((state) => {
          const existing = state.items.find(
            (i) => i.productId === item.productId && i.variantId === item.variantId
          );
          if (existing) {
            return {
              items: state.items.map((i) =>
                i.productId === item.productId
                  ? { ...i, quantity: i.quantity + item.quantity }
                  : i
              ),
            };
          }
          return { items: [...state.items, item] };
        }),
      removeItem: (productId) =>
        set((state) => ({
          items: state.items.filter((i) => i.productId !== productId),
        })),
      updateQuantity: (productId, quantity) =>
        set((state) => ({
          items: state.items.map((i) =>
            i.productId === productId ? { ...i, quantity } : i
          ),
        })),
      clearCart: () => set({ items: [] }),
      totalPrice: () => get().items.reduce((sum, i) => sum + i.price * i.quantity, 0),
      totalItems: () => get().items.reduce((sum, i) => sum + i.quantity, 0),
    }),
    { name: 'cart-storage' }
  )
);

checkoutAPI

// src/app/api/checkout/route.ts
import { NextRequest, NextResponse } from 'next/server';
import Stripe from 'stripe';

const stripe = new Stripe(process.env.STRIPE_SECRET_KEY!);

export async function POST(request: NextRequest) {
  const { items } = await request.json();

  // 在庫konfirmasi
  for (const item of items) {
    const product = await getProduct(item.productId);
    if (!product || product.stock < item.quantity) {
      return NextResponse.json(
        { error: `${product?.name || '商品'}の在庫が不足しています` },
        { status: 400 }
      );
    }
  }

  const session = await stripe.checkout.sessions.create({
    mode: 'payment',
    payment_method_types: ['card'],
    line_items: items.map((item: CartItem) => ({
      price_data: {
        currency: 'jpy',
        product_data: { name: item.productId },
        unit_amount: item.price,
      },
      quantity: item.quantity,
    })),
    success_url: `${process.env.APP_URL}/order/success?session_id={CHECKOUT_SESSION_ID}`,
    cancel_url: `${process.env.APP_URL}/cart`,
    shipping_address_collection: {
      allowed_countries: ['JP'],
    },
  });

  return NextResponse.json({ url: session.url });
}

商品daftarkomponen

// src/components/ProductCard.tsx
import Image from 'next/image';
import Link from 'next/link';
import { Product } from '@/types/product';

export function ProductCard({ product }: { product: Product }) {
  const discount = product.compareAtPrice
    ? Math.round((1 - product.price / product.compareAtPrice) * 100)
    : 0;

  return (
    <Link href={`/products/${product.slug}`} className="group">
      <div className="relative aspect-square overflow-hidden rounded-lg">
        <Image
          src={product.images[0]}
          alt={product.name}
          fill
          className="object-cover group-hover:scale-105 transition-transform"
        />
        {discount > 0 && (
          <span className="absolute top-2 right-2 bg-red-500 text-white text-xs px-2 py-1 rounded">
            {discount}% OFF
          </span>
        )}
      </div>
      <h3 className="mt-2 font-medium">{product.name}</h3>
      <div className="flex items-center gap-2">
        <span className="text-lg font-bold">${product.price.toLocaleString()}</span>
        {product.compareAtPrice && (
          <span className="text-sm text-gray-400 line-through">
            ${product.compareAtPrice.toLocaleString()}
          </span>
        )}
      </div>
    </Link>
  );
}

Summary

Untuk Claude Codeを使えば、ECサイトのkompleksな機能群を整合性のとれたコードで一気にpembangunanできます。決済pemrosesanの詳細はStripe決済のintegrasipanduan、状態manajemenのpola, lihat 状態管理の実装.

Stripe 公式tutorial(stripe.com/docs) juga あわせてkonfirmasi おすすめ.

#Claude Code #EC #Stripe #Next.js #TypeScript
Gratis

PDF Gratis: Cheatsheet Claude Code dalam 5 Menit

Cukup masukkan emailmu dan kami akan langsung mengirim cheatsheet PDF A4 satu halaman.

Kami menjaga data pribadimu dengan aman dan tidak pernah mengirim spam.

Masa

Tentang Penulis

Masa

Engineer yang aktif menggunakan Claude Code. Mengelola claudecode-lab.com, media teknologi 10 bahasa dengan lebih dari 2.000 halaman.