---
auto_generated: true
created: 2026-05-18
manual_updated_at: 2026-05-18
modified: 2026-05-18
name: Developer_Manual
status: active
tags:
- client/oliver
- domain/accessibility
- domain/security
- tech/azure-ad
- tech/claude
- tech/docker
- tech/postgresql
- tech/python
type: sop
---

# PDF Accessibility Checker Developer Manual

## Architecture Overview

The application is a microservice-oriented system comprising:
1. **Web Frontend**: HTML/CSS/JS interface for upload, visualization, and result inspection.
2. **Backend API (Python)**: Handles file processing, AI analysis coordination, database interactions, and API authentication.
3. **Database (PostgreSQL)**: Stores job metadata, analysis results, and user configuration.
4. **External Services**:
   - **Anthropic Claude 3.5 Sonnet**: Used for AI-powered image alt-text generation and analysis.
   - **Google Cloud Vision**: Optional OCR and text-in-image detection.
   - **Cloud Run**: Optional external service for offloading PDF processing tasks.

## Tech Stack

- **Backend**: Python 3, FastAPI/Flask (implied by REST API structure), veraPDF for validation.
- **Frontend**: Vanilla JavaScript, HTML5, CSS3 (Tailwind-like utility classes).
- **Database**: PostgreSQL 16.
- **Containerization**: Docker & Docker Compose.
- **Authentication**: Azure AD (MSAL) for UI access, API Key for REST access.
- **AI**: Anthropic API, Google Cloud Vision API.

## Local Setup

### Prerequisites
- Docker and Docker Compose.
- Python 3.9+ (for local script execution without Docker).
- API Keys for Anthropic and optionally Google Cloud.

### Step-by-Step Setup

1. **Clone the Repository**:
   ```bash
   git clone <repo-url>
   cd pdf-accessibility-checker
   ```

2. **Environment Configuration**:
   ```bash
   cp .env.example .env
   ```
   Edit `.env` and fill in:
   - `ANTHROPIC_API_KEY`: Required for AI image analysis.
   - `GOOGLE_API_KEY` or `GOOGLE_APPLICATION_CREDENTIALS`: Optional, for enhanced OCR.
   - `DB_PASSWORD`: Set a strong password for PostgreSQL.
   - `AZURE_TENANT_ID`, `AZURE_CLIENT_ID`, `AZURE_REDIRECT_URI`: For Azure AD login.
   - `CLOUD_RUN_URL`: Set if deploying to GCP Cloud Run; leave empty for local processing.

3. **Start Services**:
   ```bash
   docker-compose up -d
   ```
   This starts the web app on port 8000 and PostgreSQL on port 5432.

4. **Verify Installation**:
   - Web UI: `http://localhost:8000`
   - API: `http://localhost:8000/api/` (requires API key in headers).

5. **Run Tests**:
   ```bash
   # Activate virtual environment first if not using Docker
   pip install -r requirements.txt
   pytest
   ```
   There are 31 automated tests covering core functionality.

## Environment Variables

| Variable | Required | Description |
|----------|----------|-------------|
| `ANTHROPIC_API_KEY` | Yes | API key for Anthropic Claude. |
| `GOOGLE_API_KEY` | No | Google Cloud Vision API key (optional). |
| `GOOGLE_APPLICATION_CREDENTIALS` | No | Path to Google credentials JSON (alternative to API key). |
| `DEV_MODE` | No | Set to `true` to bypass Azure AD auth for local dev. |
| `DB_HOST` | Yes | PostgreSQL host (default `postgres`). |
| `DB_PORT` | Yes | PostgreSQL port (default `5432`). |
| `DB_NAME` | Yes | Database name (default `pdf_checker`). |
| `DB_USER` | Yes | Database user (default `pdf_checker`). |
| `DB_PASSWORD` | Yes | Database password. |
| `CLOUD_RUN_URL` | No | URL for external Cloud Run service. |
| `GCP_SA_KEY_PATH` | No | Path to GCP Service Account key for Cloud Run auth. |
| `GCS_BUCKET_NAME` | No | GCS bucket for storing page images. |
| `RETENTION_HOURS` | No | Hours to keep uploaded PDFs (default 24). |
| `RESULTS_RETENTION_HOURS` | No | Hours to keep result JSONs (default 720). |
| `AZURE_TENANT_ID` | Yes | Azure AD Tenant ID. |
| `AZURE_CLIENT_ID` | Yes | Azure AD Client ID. |
| `AZURE_REDIRECT_URI` | Yes | Azure AD Redirect URI. |

## Key Services & Entry Points

- **`js/batch.js`**: Handles multi-file drag-and-drop and upload logic.
- **`js/page-viewer.js`**: Renders the visual page inspector with SVG markers for issues.
- **`js/results.js`**: Displays scores, severity counts, and manages issue filtering/dismissal logic.
- **`js/upload.js`**: Handles single-file upload and polling for analysis status.
- **`docker-compose.yml`**: Defines the web and postgres services.
- **`.env.example`**: Template for configuration.

## API Reference

### Authentication
- **UI**: Uses Azure AD via MSAL.
- **REST**: Requires an API key in the `Authorization` header (e.g., `Bearer <api_key>`).

### Endpoints
- `POST /upload`: Uploads a PDF for analysis. Returns a `job_id`.
- `GET /results/{job_id}`: Retrieves analysis results. Poll this endpoint until `status` is `completed`.
- `GET /api/image?job_id=&page=`: Retrieves the rendered page image for the visual inspector.

### Payload Example (Results)
```json
{
  "accessibility_score": 85,
  "severity_counts": { "critical": 0, "error": 2, "warning": 5, "info": 1, "success": 10 },
  "issues": [ ... ],
  "page_images": { "1": "https://...", "2": "https://..." },
  "wcag_compliance": { "1.1.1": "A", "1.4.3": "AA" },
  "dismissed_indices": [],
  "score_breakdown": { "adjusted": false }
}
```

## Deployment

1. **Environment**: Set `DEV_MODE=false` and use production DB credentials.
2. **Secrets**: Never commit `.env`. Use secrets management (e.g., AWS Secrets Manager, GCP Secret Manager) for API keys.
3. **Cloud Run**: Deploy the Python service to Cloud Run using `CLOUD_RUN_URL` and `GCP_SA_KEY_PATH` for authentication.
4. **Database**: Use a managed PostgreSQL instance (e.g., Cloud SQL, Azure Database).
5. **Storage**: Configure GCS bucket for image storage if using Cloud Run.

## Known Gotchas

1. **Duplicate Files**: The frontend (`js/batch.js`) prevents adding duplicate files based on name and size. Ensure backend also validates.
2. **AI Costs**: AI analysis via Anthropic and Google Cloud incurs costs. Monitor usage.
3. **Polling**: Frontend uses polling for analysis status. Implement exponential backoff on the backend if processing takes long.
4. **Retention**: Ensure `RETENTION_HOURS` and `RESULTS_RETENTION_HOURS` are set correctly to manage storage costs.
5. **Auth Bypass**: Never leave `DEV_MODE=true` in production.
6. **Imports**: A critical import bug was previously fixed in the remediation module. Ensure all imports are relative and correct if modifying Python code.

## Related
- [[01 Projects/ppt-tool/DEVELOPER_MANUAL]]
- [[01 Projects/ppt-tool/DEVELOPER_MANUAL.md]]
- [[01 Projects/pdf-accessibility/USER_MANUAL.md]]
- [[01 Projects/pdf-accessibility/DEVELOPER_MANUAL.md]]