# Book Search & Discovery — Spec

## Overview
Enable users to search books within the library and discover new books via filters and a dedicated detail view.

## Backend API Contracts

### Book List & Search
`GET /api/books/`

**Query Parameters:**
| Param | Type | Description |
|-------|------|-------------|
| `q` | string | Full-text search across title, author, genre |
| `genre` | string | Exact filter by genre |
| `author` | string | Exact filter by author |
| `reading_status` | string | Filter: `want_to_read`, `reading`, `finished`, `dnf` |
| `ordering` | string | `title`, `author`, `genre`, `created_at` (prefix `-` for desc) |
| `page` | int | Page number (default: 1) |

**Response (paginated):**
```json
{
  "count": 42,
  "next": "http://.../?page=2",
  "previous": null,
  "results": [
    {
      "id": 1,
      "title": "Dune",
      "author": "Frank Herbert",
      "genre": "Science Fiction",
      "reading_status": "finished",
      "reading_status_display": "Finished",
      "cover_image": "https://..."
    }
  ]
}
```

### Book Detail
`GET /api/books/{id}/`

**Response:**
```json
{
  "id": 1,
  "title": "Dune",
  "author": "Frank Herbert",
  "genre": "Science Fiction",
  "description": "...",
  "reading_status": "finished",
  "reading_status_display": "Finished",
  "cover_image": "https://...",
  "total_pages": 688,
  "created_at": "2025-01-01T00:00:00Z",
  "updated_at": "2025-01-15T00:00:00Z"
}
```

### Genre / Author Discovery
`GET /api/books/genres/` → `["Fiction", "Science Fiction", ...]`

`GET /api/books/authors/` → `["Frank Herbert", "Ursula K. Le Guin", ...]`

## Frontend Components

### LibraryPage (enhanced)
- **Search bar** at top: text input with debounced `onChange` → calls API with `q` param
- **Filter row**: genre dropdown, author dropdown, reading status dropdown
  - Genre/Author dropdowns populated from `/api/books/genres/` and `/api/books/authors/`
  - Reading status uses static enum values (`READING_STATUS_OPTIONS`)
- **Results grid**: card layout showing cover, title, author, reading status badge
- **Empty state**: "No books found" with clear message when results are empty
- **Loading state**: spinner/skeleton while fetching
- **Click card → navigate to** `/books/{id}`

### BookDetailPage (new)
- Shows full book info: cover, title, author, genre, description, reading status, total pages
- Back button to return to library
- Clean, mobile-responsive layout

### API Client — `frontend/src/api/books.ts`

| Method | Endpoint | Returns |
|--------|----------|---------|
| `searchBooks(params)` | `GET /api/books/` | `{count, results: BookListItem[]}` |
| `getBook(id)` | `GET /api/books/{id}/` | `BookDetail` |
| `getGenres()` | `GET /api/books/genres/` | `string[]` |
| `getAuthors()` | `GET /api/books/authors/` | `string[]` |

## Routes (Frontend)
| Path | Component | Auth |
|------|-----------|------|
| `/` | LibraryPage | Protected |
| `/books/:id` | BookDetailPage | Protected |

## Data Flow
1. User types in search bar → 300ms debounce → `GET /api/books/?q=...`
2. User selects filter → `GET /api/books/?genre=...&author=...&reading_status=...`
3. User clicks result → navigate to `/books/:id`
4. BookDetailPage → `GET /api/books/{id}/`

## Mobile Optimizations
- Filters collapse into a toggleable panel on small screens
- Cards stack in single column on mobile
- Touch-friendly tap targets (min 44px)