# Vehicles API Reference

Complete API documentation for the vehicles feature in MotoVaultPro.

## Overview

The Vehicles API provides endpoints for managing user vehicles, including CRUD operations, image management, and hierarchical dropdown data for vehicle selection forms.

**Authentication**: All endpoints require JWT authentication via `Authorization: Bearer <token>` header.

## Base URL

```
https://motovaultpro.com/api
```

## Vehicle CRUD Operations

### List User Vehicles

Returns all vehicles for the authenticated user.

```
GET /api/vehicles
```

**Response** (200):
```json
[
  {
    "id": "uuid",
    "userId": "auth0|123456",
    "vin": "1HGBH41JXMN109186",
    "make": "Honda",
    "model": "Civic",
    "year": 2021,
    "engine": "2.0L 4-Cylinder",
    "transmission": "CVT Automatic",
    "trimLevel": "EX",
    "driveType": "FWD",
    "fuelType": "Gasoline",
    "nickname": "My Honda",
    "color": "Blue",
    "licensePlate": "ABC123",
    "odometerReading": 15000,
    "isActive": true,
    "createdAt": "2025-01-01T00:00:00.000Z",
    "updatedAt": "2025-01-01T00:00:00.000Z",
    "imageUrl": "/api/vehicles/{id}/image"
  }
]
```

### Get Single Vehicle

```
GET /api/vehicles/:id
```

**Parameters**:
- `id` (path): Vehicle UUID

**Response** (200): Single vehicle object (same structure as list item)

**Errors**:
- `404`: Vehicle not found or not owned by user

### Create Vehicle

```
POST /api/vehicles
```

**Request Body**:
```json
{
  "vin": "1HGBH41JXMN109186",
  "year": 2021,
  "make": "Honda",
  "model": "Civic",
  "engine": "2.0L 4-Cylinder",
  "transmission": "CVT Automatic",
  "trimLevel": "EX",
  "driveType": "FWD",
  "fuelType": "Gasoline",
  "nickname": "My Honda",
  "color": "Blue",
  "licensePlate": "ABC123",
  "odometerReading": 15000
}
```

**Required**: Either `vin` OR `licensePlate` must be provided (not both required).

**Response** (201): Created vehicle object

### Update Vehicle

```
PUT /api/vehicles/:id
```

**Parameters**:
- `id` (path): Vehicle UUID

**Request Body**: Same fields as create (all optional, only provided fields are updated)

**Response** (200): Updated vehicle object

### Delete Vehicle

Soft-deletes a vehicle (sets `deleted_at` timestamp).

```
DELETE /api/vehicles/:id
```

**Parameters**:
- `id` (path): Vehicle UUID

**Response** (204): No content

## Vehicle Images

### Upload Image

Upload or replace the vehicle's image.

```
POST /api/vehicles/:id/image
Content-Type: multipart/form-data
```

**Parameters**:
- `id` (path): Vehicle UUID

**Form Data**:
- `image`: Image file (JPEG, PNG, WebP; max 5MB)

**Response** (200):
```json
{
  "success": true,
  "imageUrl": "/api/vehicles/{id}/image"
}
```

### Download Image

```
GET /api/vehicles/:id/image
```

**Parameters**:
- `id` (path): Vehicle UUID

**Response**: Image binary with appropriate `Content-Type` header

**Errors**:
- `404`: No image exists for vehicle

### Delete Image

```
DELETE /api/vehicles/:id/image
```

**Parameters**:
- `id` (path): Vehicle UUID

**Response** (204): No content

## Dropdown Cascade API

Hierarchical endpoints for vehicle selection dropdowns. Each level filters based on previous selections.

### Get Years

Returns available model years in descending order.

```
GET /api/vehicles/dropdown/years
```

**Response** (200):
```json
{
  "years": [2025, 2024, 2023, 2022, ...]
}
```

### Get Makes

Returns makes available for a specific year.

```
GET /api/vehicles/dropdown/makes?year={year}
```

**Query Parameters**:
- `year` (required): Model year (e.g., 2024)

**Response** (200):
```json
{
  "makes": ["Acura", "Audi", "BMW", "Chevrolet", "Ford", ...]
}
```

### Get Models

Returns models available for a specific year and make.

```
GET /api/vehicles/dropdown/models?year={year}&make={make}
```

**Query Parameters**:
- `year` (required): Model year
- `make` (required): Make name (e.g., "Ford")

**Response** (200):
```json
{
  "models": ["Bronco", "Edge", "Explorer", "F-150", "Mustang", ...]
}
```

### Get Trims

Returns trims available for a specific year, make, and model.

```
GET /api/vehicles/dropdown/trims?year={year}&make={make}&model={model}
```

**Query Parameters**:
- `year` (required): Model year
- `make` (required): Make name
- `model` (required): Model name (e.g., "F-150")

**Response** (200):
```json
{
  "trims": ["XL", "XLT", "Lariat", "King Ranch", "Platinum", ...]
}
```

### Get Engines

Returns engines available for a specific year, make, model, and trim.

```
GET /api/vehicles/dropdown/engines?year={year}&make={make}&model={model}&trim={trim}
```

**Query Parameters**:
- `year` (required): Model year
- `make` (required): Make name
- `model` (required): Model name
- `trim` (required): Trim level (e.g., "XLT")

**Response** (200):
```json
{
  "engines": [
    "3.3L V6 Ti-VCT",
    "2.7L V6 EcoBoost",
    "5.0L V8 Ti-VCT",
    "3.5L V6 EcoBoost"
  ]
}
```

### Get Transmissions

Returns transmissions available for a specific year, make, model, and trim.

```
GET /api/vehicles/dropdown/transmissions?year={year}&make={make}&model={model}&trim={trim}
```

**Query Parameters**:
- `year` (required): Model year
- `make` (required): Make name
- `model` (required): Model name
- `trim` (required): Trim level

**Response** (200):
```json
{
  "transmissions": [
    "10-Speed Automatic",
    "6-Speed Automatic"
  ]
}
```

### Get Pair-Safe Options

Returns valid engine/transmission combinations, ensuring only compatible pairs are shown.

```
GET /api/vehicles/dropdown/options?year={year}&make={make}&model={model}&trim={trim}[&engine={engine}][&transmission={transmission}]
```

**Query Parameters**:
- `year` (required): Model year
- `make` (required): Make name
- `model` (required): Model name
- `trim` (required): Trim level
- `engine` (optional): If provided, returns only transmissions compatible with this engine
- `transmission` (optional): If provided, returns only engines compatible with this transmission

**Response** (200):
```json
{
  "engines": ["3.3L V6 Ti-VCT", "2.7L V6 EcoBoost"],
  "transmissions": ["10-Speed Automatic"]
}
```

## Platform API

Direct platform endpoints for vehicle data lookups (alternative to dropdown cascade).

```
GET /api/platform/years
GET /api/platform/makes?year={year}
GET /api/platform/models?year={year}&make={make}
GET /api/platform/trims?year={year}&make={make}&model={model}
GET /api/platform/engines?year={year}&make={make}&model={model}&trim={trim}
GET /api/platform/transmissions?year={year}&make={make}&model={model}&trim={trim}
```

Same functionality as dropdown cascade API but with `/api/platform/` prefix.

## Error Responses

All endpoints return standard error responses:

```json
{
  "error": "Error message",
  "statusCode": 400
}
```

**Common Status Codes**:
- `400`: Bad request (validation error)
- `401`: Unauthorized (missing or invalid JWT)
- `404`: Resource not found
- `500`: Internal server error

## Data Model

### Vehicle Fields

| Field | Type | Required | Description |
|-------|------|----------|-------------|
| id | UUID | Auto | Primary key |
| userId | string | Auto | Auth0 user ID (from JWT) |
| vin | string | No* | Vehicle Identification Number (17 chars) |
| make | string | No | Manufacturer (e.g., "Ford") |
| model | string | No | Model name (e.g., "F-150") |
| year | integer | No | Model year |
| engine | string | No | Engine specification |
| transmission | string | No | Transmission type |
| trimLevel | string | No | Trim level (e.g., "XLT") |
| driveType | string | No | Drive type (e.g., "4WD", "FWD") |
| fuelType | string | No | Fuel type (e.g., "Gasoline", "Diesel") |
| nickname | string | No | User-defined name |
| color | string | No | Vehicle color |
| licensePlate | string | No* | License plate number |
| odometerReading | integer | No | Current odometer (default: 0) |
| isActive | boolean | Auto | Active status (default: true) |
| createdAt | datetime | Auto | Creation timestamp |
| updatedAt | datetime | Auto | Last update timestamp |
| imageUrl | string | Auto | URL to vehicle image (if uploaded) |

*Either `vin` OR `licensePlate` should be provided for vehicle identification.

### VIN Validation

When a VIN is provided:
- Must be exactly 17 characters
- Cannot contain letters I, O, or Q
- Check digit validation is performed

## Database Schema

### Platform Tables

Vehicle lookup data is stored in three denormalized tables optimized for dropdown cascade queries:

- **engines**: Engine specifications (name, displacement, horsepower, fuel_type, etc.)
- **transmissions**: Transmission types (type, speeds, drive_type)
- **vehicle_options**: Denormalized year/make/model/trim combinations with engine/transmission references

See `docs/DATABASE-SCHEMA.md` for complete table definitions.

### Migration Location

Platform migrations: `backend/src/features/platform/migrations/001_create_vehicle_lookup_schema.sql`

## Caching

- **Dropdown data**: Cached in Redis for 6 hours (key: `dropdown:{dataType}:{params}`)
- **User vehicle lists**: Cached for 5 minutes (key: `vehicles:user:{userId}`)
- Cache is invalidated on vehicle create/update/delete operations

## Frontend Integration

### Form Cascade Order

The vehicle form uses cascading dropdowns in this order:
1. Year (loads makes)
2. Make (loads models)
3. Model (loads trims)
4. Trim (loads engines and transmissions)
5. Engine and Transmission (pair-safe filtering via `/dropdown/options`)

### Files

- Form component: `frontend/src/features/vehicles/components/VehicleForm.tsx`
- Types: `frontend/src/features/vehicles/types/vehicles.types.ts`
- API hooks: `frontend/src/features/vehicles/hooks/`

## Related Documentation

- Feature README: `backend/src/features/vehicles/README.md`
- Platform README: `backend/src/features/platform/README.md`
- Database Schema: `docs/DATABASE-SCHEMA.md`
- Architecture: `docs/ARCHITECTURE-OVERVIEW.md`
