# CLAUDE.md

This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.

## Commands

```bash
npm run dev       # Start Vite dev server on port 3000
npm run build     # Production build to dist/
npm run preview   # Preview production build
```

No test or lint scripts are configured. ESLint config exists (`eslint.config.js`) but has no npm script.

## Environment

Requires Node.js >= 18. Set `GEMINI_API_KEY` in `.env.local` for the AI chat feature (Google Gemini API).

## Project Structure

```
├── App.tsx                  # Main app component, global state orchestrator
├── index.tsx                # React entry point
├── index.html               # HTML template (Tailwind CDN loaded here)
├── types.ts                 # All TypeScript interfaces
├── vite.config.ts           # Vite config (port 3000, proxy routes, path alias)
├── vercel.json              # Vercel deployment config (API rewrites, SPA routing)
├── firebase.json            # Firebase hosting config (alternative deployment)
├── api/                     # Vercel serverless functions
│   ├── ask-gemini.ts        # Gemini AI chat proxy
│   ├── fetch-data.ts        # Sales CSV from Dropbox
│   ├── fetch-ads.ts         # Ads Excel from Dropbox
│   ├── fetch-traffic.ts     # Traffic data
│   ├── fetch-stock.ts       # Item availability
│   ├── fetch-paneu-stock.ts # PAN-EU vendor stock
│   ├── fetch-uk-inventory.ts# UK inventory
│   ├── fetch-buybox.ts      # Buy Box tracker
│   ├── fetch-forecast.ts    # Forecast data
│   └── fetch-vendor-stock.ts
├── components/              # React components
│   ├── Dashboard.tsx        # KPI cards, charts, YoY comparisons
│   ├── DataGrid.tsx         # Pivot table with Excel-style filters (~96KB)
│   ├── WeeklyGrid.tsx       # Weekly time-series view
│   ├── TopMovers.tsx        # Growth/decline analysis
│   ├── AdsPerformance.tsx   # Ad spend, ROAS, ACOS metrics
│   ├── ForecastView.tsx     # Product forecasts with seasonality
│   ├── FilterBar.tsx        # Sticky filter controls
│   ├── AIChat.tsx           # AI assistant sidebar
│   ├── FileUpload.tsx       # Manual data upload modal
│   ├── ExcelFilter.tsx      # Advanced column filtering UI
│   ├── MultiSelectDropdown.tsx # Reusable filter dropdown
│   ├── StockBadge.tsx       # Stock status indicator
│   ├── VendorStockBadge.tsx # Vendor stock indicator
│   ├── BuyBoxWarningBadge.tsx # Buy Box loss warnings
│   ├── Top50Badge.tsx       # Top 50 product badge
│   ├── InColumnStockFilter.tsx # In-column stock filter
│   ├── NumericColumnFilter.tsx # Numeric column filter
│   ├── CrazeLogo.tsx        # Header branding
│   ├── ErrorBoundary.tsx    # Error handling wrapper
│   └── Icons.tsx            # SVG icon library
├── services/                # Business logic and data layer
│   ├── dataProcessor.ts     # Core data engine (~2400 lines)
│   ├── storage.ts           # IndexedDB + localStorage caching
│   ├── geminiService.ts     # AI context builder + API calls
│   └── filterHelper.ts      # Filter utilities
└── public/                  # Static data files
    ├── fc 26.xlsx           # EU forecast
    ├── fc UK 26.xlsx        # UK forecast
    ├── Item Availability.xlsx
    ├── Buy_Box_tracker.xlsx
    └── Vendor Stock.xlsx
```

## Architecture

Amazon seller analytics dashboard: React 19 + TypeScript + Vite + Tailwind CSS (CDN). Deployed on Vercel with serverless API routes.

### Data Flow

```
Dropbox (CSV/Excel files)
  → /api/* serverless functions (fetch + proxy)
  → dataProcessor.ts (parse, normalize, aggregate)
  → App.tsx state (useState, no Redux)
  → View components (Dashboard, DataGrid, AdsPerformance, etc.)
```

Data is cached in IndexedDB via `services/storage.ts`. On load, cached data displays immediately while fresh data fetches in the background.

### Key Files

- **App.tsx** — Main orchestrator. Holds all global state (rawData, adsData, trafficData, filters, etc.) and passes data/handlers as props to views.
- **services/dataProcessor.ts** (~2400 lines) — Core data engine. Handles CSV/Excel parsing, currency normalization (EU `1.234,56` and US `1,234.56` formats), Spanish/English month mapping, filtering (`filterData`, `filterAdsData`), aggregation (`aggregateData`), and pivot table generation (`pivotSalesData`).
- **types.ts** — All TypeScript interfaces: `SalesRecord`, `AdsRecord`, `TrafficRecord`, `ForecastRecord`, `FilterState`, `AggregatedData`, `PivotRow`, etc.
- **services/storage.ts** — IndexedDB + localStorage caching with schema versioning.
- **services/geminiService.ts** — Builds structured context from aggregated data and sends to Gemini API.

### Views (rendered conditionally by `view` state in App.tsx)

| View | Component | Purpose |
|------|-----------|---------|
| dashboard | Dashboard.tsx | KPI cards, charts, YoY comparisons |
| table | DataGrid.tsx | Pivot table with Excel-style column filters |
| weekly | WeeklyGrid.tsx | Weekly time-series breakdown |
| movers | TopMovers.tsx | Top growth/decline products |
| ads | AdsPerformance.tsx | Ad spend, ROAS, ACOS metrics |
| forecast | ForecastView.tsx | Product forecasts with velocity mapping |

### API Routes (`/api/`)

All serverless functions fetch data from Dropbox (direct download URLs with `dl=1`). Each returns the raw file content for client-side processing:
- `fetch-data.ts` (sales CSV), `fetch-ads.ts` (ads Excel), `fetch-traffic.ts`, `fetch-stock.ts`, `fetch-paneu-stock.ts`, `fetch-uk-inventory.ts`, `fetch-buybox.ts`, `fetch-forecast.ts`
- `ask-gemini.ts` — Proxies chat requests to Google Gemini API

### Important Constants (in dataProcessor.ts)

- `PAN_EU_COUNTRIES = ['Amazon DE', 'Amazon IT', 'Amazon FR', 'Amazon ES']` — Default country filter when no customer is selected
- `MONTH_ORDER`, `MONTH_MAP` — Month normalization including Spanish names (Enero→Jan, etc.)
- `parseCurrency()` — Handles both EU and US number formats
- Country mapping normalizes various spellings (e.g., "Germany", "Deutschland", "DE", "Alemania" → "Amazon DE")

### Filtering Architecture

Filters flow from `FilterBar.tsx` → `App.tsx` state → `filterData()`/`filterAdsData()` in dataProcessor.ts. When no customer filter is selected, ads data defaults to PAN_EU_COUNTRIES only. Sales data and ads data have separate filter functions.

### Path Alias

`@/*` maps to project root (configured in both `tsconfig.json` and `vite.config.ts`).
