New releases
Recipe version compared with the latest known upstream release. A version number, not a reading of what changed.
Stirling PDF combines editing, conversion, OCR, compression, signing, and automated PDF processing in one web interface. This recipe makes authentication mandatory, uses local H2, and binds to localhost, so documents never need to reach a cloud service.
Stirling PDF is a web suite of more than 60 PDF operations: merging and splitting, editing, OCR, office-format conversion, compression, signing, metadata editing, and automation pipelines. It suits personal or small internal document workflows that would otherwise send files to Adobe Acrobat Online, Smallpdf, or iLovePDF. An official desktop client can connect to a self-hosted server.
The recipe runs the pinned 2.14.3 standard image with mandatory authentication
and embedded H2, and the interface defaults to English — one variable switches
it. Settings, users, and H2 persist in /configs; branding lives under /customFiles, automation under /pipeline,
and OCR data under /usr/share/tessdata. External PostgreSQL is omitted because
upstream classifies custom databases as paid Server/Enterprise functionality.
The full application smoke test has passed on amd64; backup and restore remain untested in practice. Authentication is enabled, while URL-to-PDF, analytics, PostHog, Scarf, and search-engine indexing are disabled. Complex PDF and office files remain untrusted input that can attack parsers or exhaust resources.
Stirling PDF is open-core, not wholly MIT. The standard image contains parts under the Stirling PDF User License, which restricts production, commercial, and client-facing use without a subscription. Upstream also advertises a Free tier for up to five users; because the interaction is unclear, obtain written confirmation of applicable rights before production use.
These are stored results of separate checks, not real-time data. An unknown status means the check has not been performed yet.
Recipe version compared with the latest known upstream release. A version number, not a reading of what changed.
Result of a dedicated Docker image scan, not a Compose configuration check.
A new major version is found by comparing version numbers. A compatibility verdict is entered by hand after reading the release notes and the migration steps.
Upstream Compose changes relative to the verified recipe.
Pinned image tags checked for newer versions.
From observation to action
The recipe already pins the latest known release. The steps below show the evidence retained for that version.
2.14.32.14.3Open this release on GitHub ↗ The link is evidence to review, not proof of compatibility.
The version numbers do not cross a major compatibility boundary. No compatibility verdict has been recorded.
No image-tag change is currently planned.
Manual steps after the pull. Release-specific migration steps still come from the release notes and installation guide.
No version change is currently planned. The recipe includes a backup procedure. Restore has not been tested.
An exact Fully verified check for this target was recorded on 2026-09-03.
The status shows how fully the published recipe meets each level's requirements.
A minimal setup for a local network or access through a VPN.
You still need to add: single server, local access, minimum components.
A public deployment with protected access and backups.
You still need to add: domain, https via reverse proxy, off-server backup.
A setup designed for predictable operations and observability.
You still need to add: separate database, external monitoring, cpu and memory limits.
Tailored to your server
Answer five questions and download a ready-to-run Stirling PDF bundle.
Screenshots have not been added yet.
Read the full guide first: it explains external access, backups, and data locations.
cp .env.example .envdocker compose up -ddocker compose psUse Ubuntu 22.04+ or Debian 12+ with Docker Engine and Compose v2.24+. Allocate at least 2 CPUs, 2 GB RAM, and 10 GB disk; 4 GB RAM is recommended. OCR, LibreOffice, and large PDFs can briefly consume more CPU, RAM, and temporary space.
docker --version
docker compose version
mkdir -p ~/services/stirling-pdf
cd ~/services/stirling-pdf
cp .env.example .env
chmod 600 .env
mkdir -p data/{configs,customFiles,pipeline,tessdata}
sed -i "s|^STIRLING_PDF_INITIAL_PASSWORD=.*|STIRLING_PDF_INITIAL_PASSWORD=$(openssl rand -base64 36 | tr -d '\n')|" .env
Before the first start, replace STIRLING_PDF_INITIAL_USERNAME and save the
generated password in a secret manager. Initial-login variables are consumed
only while H2 is created; editing .env later does not reset the password. This
recipe never uses the upstream admin/stirling default.
Every .env variable:
STIRLING_PDF_PORT is the local web port, normally 8080;STIRLING_PDF_URL is the exact public origin with a scheme, no trailing /, and no path; it becomes the frontend URL, backend URL, and sole CORS origin;STIRLING_PDF_DATA_PATH is the root of four bind-mounted directories;STIRLING_PDF_INITIAL_USERNAME and STIRLING_PDF_INITIAL_PASSWORD are required non-default first-administrator credentials;STIRLING_PDF_DEFAULT_LOCALE is the UI locale, default en-GB; ru-RU and the other supported locales work too;STIRLING_PDF_UPLOAD_LIMIT_MB is a defensive file and request limit from 1 to 999 MB;STIRLING_PDF_BACKUP_DIR selects the host archive directory.configs holds settings, users, and the
stirling-pdf-DB-<schema-version>.mv.db H2 file; customFiles holds branding
and signatures; pipeline holds automations and watched folders; tessdata
holds OCR languages. Read logs with docker compose logs: persistent /logs
is not needed for recovery and is deliberately omitted.
docker compose config
docker compose pull
docker compose up -d --wait
curl --fail http://127.0.0.1:8080/api/v1/info/status
Open STIRLING_PDF_URL, sign in with the initial credentials, and immediately
change the password in account settings. Authentication is enabled. Analytics,
PostHog, Scarf, Google visibility, and URL-to-PDF are disabled; the health
endpoint remains reachable without login. Do not expose the service until login
has been verified.
Keep 127.0.0.1:${STIRLING_PDF_PORT}:8080, allow only SSH, HTTP, and HTTPS in
the firewall, and expose the app through a proxy on the same host. Set the real
HTTPS origin in STIRLING_PDF_URL, DNS, and proxy before first startup. H2 fits
this free single-container recipe; do not add external PostgreSQL as an
“improvement” without an applicable paid licence.
Prefer a VPN or ssh -L 8080:127.0.0.1:8080 user@server; temporarily set
STIRLING_PDF_URL=http://localhost:8080 for that tunnel. For permanent LAN
access, replace only 127.0.0.1 in Compose with a specific private address, set
the matching origin, and restrict the port by firewall. Do not use 0.0.0.0
without filtering.
Set STIRLING_PDF_URL=https://pdf.example.com without a path or trailing slash,
replace the domain in proxy/Caddyfile, proxy/nginx.conf, or
proxy/traefik.yaml, and recreate the container. Caddy obtains a certificate,
Nginx expects Certbot, and Traefik uses the letsencrypt resolver. Preserve
Host, X-Forwarded-Proto, and client addresses, and keep the proxy upload
limit aligned with STIRLING_PDF_UPLOAD_LIMIT_MB. A containerized proxy cannot
reach host localhost; use a reachable host gateway or shared Docker network.
chmod +x backup.sh restore.sh smoke-test.sh
./backup.sh
The script stops Stirling PDF so H2 cannot change while it archives configs,
customFiles, pipeline, and tessdata together, then restarts the container.
The archive contains H2 users and sensitive settings: encrypt it, copy it off
the server, and test restores regularly. Input and temporary PDFs are normally
deleted and are not backed up. Copy any separately allowed pipeline directories
outside STIRLING_PDF_DATA_PATH yourself.
Restore irreversibly replaces all four directories. Put the same 2.14.3
version in Compose, retain the active .env, verify free space, and run:
./restore.sh ./backups/stirling-pdf-YYYYMMDDTHHMMSSZ.tar.gz
docker compose ps
curl --fail http://127.0.0.1:8080/api/v1/info/status
The script saves the replaced state in an emergency archive, restores the
stopped snapshot, and waits for health. The procedure has restore_tested: false; test a copy on another server first and verify login, settings, custom
files, and pipelines.
Back up first and read the new release notes, migration guide, and licence.
Replace only the exact stirlingtools/stirling-pdf:2.14.3 tag with a reviewed
semantic version, never latest, then run:
docker compose pull
docker compose up -d --wait
docker compose logs --tail=200 stirling-pdf
curl --fail http://127.0.0.1:8080/api/v1/info/status
Startup may migrate H2 and create a file with a new schema version. Review major releases, persistent-path changes, and the User License separately.
Never run an old image over already migrated H2. Stop the container, restore the
old exact tag, and restore the complete pre-update archive with restore.sh.
H2 has no supported downgrade: migration rollback means returning synchronized
configs, customFiles, pipeline, and tessdata. Without a backup, preserve
the current state and contact upstream instead of renaming H2 files manually.
docker compose down preserves bind-mounted data. After verifying an external
backup, remove everything irreversibly:
docker compose down
rm -rf ./data ./backups .env
Sources: Docker installation, configuration, production, health, and backup, analytics, modes and licensing, and the 2.14.3 licence.
docker compose ps
docker compose logs --tail=200 stirling-pdf
docker inspect --format '{{json .State.Health}}' "$(docker compose ps -q stirling-pdf)"
curl -v http://127.0.0.1:8080/api/v1/info/status
The endpoint must return JSON with status: UP. First startup is slower while
H2 and tools are prepared. Verify 2 GB RAM, free disk space, port 8080, and
permissions on all four data directories.
SECURITY_INITIALLOGIN_* applies only while the first database is created. If
configs already contains stirling-pdf-DB-*.mv.db, editing .env does not
change that user. Do not delete H2 with settings and users: restore a known
backup or use an upstream-supported reset procedure. Ensure .env has no
CHANGE_ME and inspect interpolation with docker compose config.
STIRLING_PDF_URL must exactly match the browser origin: scheme, domain, and
optional port, with no path or trailing /. Run
docker compose up -d --force-recreate after changing it. Verify proxy Host
and X-Forwarded-Proto. This recipe supports root /, not a subpath.
Align STIRLING_PDF_UPLOAD_LIMIT_MB with Nginx client_max_body_size or Caddy
request_body max_size. Check temporary space and RAM: processing can need
several times the source file size. Do not remove limits from a public service
without resource controls.
Inspect data/tessdata and logs. Every image variant may not bundle the required
traineddata; add only an official Tesseract tessdata file to the mounted
directory. Do not switch away from the standard image without rechecking
features and architecture support.
Do not run an old image over a new schema or rename
stirling-pdf-DB-<schema-version>.mv.db. Preserve the failed configs, restore
the old tag and complete pre-update archive through restore.sh. Without a
backup, stop the container and request upstream migration guidance.
On the host, run curl http://127.0.0.1:8080/api/v1/info/status, then inspect
the upstream, timeouts, and proxy network namespace. Inside a container,
127.0.0.1 refers to that proxy, not Stirling PDF on the host.
Fossary is an independent informational catalog and is not affiliated with the developers of the listed applications. We collect information from public sources and verify published recipes, but we do not develop, distribute, or control these applications.
A listing or validation status is not a requirement, endorsement, or personal recommendation to use an application. You decide whether it is suitable and use it at your own risk. We do not warrant an application's security, availability, or fitness for purpose and, to the extent permitted by law, are not liable for resulting loss or damage. Review its license, security settings, data processing, and backup procedures before installation.