Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
21 commits
Select commit Hold shift + click to select a range
4079aac
docs: note custom platform icons only apply to the classic UI
gantoine Sep 26, 2026
7b04219
docs: remove the custom platform icon guide
gantoine Sep 26, 2026
bc8059f
Merge pull request #150 from rommapp/docs/custom-icons-new-ui
gantoine Sep 26, 2026
967e263
docs(install): state the minimum MariaDB and MySQL versions
gantoine Sep 26, 2026
fed398a
Merge pull request #151 from rommapp/docs/db-minimum-versions
gantoine Sep 26, 2026
efbf8ba
docs: replace httpx references with httpx2
sdornan Sep 27, 2026
570273c
chore: vendor the humanizer skill
claude Sep 27, 2026
39331f8
chore: add a humanize-docs skill that runs humanizer over changed pages
claude Sep 27, 2026
c5bbf4a
Merge pull request #152 from rommapp/claude/httpx-to-httpx2-txupif
gantoine Sep 27, 2026
4ac781e
Merge pull request #153 from rommapp/claude/language-skills-humanizer…
gantoine Sep 27, 2026
1fbad13
docs(streaming): document the RetroArch core override
LoneAngelFayt Sep 27, 2026
eab8053
docs(streaming): humanize the RetroArch core override prose
LoneAngelFayt Sep 27, 2026
0136284
docs: humanize prose across all pages
gantoine Sep 28, 2026
5f9d93a
docs: fix content bugs found during the humanize pass
gantoine Sep 28, 2026
34a20ff
Merge pull request #156 from rommapp/docs/humanize-all
gantoine Sep 28, 2026
9d959ad
docs: SEVEN_ZIP_TIMEOUT defaults to 180 seconds
gantoine Sep 28, 2026
5256c04
Merge remote-tracking branch 'origin/main' into pr155
gantoine Sep 28, 2026
e79bd63
Merge pull request #155 from LoneAngelFayt/docs/retroarch-core-override
gantoine Sep 28, 2026
7e9b95d
Merge pull request #154 from rommapp/docs/seven-zip-timeout-scaling
gantoine Sep 28, 2026
6ef62c0
Merge remote-tracking branch 'origin/claude/new-session-iabs8x' into …
sdornan Sep 28, 2026
30ebde4
docs: catch the device sync page up with recent sync changes
sdornan Sep 28, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
58 changes: 58 additions & 0 deletions .claude/skills/humanize-docs/SKILL.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
---
name: humanize-docs
description: Run the vendored humanizer over the documentation pages a change adds or edits, as the last step before opening a PR. Rewrites prose only, leaving headings, front matter, snippet partials and MkDocs syntax untouched.
argument-hint: "[page paths | nothing for the pages changed since main]"
disable-model-invocation: true
---

# Humanize changed docs pages

Apply `.claude/skills/humanizer/SKILL.md` to the prose a change adds, then prove
the site still builds. Read that file and follow it rather than invoking the
skill, since a personal install of the same name would load instead.

## Target

`$ARGUMENTS` is a list of page paths, or nothing. With nothing, the target is
every page under `docs/` that differs from `main`, committed or not:

```bash
set -eu
git fetch origin main
BASE="$(git merge-base origin/main HEAD)"
git diff --name-only --diff-filter=AM "$BASE" -- 'docs/*.md' \
':(exclude)docs/resources/snippets/**' ':(exclude)docs/Navigation.md'
```

Snippet partials are included into several pages, so a rewrite there changes
pages the diff never shows; leave them out even when passed by name.
`Navigation.md` is the nav tree, not prose.

## Scope

In file mode, rewrite only the paragraphs `git diff "$BASE"` adds or changes on
each page. Untouched paragraphs stay as they are, even when they carry a tell.

Leave these exactly as written:

- Front matter (`title`, `description`, `search`), which feeds the nav and
search index.
- Heading text. Pages link to `#anchors` derived from it, and the docs use
Title Case, so skip the "Decorative headings" pattern.
- MkDocs syntax: `!!!` and `???` admonition lines and their quoted titles,
`===` tab labels, `--8<--` includes, `{ ... }` attribute lists, `/// caption`
blocks, footnote markers and table structure. Prose inside them is in scope.
- UI labels, setting names, env vars, paths and version numbers. They have to
match the app, so a "more natural" wording is wrong.
- Bold on UI labels and on lead-in sentences in lists; "Bold as decoration"
applies only to bold a new paragraph adds for emphasis.

## Finish

1. Run `trunk fmt && trunk check` on the pages you touched.
2. Run `uv run mkdocs build --strict`, which CI runs on every PR; a broken
anchor or include fails it.
3. Commit the rewrite on its own, so it is one `git revert` away.

Report which pages changed and any tell you left in place because it sat in a
protected span.
21 changes: 21 additions & 0 deletions .claude/skills/humanizer/LICENSE
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
MIT License

Copyright (c) 2025 Siqi Chen

Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:

The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
374 changes: 374 additions & 0 deletions .claude/skills/humanizer/SKILL.md

Large diffs are not rendered by default.

5 changes: 5 additions & 0 deletions .claude/skills/humanizer/UPSTREAM
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
Vendored unmodified from https://github.com/blader/humanizer
Commit: 9862685f575c65a8247f90369951df1b3416e3d6 (v3.0.0)

To update, copy SKILL.md and LICENSE from a newer commit, review the diff, and
bump the commit above. Keep docs-specific rules outside this folder.
4 changes: 4 additions & 0 deletions .trunk/trunk.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,10 @@ lint:
- trufflehog@3.88.12
- yamllint@1.35.1
ignore:
# Vendored humanizer skill, kept byte-identical to upstream
- linters: [ALL]
paths:
- .claude/skills/humanizer/**
# Snippet partials are included into other pages via pymdownx.snippets,
# so they intentionally lack a top-level heading and standalone structure.
- linters: [markdownlint]
Expand Down
2 changes: 1 addition & 1 deletion docs/about/brand-guidelines.md
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ The logo should always be used in its standard colors:
- Always use our logo in the colors provided.
- Always use our name in a way that makes clear you are not affiliated with the project.

If you're building something that integrates with RomM and would like to use/remix the logo, **please reach out first** via [Discord](https://discord.gg/romm). We'd love to hear about it.
If you're building something that integrates with RomM and would like to use/remix the logo, please reach out first via [Discord](https://discord.gg/romm). We'd love to hear about it.

## Please don't

Expand Down
6 changes: 3 additions & 3 deletions docs/about/credits.md
Original file line number Diff line number Diff line change
Expand Up @@ -22,15 +22,15 @@ The 19 locales exist because individual community members took the time to trans

## Community apps

Built by the community, not the RomM team. Full list in the [Community section in the RomM README](https://github.com/rommapp/romm/#community).
These apps are built by the community, not the RomM team. The full list is in the [Community section in the RomM README](https://github.com/rommapp/romm/#community).

## Financial supporters

Donors via [Open Collective](https://opencollective.com/romm) make continued development possible. The project wouldn't exist without you. Thank you! ❤️
Donors via [Open Collective](https://opencollective.com/romm) make continued development possible, and the project wouldn't exist without you. Thank you! ❤️

## Upstream projects

This stack stands on an enormous amount of open-source work. In rough order of "how visible they are to users":
This stack depends on a large amount of open-source work. In rough order of "how visible they are to users":

### In-browser emulation

Expand Down
14 changes: 7 additions & 7 deletions docs/about/faqs.md
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ The emphasis here is self-hosted + multi-user + in-browser-play + the companion-

## Do I need metadata API keys?

It runs without any but games won't match against a metadata source, so you won't get covers, descriptions, or ratings.
It runs without any, but games won't match against a metadata source, so you won't get covers, descriptions, or ratings.

## Is RomM legal?

Expand Down Expand Up @@ -83,7 +83,7 @@ See [Folder Structure](../getting-started/folder-structure.md) and [Scanning Tro

## Why is my metadata wrong or incomplete?

Metadata isn't owned, only pulled from third parties like IGDB and ScreenScraper. If a field is missing or wrong, the fix has to happen upstream on the provider's site. Cross-check against another provider if one is consistently off for your library.
RomM doesn't own metadata. It pulls it from third parties like IGDB and ScreenScraper. If a field is missing or wrong, the fix has to happen upstream on the provider's site. Cross-check against another provider if one is consistently off for your library.

## Why am I getting a "Configuration file not Mounted!" error?

Expand Down Expand Up @@ -114,11 +114,11 @@ See [Invitations & Registration](../administration/invitations-and-registration.

## Can guests browse without an account?

Absolutely, just set `KIOSK_MODE=true` in your environment variables and anonymous visitors get read-only access (see [Authentication → Kiosk mode](../administration/authentication.md#kiosk-mode)).
Yes. Set `KIOSK_MODE=true` in your environment variables and anonymous visitors get read-only access (see [Authentication → Kiosk mode](../administration/authentication.md#kiosk-mode)).

## How do I back up?

`mysqldump` the DB + rsync the `/romm/assets` and `/romm/config` volumes nightly. Full procedure and test-restore protocol in [Backup & Restore](../install/backup-and-restore.md).
`mysqldump` the DB + rsync the `/romm/assets` and `/romm/config` volumes nightly. The full procedure and test-restore protocol are in [Backup & Restore](../install/backup-and-restore.md).

## Can I use RomM without the internet?

Expand All @@ -138,7 +138,7 @@ Several possibilities, in rough order of likelihood:
2. Metadata providers rate-limiting (mostly ScreenScraper).
3. Many files on a network mount with high latency.

[Scanning Troubleshooting → Hash calculations are slow](../troubleshooting/scanning.md#hash-calculations-are-slow).
See [Scanning Troubleshooting → Hash calculations are slow](../troubleshooting/scanning.md#hash-calculations-are-slow).

## When will [feature X] be added?

Expand All @@ -156,9 +156,9 @@ For bugs, open an issue at [rommapp/romm](https://github.com/rommapp/romm/issues

## Who runs RomM?

A small team of maintainers plus a chunk of active community contributors. Support the project via [Open Collective](https://opencollective.com/romm) if you'd like!
A small team of maintainers plus a group of active community contributors. Support the project via [Open Collective](https://opencollective.com/romm) if you'd like!

## Where's can I find you?
## Where can I find you?

- **Discord**: [discord.gg/romm](https://discord.gg/romm)
- **GitHub**: [rommapp/romm](https://github.com/rommapp/romm)
Expand Down
6 changes: 3 additions & 3 deletions docs/about/license.md
Original file line number Diff line number Diff line change
Expand Up @@ -25,12 +25,12 @@ The RomM umbrella hosts several projects under different licenses:
| Project | License |
| --------------------------------------------------------------------- | ------- |
| [rommapp/romm](https://github.com/rommapp/romm) | AGPLv3 |
| [rommapp/argosy-launcher](https://github.com/rommapp/argosy-launcher) | AGPLv3 |
| [rommapp/argosy-launcher](https://github.com/rommapp/argosy-launcher) | GPLv3 |
| [rommapp/grout](https://github.com/rommapp/grout) | MIT |
| [rommapp/playnite-plugin](https://github.com/rommapp/playnite-plugin) | AGPLv3 |
| [rommapp/playnite-plugin](https://github.com/rommapp/playnite-plugin) | GPLv3 |
| [rommapp/docs](https://github.com/rommapp/docs) (what you're reading) | CC0 |

Companion repos use more permissive licenses AGPLv3 or MIT because they're smaller, more-replaceable, and don't host the library. The AGPL network-service clause doesn't offer the same protection benefits there.
Companion repos use GPLv3 or MIT because they're smaller, more replaceable, and don't host the library, so AGPL's network-service clause wouldn't add much protection there.

## Third-party components

Expand Down
12 changes: 6 additions & 6 deletions docs/administration/authentication.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ description: Configure how users sign in.

# Authentication

This page is the **operator-side** authentication reference, the knobs you turn on the server to control how people sign in. The **client-side** reference ("how do I actually authenticate an API call?") is in [API Authentication](../developers/api-authentication.md).
This page is the operator-side authentication reference: the settings you change on the server to control how people sign in. The client-side reference ("how do I actually authenticate an API call?") is in [API Authentication](../developers/api-authentication.md).

Authentication flows RomM supports:

Expand Down Expand Up @@ -45,7 +45,7 @@ environment:

### Admin-triggered password reset

Until email-based self-serve reset lands, admins set passwords manually for any user. The next login on that account will use the new password but existing sessions remain valid until they expire.
Until email-based self-serve reset lands, admins set passwords manually for any user. The next login on that account will use the new password, but existing sessions remain valid until they expire.

## OIDC

Expand All @@ -65,18 +65,18 @@ When OIDC is configured, an OIDC sign-in option is offered alongside username/pa

## Client API Tokens

For anything long-lived (a companion app, a cron job, a script) use **Client API Tokens** instead of storing a password. Each token:
For anything long-lived (a companion app, a cron job, a script) use Client API Tokens instead of storing a password. Each token:

- Belongs to a specific user
- Carries a **subset** of that user's scopes (you choose which at creation time)
- Carries a subset of that user's scopes (you choose which at creation time)
- Has an optional expiry (no expiry = never expires until manually revoked)
- Can be "paired" to a device via a short code

Each user gets up to 25 active tokens. The API side ("how do I send this thing in a request?") lives in [API Authentication](../developers/api-authentication.md).

## Kiosk mode

Grants unauthenticated, read-only access to nearly every GET endpoint. Anyone reaching the instance can browse but only a logged-in admin can write, scan, upload, or manage users.
Kiosk mode grants unauthenticated, read-only access to nearly every GET endpoint. Anyone reaching the instance can browse, but only a logged-in admin can write, scan, upload, or manage users.

```yaml
environment:
Expand All @@ -98,7 +98,7 @@ environment:
- DISABLE_DOWNLOAD_ENDPOINT_AUTH=true
```

Skips auth on `GET /api/roms/{id}/content/…` and the firmware download endpoint. Exists so third-party apps that can't carry a bearer header (like dumb emulators loading a ROM by URL) can still pull files. **Only enable this when the public internet can't reach RomM directly**, i.e. there's auth or an IP allowlist at the reverse-proxy layer. Otherwise you've just made your library world-downloadable.
Skips auth on `GET /api/roms/{id}/content/…` and the firmware download endpoint. It exists so third-party apps that can't carry a bearer header (like dumb emulators loading a ROM by URL) can still pull files. **Only enable this when the public internet can't reach RomM directly**, i.e. there's auth or an IP allowlist at the reverse-proxy layer. Otherwise you've just made your library world-downloadable.

## Revoking access

Expand Down
8 changes: 4 additions & 4 deletions docs/administration/firmware-management.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ description: Upload, associate, and serve BIOS/firmware files for emulation.

# Firmware Management

Many emulated platforms require BIOS or firmware to boot, or to reach a certain level of stability. RomM tracks firmware files **per platform**, stores them on disk, and serves them to in-browser players (EmulatorJS/Ruffle) and companion apps that request them.
Many emulated platforms require BIOS or firmware to boot, or to reach a certain level of stability. RomM tracks firmware files per platform, stores them on disk, and serves them to in-browser players (EmulatorJS/Ruffle) and companion apps that request them.

Firmware is **not** ROM. Keep the two separate:

Expand All @@ -14,7 +14,7 @@ Firmware is **not** ROM. Keep the two separate:

<!-- prettier-ignore -->
!!! important "Legality varies by jurisdiction"
RomM does not ship games or firmware, and the team cannot help you obtain BIOS files. Always check your local laws and the emulator's documentation for guidance on what you can legally use.
RomM does not ship games or firmware, and the team cannot help you obtain BIOS files. Always check your local laws and the emulator's documentation for guidance on what you can legally use.

## Ingesting firmware

Expand All @@ -26,7 +26,7 @@ Where `bios/` lives is up to you. The default is `bios/{platform}` at the librar

## Missing firmware

Delete a file from `bios/` and the next scan **flags it missing** instead of dropping it from the database. Put the file back and the next scan clears the flag. If you're never replacing it, the **Cleanup missing firmware** task deletes every flagged row in one go (see [Scheduled Tasks](scheduled-tasks.md#triggering-a-task-manually)).
Delete a file from `bios/` and the next scan flags it missing instead of dropping it from the database. Put the file back and the next scan clears the flag. If you're never replacing it, the **Cleanup missing firmware** task deletes every flagged row in one go (see [Scheduled Tasks](scheduled-tasks.md#triggering-a-task-manually)).

## Platform-specific firmware

Expand All @@ -42,7 +42,7 @@ Common examples:
| Saturn | `saturn_bios.bin`, `mpr-17933.bin` | `bios/saturn/` |
| Nintendo DS | `firmware.bin`, `bios9.bin`, `bios7.bin` | `bios/nds/` |

File naming matters as emulators look for specific filenames. Double-check against the emulator core's documentation if something won't boot.
File naming matters because emulators look for specific filenames. Double-check against the emulator core's documentation if something won't boot.

## Integration with companion apps

Expand Down
2 changes: 1 addition & 1 deletion docs/administration/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ description: Running RomM for yourself and others.

# Administration

Administration is everything you do **as the server owner** of a RomM instance: managing accounts, controlling access, configuring metadata sources, scheduling scans, watching the library for changes, monitoring the server, and keeping data safe.
Administration is everything you do as the server owner of a RomM instance: managing accounts, controlling access, configuring metadata sources, scheduling scans, watching the library for changes, monitoring the server, and keeping data safe.

The end-user equivalent (how to actually play the games, build collections, upload saves) lives in [Using RomM](../using/index.md).

Expand Down
8 changes: 4 additions & 4 deletions docs/administration/invitations-and-registration.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ There are three ways a new account ends up on a RomM instance:

## First-admin setup

When a fresh RomM container starts against an empty database, hitting any page redirects to the **Setup Wizard**. The wizard collects a username, email, and password. The resulting account is **always an Admin**, regardless of any env var.
When a fresh RomM container starts against an empty database, hitting any page redirects to the **Setup Wizard**. The wizard collects a username, email, and password. The resulting account is always an Admin, regardless of any env var.

To skip the wizard (e.g. when provisioning via automation and you'll create users through the API), set:

Expand All @@ -26,14 +26,14 @@ You'll then need to create the first admin via the API or by injecting a databas

## Invite links

The recommended way to add users, because it avoids you ever touching their password.
Invite links are the recommended way to add users, because you never have to touch their password.

1. **Administration → Users → Invite.** Pick a role (User or Admin).
2. RomM generates a single-use URL → copy it and send it to the invitee.
2. RomM generates a single-use URL. Copy it and send it to the invitee.
3. When they open it, they pick their own username and password.
4. RomM creates the account with the role you chose and logs them straight in.

Invite tokens are **single-use** and **time-limited**. Defaults:
Invite tokens are single-use and time-limited. Defaults:

| Setting | Default | Env var |
| ------- | ---------- | ----------------------------- |
Expand Down
Loading
Loading