# Koillection: a self-hosted collection manager with no built-in metadata

> Koillection is a self-hosted PHP and Symfony application for cataloguing physical collections of any kind. Its defining choice is that it ships no pre-built metadata download, so you describe your own fields and, if you want automation, write your own scraper.

**benjaminjonard/koillection** — Koillection is a self-hosted service allowing users to manage any kind of collections.

- Repository: https://github.com/benjaminjonard/koillection
- Website: https://github.com/koillection/koillection/wiki
- Stars: 1,324 · Forks: 67
- Language: PHP
- License: MIT
- Published: 2026-09-10 · Updated: 2026-09-10 · Language: en
- Canonical page: https://hysenlabs.com/projects/benjaminjonard-koillection

## What Koillection actually solves, and for whom

Most collection software assumes it knows what you collect. Point it at a barcode or a title and it fetches cover art, publisher, release year and track listing from a central database. Koillection inverts that. The README describes it as a self-hosted collection manager "created to keep track of physical (mostly) collections of any kind like books, DVDs, stamps, games", and then states the trade-off plainly: it "doesn't come with pre-built metadata download".

That single sentence defines the audience. If your collection fits a well-known schema with a public API behind it, Koillection makes you do work that a dedicated tool would do for you. If your collection does not fit any schema (postcards, mineral samples, mechanical keyboards, a shelf of odd hardware), the absence of a fixed model is the point. You decide which fields exist, and the application stores what you tell it to store.

The secondary audience is people who want the catalogue to live on their own hardware. Koillection is PHP, uses Symfony, and lists PostgreSQL, MariaDB and MySQL among its topics and badges, so the deployment shape is a familiar web application plus a database you already run. There is no hosted tier described in the README. The wiki is the documentation surface, and the README itself notes it is "under construction", which is an honest signal about how much you should expect to be written down.

## How the pieces fit: Symfony, API Platform and a database

The repository layout tells you most of the architecture. There is a src/ directory for application code, config/ for Symfony configuration, templates/ for Twig views, migrations/ for Doctrine database migrations, api/ for the API surface, and assets/ for frontend sources built with Yarn. The composer.json and symfony.lock files confirm a Composer-managed PHP application. The topics list api-platform and symfony, so the HTTP API is generated through API Platform rather than hand-written controllers for every endpoint.

The Dockerfile confirms the runtime more precisely than the README does. It builds from dunglas/frankenphp:php8.5, copies the repository into /app/public, installs PHP extensions including opcache, pdo_pgsql, pdo_mysql, intl, gd, zip, apcu and curl, then runs composer install --classmap-authoritative. It also runs php bin/console app:translations:dump, a project-specific console command that exports translations for the JavaScript side. A Caddyfile from docker/Caddyfile is copied to /etc/caddy/Caddyfile, so Caddy serves the application inside the container.

Two details matter for operators. First, the image installs chromium and chromium-driver and sets PANTHER_CHROME_BINARY, PANTHER_CHROME_DRIVER_BINARY and PANTHER_NO_SANDBOX. That is browser automation inside the application image, which is consistent with scraping being a first-class feature rather than an add-on. Second, the base image is pinned to PHP 8.5, so the container path and any manual PHP install have to agree on a version that satisfies the Composer constraints.

## Installing Koillection and adding your first item

The README does not contain install steps. It points to the Installation page in the wiki, and the repository ships a docker-compose.dist.yml at the top level plus a docker/ directory. Because the README does not reproduce the compose file, the exact service names and ports are not stated there, and I will not invent them. What can be said is that Docker is the intended path for most users: the Dockerfile is a production build, and Dockerfile.dev exists for development.

Start by reading the distribution compose file before you run anything, since it is the file that defines your database service and the application port.

```bash
cat docker-compose.dist.yml
```

Reading it first is not filler. The README's warning section is explicit about data risk: "Please back up your database, especially when updating to a new version." Knowing which volume holds your database before the first start is the difference between a recoverable mistake and a lost catalogue.

Once the stack is up, the workflow is: create a collection, define the fields it needs, then add items. Koillection gives you no metadata to accept or reject, so the first item is entirely manual. If you want the application to fetch anything, you configure a scraper yourself. The README points to a Scraping page in the wiki and says you "can tailor your own HTML scraper". The Dockerfile's inclusion of Chromium and ChromeDriver is what makes a scraper able to render pages that require JavaScript.

For a quick look without installing, the README offers a Gitpod instance from the koillection-gitpod repository. It states that Gitpod runs "a new and temporary instance" and that once loading finishes you select More actions, then Open in browser. Temporary is the operative word: nothing you enter there is meant to persist.

## The metadata gap is a design decision, not a missing feature

It is tempting to file "no pre-built metadata download" under limitations and move on. That undersells how much of the product's shape follows from it. A catalogue with automatic lookups needs a canonical schema: title, creator, date, identifier, cover image. Koillection has no such schema, which is why it can handle stamps and games with the same code. The cost is that every field is your decision, and consistency across a large collection becomes a discipline problem rather than a technical one.

Scraping is the escape hatch, and it is a heavier one than a built-in integration. An HTML scraper is coupled to someone else's markup. When a site changes its page structure, the scraper breaks, and nothing in the repository suggests Koillection can detect that for you. The wiki page on scraping is the place to check what a scraper definition looks like before you plan around it.

There is also a practical limit the README implies rather than states: this is a single-maintainer project. The warning section is written in the first person ("I do my best to test new versions"), and the support section asks for bug reports and proofreading of translations. That is a normal shape for self-hosted software, but it means the upgrade path deserves attention. The repository has migrations/, so schema changes ship as Doctrine migrations, and the README's request to back up your database before updating is aimed at exactly that. The last push to the repository was on 2026-09-08, and the most recent release listed is 1.8.4 from 2026-08-23.

## Where Koillection is the wrong tool

If your collection is books and you want ISBN in, cover and blurb out, Koillection adds a configuration project between you and that outcome. Tools built around a specific medium already know the fields and the data sources. Koillection will store the ISBN, but only because you created a field for it.

If you need multi-user access control as a primary concern, the README says nothing about roles, permissions or sharing, so you cannot evaluate that from it alone. Check the wiki before assuming it exists.

If you want zero-maintenance hosting, a self-hosted PHP application with a database, Doctrine migrations and a documented backup warning is the opposite of that. The README's repeated request to back up the database is not boilerplate; it is the maintainer telling you where the failure modes are.

And if your collection is small enough that a spreadsheet works, Koillection's value (custom fields, a web UI, an API, scrapers) does not apply. The setup cost is real and it does not shrink with collection size.

## Alternatives and the actual difference in approach

Homebox is the closest comparison that people search for alongside Koillection, and the difference is philosophical rather than technical. Homebox is built around a location-oriented inventory model: items live in places, and the questions it answers are "what is in this box" and "where did I put this". Koillection is built around collection items and user-defined fields, and the question it answers is "what do I know about this object". If you are cataloguing a stamp collection with condition, catalogue number and acquisition date, the field model matters more than the location model. If you are tracking where the spare cables went, the reverse is true.

A general-purpose database or spreadsheet is the honest alternative for many people. It gives you the same freedom over fields with none of the deployment work, at the cost of a UI, an API and any scraping. Koillection's advantage over a spreadsheet is the structure and the query surface; its disadvantage is that you now run a Symfony application.

The Gitpod demo sits in a different category: it is not an alternative product but an alternative to installing, and the README is clear that instances created there are temporary. Use it to judge the UI, not to hold data.

## Licence, upgrades and what maintenance costs you

Koillection is MIT licensed. In practice that means you can run it, modify it and redistribute it with few conditions, and the main obligation is preserving the licence text and copyright notice. This is not legal advice; read LICENSE in the repository if the distinction matters to your situation.

Upgrade cost is the real operational question. Releases are tagged (1.8.4, 1.8.3, 1.8.2 in the recent list) and the default branch is 1.8, so the project tracks a versioned line rather than a single rolling branch. The Updating page in the wiki is the authoritative procedure, and the README does not reproduce it. What the README does say, twice, is to back up the database. Migrations exist in the repository, which means an upgrade can alter your schema, and a schema change without a dump is the scenario the warning is written for.

On the development side, the repository carries phpunit.xml, .php-cs-fixer.dist.php and rector.php, so there is a test suite and automated style and refactoring tooling. That is a positive signal for contributors and says nothing about whether your particular upgrade will be clean. Pin your image tag rather than tracking a moving tag, read the changelog for the version you are moving to, and keep the dump.

## Conclusion

Adopt Koillection if you want a self-hosted cataloguing tool whose schema you control and you accept that metadata entry and scraping are your responsibility. Do not adopt it if you expect automatic lookups from Discogs, TMDB or similar sources out of the box, or if you want a managed service with backups handled for you. Before committing real data, verify the installation path in the wiki, confirm your database version meets the stated minimums (PostgreSQL >= 10.0, MariaDB >= 10.0, MySQL >= 8.0), and take a database dump before every upgrade, which the README explicitly asks for.

## FAQ

### How do I install Koillection?

The README does not include installation steps; it points to the Installation page in the project wiki. The repository ships a docker-compose.dist.yml and a production Dockerfile, which is the intended deployment path for most users.

### Does Koillection download metadata for my items automatically?

No. The README states that Koillection "doesn't come with pre-built metadata download", so you add metadata yourself or tailor your own HTML scraper. The wiki has a Scraping page describing that workflow.

### Which databases does Koillection support?

The README badges list PostgreSQL >= 10.0, MariaDB >= 10.0 and MySQL >= 8.0. The Dockerfile installs both pdo_pgsql and pdo_mysql PHP extensions, so either engine is supported by the image.

### Can I try Koillection without installing it?

Yes. The README links a Gitpod instance from the koillection-gitpod repository, which it says runs a new and temporary instance. After Gitpod finishes loading, you select More actions and then Open in browser.

### What should I do before updating Koillection to a new version?

Back up your database. The README asks for this explicitly, noting that new versions can contain data migrations where edge cases may escape testing. The Updating page in the wiki has the procedure.

## Sources

- [benjaminjonard/koillection on GitHub](https://github.com/benjaminjonard/koillection)
- [License: MIT](https://github.com/benjaminjonard/koillection/blob/1.8/LICENSE)
- [Project website](https://github.com/koillection/koillection/wiki)
- [README](https://github.com/benjaminjonard/koillection/blob/1.8/README.md)
- [Releases](https://github.com/benjaminjonard/koillection/releases)

---

Hysen Labs editorial analysis, written from the project's own repository and release notes. Cite the canonical page: https://hysenlabs.com/projects/benjaminjonard-koillection
