Compendium
A library card catalog system for physical items — books, vinyl records, DVDs, CDs.
Features
- Catalog — add items by ISBN / UPC / MusicBrainz ID / TMDb ID / title search (Google Books / Open Library, MusicBrainz, TMDb) or manually for obscure items; search and browse works and copies; faceted discovery (media type, decade, availability)
- Recoverable work deletion — deleting a work moves it (copies, loan/hold history, notes, creator links, curated-list memberships) to a trash, restorable from Recently Deleted,
compendium work trash, or the API; blocked while copies are on loan or carry outstanding fines; holds are cancelled; trashed works auto-purge after a configurable retention window (COMPENDIUM_TRASH_RETENTION_DAYS, default 90 days) - Circulation — checkout, checkin, loan renewal with category-aware per-media-type loan policies; lost / damaged / claims-returned states; self-checkout kiosk mode; library hours and holiday calendar so due dates never land on closed days and overdue fines skip closed days
- Holds — patron reservation queue; immediate promotion when a copy is available; suspend/resume; auto-expiry via maintenance command
- Fines — configurable per-policy overdue rates with caps and grace periods; lost/damaged fees; threshold-based checkout/hold blocking; pay/waive workflow; per-patron and bulk overdue assessment
- Notifications — outbox-pattern email delivery (hold-ready, due-soon, overdue) drained by a cron-invoked CLI; admin viewer + retry; per-patron opt-out; configurable retention
- Reports — checkouts/month, popular works, dormant items (weeding list), current overdues; CSV export; Chart.js trendlines
- Patrons & cards — patron categories (Adult/Child/Staff/Teacher seeded), card expiry with maintenance auto-deactivation, optional 1:1 patron↔user link for self-service
- Bulk import/export — round-trippable CSV; MARC21 binary + MARCXML import/export; LibraryThing TSV import; GoodReads CSV import; Discogs collection-CSV import (all with lenient encoding for messy real-world exports)
- Backup/restore — portable JSONL tarballs; backend-agnostic (SQLite ↔ Postgres); doubles as a DB migration path
- Labels — Avery-template item labels (spine / pocket) and patron cards (full / sticker) as PDFs. Spine templates:
avery-5167-spine(½" narrow face),avery-5160-spine(1" medium face, rotated),avery-5160(flat wrap-around, centered text),avery-22805/avery-22806(square classification labels). Live in-page SVG preview updates as you change kind/template/fields — no PDF round-trip needed. - Curated lists — librarian-editable named collections of Works ("Staff picks", "Summer reads") with slugs, per-work annotations, public/private and featured toggles; featured lists appear as a shelf on the OPAC landing page; public browse at
/ui/lists - Auth — five preset roles (ReadOnly, Patron, Librarian, SystemAdmin, Administrator) plus custom roles via the admin UI; JWT for API, cookie-based for web UI
- Audit log — synchronous trail of administrative mutations (Librarian + system tier); queryable via web UI, CLI, or REST
- DB-editable settings — most configuration knobs (library name, fines, kiosk timeout, SMTP, retention, configurable nav shortcuts, etc.) editable from the UI / CLI / API; env vars still win as a break-glass
- Remote phone scanner — pair a phone to the circulation desk via QR code; the phone camera dispatches scans to the desk in real time without installing an app. Supports checkout, checkin, and catalog-lookup modes. Pairing is ephemeral: a short-TTL claim secret lives in the QR; after the phone claims it, the secret rotates to a session cookie; the librarian can unpair from the desk at any time. Requires HTTPS on both the server and the phone browser (secure context for camera). Settings:
public_base_url(DB-editable, envCOMPENDIUM_PUBLIC_BASE_URL) andscan_session_minutes(DB-editable, envCOMPENDIUM_SCAN_SESSION_MINUTES, default 60). - Circulate by ISBN/UPC — checkout, checkin, and renew accept a book's printed ISBN barcode (or a disc's UPC) in place of a Compendium item label, so home and classroom libraries don't need to print labels. With several copies of the same title on loan, checkin asks the desk which copy came back rather than guessing. Toggle with the
circulation_scan_isbn_enabledsetting (envCOMPENDIUM_CIRCULATION_SCAN_ISBN_ENABLED, default on) at Admin → Settings → Circulation. - Web UI — HTMX + Jinja2 browser interface with catalog search, circulation desk (camera-based barcode scanning), patron self-service, light/dark/auto theme; per-user nav shortcut overrides via browser localStorage
- REST API — FastAPI; consumed by the web UI and available for integrations
- CLI — full librarian + sysadmin workflow without running a server, including stdin/stdout (
-) for backup, import/export, and labels
Install
# Install the CLI as a standalone tool (recommended for production)
uv tool install compendium-ils # SQLite only
uv tool install "compendium-ils[postgres]" # + Postgres support
# Or with pip
pip install compendium-ils
pip install "compendium-ils[postgres]"
The installed command is compendium.
Quick start
Quick start (Docker)
One command — needs only Docker with the compose plugin:
curl -fsSL https://raw.githubusercontent.com/statyk/compendium/master/install.sh | sh
This scaffolds a ./compendium/ deployment (compose file, nginx, generated
secrets) and starts it. Already have the package installed? compendium init ./compendium does the scaffold step alone. See docs/deployment.md for details.
Prerequisites
Python 3.11.4 or newer. (Backup restore uses the tarfile data filter from
PEP 706, which was backported to 3.11.4.)
Debian / Ubuntu
sudo apt-get update
sudo apt-get install -y python3 python3-venv python3-dev build-essential
curl -LsSf https://astral.sh/uv/install.sh | sh
source $HOME/.local/bin/env
RedHat / CentOS / Fedora
sudo dnf install -y python3 python3-devel gcc
curl -LsSf https://astral.sh/uv/install.sh | sh
source $HOME/.local/bin/env
macOS
brew install python uv
Run
# Install dependencies
uv sync --extra dev
# Initialise the database (creates ./compendium.db with SQLite by default)
uv run compendium db init
# Create an Administrator account
uv run compendium user add --username admin --role Administrator
# Add a book by ISBN (looks up metadata from Google Books when key is set, else Open Library)
uv run compendium item add --isbn 9780441013593
# Add a patron
uv run compendium patron add --name "Alice Example"
# Start the server (web UI at http://localhost:8000/ui/catalog)
uv run compendium serve
Log in at http://localhost:8000/ui/login with the username and password you set above.
CLI reference
Run compendium --help for the full command tree, or compendium <group> --help for the subcommands of a specific group.
Catalog & cataloging
| Group | Common subcommands |
|---|---|
item |
add (--isbn / --upc / --mbid / --tmdb-id / --title), add-manual, show, edit (location/call-number/condition/notes/loanable), withdraw; note add/list/delete; declare-lost, mark-damaged, clear-lost, clear-damage |
work |
list, search, show, new-arrivals, recently-returned, delete; trash list/restore/purge |
creator |
edit |
curated-list |
add, list, show, edit, delete, add-work, remove-work, reorder |
branch |
list, edit |
import |
csv, marc (use - for stdin) |
export |
csv, marc (use - for stdout) |
Circulation
| Group | Common subcommands |
|---|---|
loan |
checkout, checkin, renew, active, list (system-wide), history, item-history |
claim |
returned (patron disputes), verify (found), write-off, list |
hold |
place, cancel, list, queue, suspend, resume, list-suspended |
fine |
list, pay, waive, assess, assess-overdue |
Patrons & accounts
| Group | Common subcommands |
|---|---|
patron |
add, list (--include-inactive), edit, link-user, unlink-user, add-user, deactivate, reactivate |
patron-category |
list, add, edit, delete |
user |
add (default --role Administrator), list (--include-inactive), edit (role and/or password), deactivate, reactivate |
role |
list, add, edit, clone |
policy |
list, add, edit (configures fines, category-aware) |
Reporting & labels
| Group | Common subcommands |
|---|---|
reports |
checkouts, popular, dormant, overdues (each supports --format csv) |
labels |
templates, spine, pocket, barcode, patron-card, patron-sticker (output -o - writes PDF to stdout; use --show/--hide for field toggles, e.g. --show barcode on spine) |
audit |
list (filters: --entity, --id, --user-id, --limit) |
Operations
| Command | Description |
|---|---|
compendium db init / db upgrade / db history |
Migrate the database |
compendium serve |
Start the API + web UI server |
compendium backup --output <path-or-> |
Write a portable JSONL tarball backup |
compendium restore <path-or-> |
Restore from a backup tarball (lenient — auto-migrates) |
compendium settings list/get/set/reset |
Inspect & edit DB-backed site settings |
compendium maintenance ... |
Cron-invoked tasks: expire-holds, resume-expired-suspends, assess-overdue-fines, queue-due-soon-notices, queue-overdue-notices, send-queued-notifications, prune-notifications, prune-audit-log, deactivate-expired-patrons, prune-cover-cache, prune-metadata-cache, prune-scan-pairings, refresh-metadata, purge-trash |
compendium metadata cache stats |
Show metadata cache row counts by adapter and TTL status |
compendium metadata cache clear |
Delete all metadata cache rows (audited) |
File-argument commands (backup, restore, import, export, labels spine/pocket/barcode/patron-card/patron-sticker) accept - for stdin/stdout. Status messages are routed to stderr in stdio mode so they don't corrupt binary output.
Every list/show command accepts --format table|json (table is the default; the reports group also keeps --format csv). table renders a readable rich table; json prints stable, script-friendly JSON to stdout — snake_case keys, ISO-8601 UTC datetimes, integer cents — with any notices sent to stderr instead, so output stays pipeable. For example:
compendium loan list --format json | jq '.[].due_at'
Web UI
Start the server with compendium serve and open your browser to http://localhost:8000/ui/catalog.
"Audience" lists the minimum preset that can access each route. Administrator can access everything. SystemAdmin gets the System-tier rows; slimmed Librarian gets librarian-tier rows but not System-tier.
| URL | Audience | Description |
|---|---|---|
/ui/catalog |
Anyone | Search catalog with facets (media type, decade, availability); featured curated lists shelf |
/ui/catalog/{work_id} |
Anyone | Work detail, items, place-hold button |
/ui/lists |
Anyone | Public OPAC browse of public curated lists |
/ui/lists/{slug} |
Anyone | Public curated list detail with annotated works |
/ui/login |
Anyone | Login form |
/ui/me/loans |
Patron | Active loans with inline renew + "I returned this" claim |
/ui/me/holds |
Patron | Active holds with inline cancel + suspend/resume |
/ui/me/fines |
Patron | Outstanding and historical fines |
/ui/me/preferences |
Patron | Notification opt-out |
/ui/me/password |
Patron | Self-service password change |
/ui/circ |
Librarian | Circulation desk — checkout / checkin / renew |
/ui/kiosk |
Librarian | Self-checkout kiosk landing/session (patron card-number-only auth) |
/ui/items/new |
Librarian | Add item by ISBN / UPC / MBID / TMDb ID / title search (with barcode scanner) |
/ui/items/new/manual |
Librarian | Manually add an item not found in external sources |
/ui/items/{barcode} |
Librarian | Item detail, loan history, withdraw, edit (incl. loanable toggle), lost/damaged/claims actions |
/ui/patrons |
Librarian | Patron list |
/ui/patrons/new |
Librarian | Create patron (with category + expiry) |
/ui/patrons/{card} |
Librarian | Patron detail with active loans, holds, link/unlink user, deactivate, reactivate |
/ui/patrons/{card}/loans |
Librarian | Patron loan history (active / returned / all) |
/ui/patrons/{card}/fines |
Librarian | Patron fines with pay/waive |
/ui/admin/loans |
Librarian | All active loans (system-wide) with overdue/due-soon filters |
/ui/admin/fines |
Librarian | All outstanding fines (system-wide) with running total |
/ui/admin/holds |
Librarian | All active holds with status/branch/work filters |
/ui/admin/claims |
Librarian | Outstanding claims-returned investigations |
/ui/admin/notifications |
Librarian | Notification log + manual retry |
/ui/admin/import |
Librarian | Bulk CSV / GoodReads CSV / LibraryThing TSV / Discogs CSV / MARC import |
/ui/admin/export |
Librarian | Bulk CSV/MARC export |
/ui/admin/patron-categories |
Librarian | Manage patron categories |
/ui/curated-lists |
Librarian | Curated list admin CRUD (curatedlist.manage) |
/ui/trash |
Librarian | Recently Deleted — restore or permanently delete trashed works (work.delete) |
/ui/admin/settings/general |
Librarian | Library name, default theme, guest search |
/ui/admin/settings/circulation |
Librarian | Currency, fine thresholds, hold/overdue/due-soon defaults |
/ui/admin/settings/kiosk |
Librarian | Kiosk idle timeout |
/ui/scan/pair |
Librarian | Generate a QR code to pair a phone as a remote barcode scanner |
/ui/scan/desk |
Librarian | Desk-side view: shows live scan count and unpair button for an active phone session |
/ui/scan/phone/* |
Phone browser | Phone-side claim, mode selector, and continuous scan loop (camera; requires HTTPS / secure context) |
/ui/policies |
Librarian | Loan policy list with inline edit |
/ui/policies/new |
Librarian | Create loan policy (per media type + patron category) |
/ui/branches |
Librarian | Branch list with classification scheme |
/ui/branches/{id}/edit |
Librarian | Edit a branch's default classification scheme |
/ui/reports |
Librarian | Reports landing — checkouts, popular, dormant, overdues |
/ui/labels |
Librarian | Generate item-label and patron-card PDFs (Avery templates) |
/ui/audit |
Librarian | Audit log viewer |
/ui/users |
SystemAdmin | User list |
/ui/users/new |
SystemAdmin | Create user |
/ui/users/{username} |
SystemAdmin | User detail — change role, deactivate, reactivate, reset password |
/ui/roles |
SystemAdmin | Role list |
/ui/roles/new |
SystemAdmin | Create custom role |
/ui/roles/{id} |
SystemAdmin | Role detail — edit permissions, clone |
/ui/admin/system/smtp |
SystemAdmin | SMTP host/port/from settings |
/ui/admin/system/secrets |
SystemAdmin | Encrypted secrets (SMTP password, TMDb / Google Books API keys) — requires COMPENDIUM_SECRET_KEY |
/ui/admin/system/retention |
SystemAdmin | Notification + audit retention, batch sizes |
Guest catalog search is enabled by default (toggle via /ui/admin/settings/general or COMPENDIUM_GUEST_SEARCH_ENABLED=false).
ISBN/UPC circulation fallback is enabled by default (toggle via /ui/admin/settings/circulation or COMPENDIUM_CIRCULATION_SCAN_ISBN_ENABLED=false).
REST API endpoints
The API is mounted at the root. Authenticate with POST /auth/login and pass the result as Authorization: Bearer <token>. Interactive docs live at http://localhost:8000/docs when the server is running.
Below is a high-level inventory grouped by concern; the OpenAPI document is the source of truth for parameters and bodies.
| Group | Common endpoints | Min permission |
|---|---|---|
| Auth | POST /auth/login |
none |
| Catalog | GET /works/search, /works/new-arrivals, /works/recently-returned; GET /items/{barcode}; POST /items/{barcode}/{withdraw,loanable,lost,damaged,clear-lost,clear-damage}; DELETE /works/{id} |
guest / item.view / item.delete / fine.manage / work.delete |
| Trash | GET /trash, POST /trash/{id}/restore, DELETE /trash/{id} |
work.delete |
| Patrons | GET/POST /patrons, PATCH /patrons/{card}, POST /patrons/{card}/{deactivate,reactivate}, POST /patrons/{card}/account, GET/POST /patron-categories, PATCH/DELETE /patron-categories/{id} |
patron.manage / patron.account.manage for account endpoints |
| Loans | POST /loans/checkout, /loans/{id}/{checkin,renew}; GET /loans (system-wide), /loans/patron/{card}, /loans/item/{barcode} |
loan.* (see below) |
| Claims | GET /claims; POST /claims/{barcode}/{returned,verify,write-off} |
loan.checkin |
| Holds | GET /holds, /holds/queue/{work_id}; POST/DELETE /holds, /holds/{id}; POST /holds/{id}/{suspend,resume} |
hold.* |
| Fines | GET /fines, GET/POST /patrons/{card}/fines, POST /fines/{id}/{pay,waive}, POST /patrons/{card}/fines/assess-overdue |
fine.manage / fine.view.self |
| Self-service | GET /me/loans, /me/holds; POST /me/holds, /me/holds/{id}/{suspend,resume}; DELETE /me/holds/{id}; POST /me/loans/{id}/{renew,claim-returned} |
*.self permissions |
| Notifications | GET /notifications, POST /notifications/{id}/retry |
notification.manage |
| Reports | GET /reports/{checkouts,popular,dormant,overdues} |
report.view |
| Bulk import/export | POST /import/{csv,goodreads,librarything,marc} (multipart), GET /export/{csv,marc} (streaming) |
catalog.import / item.view |
| Labels | GET /labels/items, /labels/patrons (PDF) |
labels.generate |
| Policies | GET/POST /policies |
item.view / policy.edit |
| Users | POST /users, POST /users/{username}/{deactivate,reactivate}, POST/DELETE /users/{username}/patron |
user.manage |
| Curated lists | GET/POST /curated-lists, PATCH/DELETE /curated-lists/{slug}, POST/DELETE /curated-lists/{slug}/works |
guest / curatedlist.manage |
| Settings | GET /settings/, GET/PATCH/DELETE /settings/{key} |
patron.manage (librarian-tier) / system.manage (system-tier) |
| Calendar | GET /library-hours/, PATCH /library-hours/{weekday}; GET/POST /closed-dates/, PATCH/DELETE /closed-dates/{id} |
calendar.manage |
| Audit | GET /audit/ |
audit.view |
The "min permission" column lists the lowest preset role that's allowed. Administrator (wildcard) covers everything. Slimmed Librarian covers librarian-tier endpoints; SystemAdmin covers user/role/system-tier endpoints.
Configuration
Compendium settings come from three layers, in order of precedence:
- Environment variable (
COMPENDIUM_<KEY>) — break-glass override, wins over everything. site_settingtable — DB-backed, editable from/ui/admin/settings/*, the CLI (compendium settings ...), or the API (PATCH /settings/{key}). Changes take effect on the next page render — no restart.- Registry default — fallback hard-coded in
services/settings_registry.py.
Most settings (library name, theme, fine thresholds, hold/overdue defaults, kiosk timeout, SMTP host/port/from, retention) are DB-editable. A handful stay env-only because they're either secrets or required before the DB is reachable:
| Env var | Why env-only |
|---|---|
COMPENDIUM_DATABASE_URL |
Bootstrap — needed before any DB read |
COMPENDIUM_JWT_SECRET_KEY |
Secret — required; server refuses to start with the built-in default. Generate with python -c "import secrets; print(secrets.token_urlsafe(48))". Set COMPENDIUM_ALLOW_INSECURE_JWT=1 to bypass for first-run/dev only. |
COMPENDIUM_JWT_ALGORITHM / COMPENDIUM_JWT_EXPIRE_MINUTES |
Auth deployment knobs |
COMPENDIUM_SSL_CERTFILE / COMPENDIUM_SSL_KEYFILE |
OS-level paths |
COMPENDIUM_SECURE_COOKIES |
Default true; set false only for plain-HTTP LAN deployments (browsers won't send Secure cookies over non-HTTPS, except localhost). |
COMPENDIUM_SECRET_KEY |
Encryption key for secrets stored in the DB (SMTP password, API keys). Optional — set to enable the /ui/admin/system/secrets page. Generate with compendium keygen --secret. |
COMPENDIUM_TMDB_API_KEY |
TMDb API key. Override — also settable via Admin → System → Secrets when COMPENDIUM_SECRET_KEY is configured. |
COMPENDIUM_GOOGLE_BOOKS_API_KEY |
Google Books API key (primary book metadata source when set). Override — also settable via Admin → System → Secrets when COMPENDIUM_SECRET_KEY is configured. |
COMPENDIUM_BOOK_METADATA_SOURCE_PREFERENCE |
Primary book metadata source: googlebooks (default; uses GB when key is set, else OL) or openlibrary. DB-editable at Admin → System → Metadata Sources. |
COMPENDIUM_BOOK_METADATA_FALLBACK_ENABLED |
When true (default), a miss from the primary book adapter automatically tries the secondary (GB→OL and OL→GB symmetric). Set false to disable. DB-editable at Admin → System → Metadata Sources. |
COMPENDIUM_METADATA_CACHE_TTL_DAYS |
Positive-hit TTL for the metadata cache in days (default 30). Negative (not-found) entries always expire after 24 hours. DB-editable at Admin → System → Metadata Sources. |
COMPENDIUM_SMTP_PASSWORD |
SMTP password. Override — also settable via Admin → System → Secrets when COMPENDIUM_SECRET_KEY is configured. |
COMPENDIUM_MAX_UPLOAD_BYTES |
Hard cap on bulk-import upload size (default 100 MB / 104857600). Env-only so a compromised admin token can't raise it. |
COMPENDIUM_LOGIN_MAX_FAILURES |
Max consecutive failed logins before the identity is throttled (default 10). DB-editable at System → Security. |
COMPENDIUM_LOGIN_FAILURE_WINDOW_SECONDS |
Sliding window for counting failures in seconds (default 300 = 5 min). DB-editable at System → Security. |
COMPENDIUM_PUBLIC_BASE_URL |
External HTTPS origin used to build QR codes for phone pairing (e.g. https://library.example.org). The QR base URL is normally derived from the request, honoring X-Forwarded-Proto — the bundled nginx sets this header, so the shipped Docker stack works without this setting. Set it when your proxy does not set that header, or to pin a specific hostname. A non-HTTPS value is refused at QR-render time. DB-editable at Admin → Settings → General; env wins. |
COMPENDIUM_SCAN_SESSION_MINUTES |
How long a paired phone session stays active in minutes (default 60). DB-editable at Admin → Settings → General; env wins. |
COMPENDIUM_TRASH_RETENTION_DAYS |
Days a deleted work stays restorable in the trash before compendium maintenance purge-trash removes it permanently (default 90; 0 disables time-based purging — manual purge only). DB-editable at Admin → Settings → General (compendium settings set trash_retention_days / PATCH /settings/trash_retention_days); env wins. |
For everything else, run compendium settings list to see the current value, source (env vs db/default), and per-key help text. The web admin UI shows the same with an "⚠ Overridden by env var" indicator on rows where an env var is currently masking the DB value.
See docs/deployment.md for full deployment guidance, or docker/README.md for the bundled Docker Compose setup (app + Postgres + nginx with auto-generated self-signed TLS).
Docker quick start
A pre-built multi-arch image (linux/amd64 + linux/arm64) is published to
GitHub Container Registry on every release:
cd docker
cp .env.example .env && $EDITOR .env # set passwords and JWT secret
docker compose pull
docker compose up -d
Image: ghcr.io/statyk/compendium — tags latest, X.Y.Z, X.Y are
published for each release. Pin a version in .env with
COMPENDIUM_IMAGE=ghcr.io/statyk/compendium:1.0.2.
PostgreSQL
SQLite is the default and fine for home or classroom use (up to ~10k items). For larger collections or multiple concurrent writers, use PostgreSQL:
uv sync --extra postgres
Then set:
COMPENDIUM_DATABASE_URL=postgresql+psycopg://compendium:<password>@localhost:5432/compendium
and run compendium db init to apply migrations. Full setup (creating the role and database, TLS, backups) is in docs/deployment.md.
Scheduled maintenance
Several maintenance commands need to run on a cadence — most importantly the
email outbox drain (send-queued-notifications), without which queued
notifications never go out. Install the bundled crontab via:
scripts/install-cron.sh
By default this writes the project path into the crontab and points logs at
$HOME/.local/state/compendium/maintenance.log. Override either with flags:
scripts/install-cron.sh --project-dir /opt/compendium --log-file journal
scripts/install-cron.sh --log-file /var/log/compendium/maintenance.log
--log-file journal routes output to the systemd journal (view with
journalctl -t compendium-maintenance -f). For paths the installer can't
create unprivileged (e.g. /var/log/...), it prints the one-time sudo
command and exits without touching the crontab.
See docs/crontab.sample for the full schedule and
docs/compendium.service.sample for
running the daemon under systemd.
Running tests
uv run pytest -q
Tests are split into tests/unit/ (no DB, mock repos) and tests/integration/ (SQLite in-memory).
Browser tests (E2E)
Browser tests run against a real compendium serve subprocess in Chromium. They are excluded from the default pytest run and require a one-time install:
uv sync --extra e2e
playwright install chromium
Then:
uv run pytest -m e2e
Expected wall time: 30–60 seconds. Tests live in tests/e2e/. The test_csp_no_console_errors.py test is the keystone: it navigates to every major page and asserts no console errors, which catches CSP/HTMX loading regressions that unit tests miss.
Layout
src/compendium/
├── domain/ # models, enums, permissions, errors
├── repositories/ # base protocols + SQLAlchemy implementations
├── services/ # business logic (catalog, circulation, holds, patrons, policies, auth, audit)
├── api/ # FastAPI routes + Pydantic schemas + JWT auth
├── web/ # HTMX + Jinja2 web UI + CSRF protection
├── cli/ # Typer CLI commands
├── config/ # settings, seed data
└── db/ # engine factory, session lifecycle
Changelog
Release-by-release changes are recorded in CHANGELOG.md.
License
MIT (to be finalised before first release).
Metadata
Release files for compendium-ils 1.6.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| compendium_ils-1.6.0.tar.gz | 1.4 MB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| compendium_ils-1.6.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 2.5 MB
Release files / compendium_ils-1.6.0.tar.gz
| Download URL | compendium_ils-1.6.0.tar.gz |
|---|---|
| Size | 1.4 MB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
54b668c09532c4520de70f58e72a447d9823b64b1fc9299138b5a9dd9b7a5e50
|
|
BLAKE2b-256 checksum How to use checksums |
848cffd9cb1474d9981c3e7ef16993ebd52c54aa951c8a5909a68c7233f48bd9
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/6.1.0 CPython/3.13.12
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Jul 16, 2026.
Transparency logRelease files / compendium_ils-1.6.0-py3-none-any.whl
| Download URL | compendium_ils-1.6.0-py3-none-any.whl |
|---|---|
| Size | 1.1 MB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
cde0ace496423135c5bb1aaf684e7829934b935650486a9060f19121179fe92b
|
|
BLAKE2b-256 checksum How to use checksums |
143ed829153a8a5e7ff0ae5103a71492e2989a8a657db9c5d70ce330a4efc731
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/6.1.0 CPython/3.13.12
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Jul 16, 2026.
Transparency log