# Epic 2: Book Search & Management **Epic Goal:** Enable users to search for books using the Open Library API and add selected books to their reading list with deadline dates, providing the foundation for all progress tracking features. ## Story 2.1: Open Library API Integration Service As a **developer**, I want **a backend service that queries the Open Library API**, so that **users can search for books by title, author, or ISBN**. **Acceptance Criteria:** 1. Service module created in `backend/src/services/openLibraryService.js` 2. Function `searchBooks(query)` implemented: - Makes HTTP request to `https://openlibrary.org/search.json?q={query}` - Parses response and extracts relevant fields: title, author, first_publish_year, cover_i, number_of_pages, isbn - Returns array of book objects with normalized structure - Handles API errors gracefully (returns empty array or error object) 3. Function limits results to top 20 books for performance 4. Book cover URLs constructed using cover_i: `https://covers.openlibrary.org/b/id/{cover_i}-M.jpg` 5. Service includes error handling for network failures and invalid responses 6. Service respects rate limits (implements basic request throttling if needed) 7. Unit tests written for service (mocked HTTP responses) ## Story 2.2: Book Search API Endpoint As a **user**, I want **an API endpoint to search for books**, so that **the frontend can retrieve book search results**. **Acceptance Criteria:** 1. API endpoint created: `GET /api/books/search?q={query}` 2. Endpoint validates query parameter (required, non-empty, max length 200 characters) 3. Endpoint calls `openLibraryService.searchBooks(query)` 4. Returns JSON response with book results: ```json { "results": [ { "olid": "OL12345W", "title": "The Name of the Wind", "author": "Patrick Rothfuss", "publishYear": 2007, "coverUrl": "https://covers.openlibrary.org/b/id/123456-M.jpg", "totalPages": 662 } ] } ``` 5. Returns 400 error if query parameter is missing or invalid 6. Returns 500 error if Open Library API fails, with user-friendly error message 7. Endpoint returns 200 with empty results array if no books found 8. Caches search results for 1 hour (in-memory cache acceptable for MVP) 9. Integration test written for endpoint (mocked Open Library service) ## Story 2.3: Add Book API Endpoint As a **user**, I want **an API endpoint to add a book to my reading list**, so that **I can start tracking progress for that book**. **Acceptance Criteria:** 1. API endpoint created: `POST /api/books` 2. Endpoint accepts JSON request body: ```json { "title": "The Name of the Wind", "author": "Patrick Rothfuss", "totalPages": 662, "coverUrl": "https://covers.openlibrary.org/b/id/123456-M.jpg", "deadlineDate": "2025-03-15" } ``` 3. Endpoint validates all required fields: title, totalPages (>0), deadlineDate (valid date, not in past) 4. Author and coverUrl are optional 5. Endpoint creates new Book record in database via Prisma 6. Sets `status` to "reading" by default 7. Returns 201 status with created book object including generated ID 8. Returns 400 error if validation fails with specific error messages 9. Returns 500 error if database operation fails 10. Unit and integration tests written covering success and error cases ## Story 2.4: List Active Books API Endpoint As a **user**, I want **an API endpoint to retrieve my active books**, so that **the frontend can display my current reading list**. **Acceptance Criteria:** 1. API endpoint created: `GET /api/books` 2. Endpoint queries database for all books with `status = "reading"` 3. Returns JSON array of book objects: ```json { "books": [ { "id": 1, "title": "The Name of the Wind", "author": "Patrick Rothfuss", "totalPages": 662, "coverUrl": "https://covers.openlibrary.org/b/id/123456-M.jpg", "deadlineDate": "2025-03-15", "isPrimary": false, "status": "reading", "createdAt": "2025-12-01T10:00:00Z" } ] } ``` 4. Books ordered by deadline date (soonest first) 5. Returns 200 status with empty array if no active books 6. Returns 500 error if database query fails 7. Integration test written ## Story 2.5: Book Search UI Component As a **user**, I want **a search interface to find and select books**, so that **I can add them to my reading list**. **Acceptance Criteria:** 1. "Add Book" screen/modal component created in `frontend/src/pages/AddBook.jsx` 2. Search input field with placeholder "Search by title, author, or ISBN" 3. Search triggers API call to `/api/books/search?q={query}` on form submit or button click 4. Loading indicator displayed while search is in progress 5. Search results displayed as a list/grid with: - Book cover thumbnail (or placeholder if no cover) - Title (bold) - Author - Total pages - "Select" button 6. Clicking "Select" button navigates to book detail view with pre-filled data 7. Empty state message shown if no results found 8. Error message shown if API call fails 9. Search input debounced (300ms delay) if implementing search-as-you-type 10. Component is mobile-responsive (card layout stacks vertically on small screens) ## Story 2.6: Add Book Form UI As a **user**, I want **a form to confirm book details and set a deadline**, so that **I can add the book to my reading list with a finish date**. **Acceptance Criteria:** 1. Add book form component created (can be part of AddBook screen or separate) 2. Form displays selected book information (cover, title, author, total pages) as read-only 3. Form includes: - Deadline date picker (required) - "Add to Reading List" button - "Cancel" or "Back" button 4. Deadline date picker validates: - Date must be in the future - User-friendly date selection interface (mobile-optimized) 5. Clicking "Add to Reading List" calls `POST /api/books` with form data 6. Loading state shown while API call is in progress 7. Success: User redirected to home screen (book list) with success message 8. Error: Error message displayed below form, user can retry 9. Form validation prevents submission if deadline is invalid 10. Form is mobile-responsive and thumb-friendly ## Story 2.7: Book List Display UI As a **user**, I want **to see all my active books on the home screen**, so that **I can quickly view my reading list and select a book to log progress**. **Acceptance Criteria:** 1. Home screen component created in `frontend/src/pages/Home.jsx` 2. Component fetches active books from `GET /api/books` on mount 3. Books displayed as cards/list items showing: - Cover thumbnail (left side) - Title and author (prominent) - Total pages and deadline date - Placeholder text for pace calculation (to be implemented in Epic 3) 4. "Add Book" button prominently displayed (e.g., floating action button or top-right) 5. Empty state shown if no books (with "Add your first book" message and CTA) 6. Loading state shown while fetching books 7. Error state shown if API call fails (with retry button) 8. Tapping a book card navigates to book detail screen (or triggers log progress modal - Epic 3) 9. List ordered by deadline date (soonest first) 10. Component is mobile-responsive with smooth scrolling ---