Replace direct playwright dependency with @playwright/test and add playwright.config.js for centralized test configuration. Update run.sh to invoke 'npx playwright test' instead of running test files with node. |
||
|---|---|---|
| .idea | ||
| data/keys | ||
| docs/plans | ||
| scripts | ||
| src/porchlight | ||
| tests | ||
| .dockerignore | ||
| .gitignore | ||
| docker-compose.yml | ||
| Dockerfile | ||
| pyproject.toml | ||
| README.md | ||
| uv.lock | ||
Porchlight
OpenID Connect Provider with user management, built with FastAPI.
Porchlight handles user registration (via magic links), credential management (passwords and WebAuthn security keys), and issues OIDC tokens for relying parties. It uses SQLite for storage, Jinja2 + HTMX for the UI, and idpyoidc for the OIDC protocol layer.
Production Setup
Docker (recommended)
docker compose --profile prod up --build
This starts Porchlight on port 8000 with 4 uvicorn workers. Data is persisted in a named Docker volume.
Set required environment variables in docker-compose.yml or via .env:
OIDC_OP_ISSUER=https://auth.example.com
OIDC_OP_SESSION_SECRET=<random-secret>
Manual
Requires Python 3.13+ and uv.
uv sync --no-dev
OIDC_OP_ISSUER=https://auth.example.com \
OIDC_OP_SESSION_SECRET=$(python -c "import secrets; print(secrets.token_hex(32))") \
uv run uvicorn fastapi_oidc_op.app:create_app \
--factory --host 0.0.0.0 --port 8000 --workers 4
Configuration
All settings are read from environment variables with the OIDC_OP_ prefix:
| Variable | Default | Description |
|---|---|---|
OIDC_OP_ISSUER |
required | OIDC issuer URL (must match public URL) |
OIDC_OP_SESSION_SECRET |
random per process | Session cookie signing secret |
OIDC_OP_DEBUG |
false |
Enable /docs Swagger UI |
OIDC_OP_SQLITE_PATH |
data/oidc_op.db |
SQLite database path |
OIDC_OP_SIGNING_KEY_PATH |
data/keys |
OIDC signing key storage |
OIDC_OP_INVITE_TTL |
86400 |
Magic link expiry in seconds |
OIDC_OP_MANAGE_CLIENT_ID |
manage-app |
Client ID for the management UI |
Database migrations run automatically on startup.
Development Setup
Prerequisites
- Python 3.13+
- uv
- Node.js (for e2e tests)
Getting started
# Install dependencies (including dev tools)
uv sync
# Start the dev server with hot reload
OIDC_OP_ISSUER=http://localhost:8000 OIDC_OP_DEBUG=true \
uv run uvicorn fastapi_oidc_op.app:create_app \
--factory --host 127.0.0.1 --port 8000 --reload --reload-dir src
Or with Docker:
docker compose --profile dev up --build
Running tests
# Unit/integration tests
uv run pytest
# Lint and format
uv run ruff check src/ tests/ --fix
uv run ruff format src/ tests/
# Type checking
uv run ty check src/
End-to-end browser tests
The e2e suite uses Playwright (Node.js) to test all user-facing flows against a running instance of the app.
# One-time setup: install Playwright and Chromium
cd tests/e2e
npm install && npm run setup
cd ../..
# Run all e2e tests
./tests/e2e/run.sh
# Run a specific test
./tests/e2e/run.sh tests/e2e/test_login.js
# Run with visible browser (not headless)
E2E_HEADLESS=0 ./tests/e2e/run.sh
The runner starts the app on port 8099, seeds test fixtures into a temporary
SQLite database, runs all test_*.js files, and tears everything down.
Full quality check
uv run ruff format src/ tests/
uv run ruff check src/ tests/ --fix
uv run ty check src/
uv run pytest
./tests/e2e/run.sh