jdownloader
Download manager with a web UI via the jlesage/jdownloader-2 OCI image.
The service runs as a Podman container. The blueprint provides the image reference (digest-pinned
per ADR-0005) and a set of environment variable defaults for timezone and
display resolution. No volumes are declared in the blueprint — the consumer must mount at least
/output (download destination) and /config (persistent application state) for the container to
function correctly.
| Attribute | Value |
|---|---|
| Runtime | OCI (Podman) |
| Port | 5800 |
| Idle timeout | 43200 s (12 h) |
| OCI image | jlesage/jdownloader-2 |
Blueprint environment defaults:
| Variable | Default |
|---|---|
TZ | Europe/Berlin |
DISPLAY_WIDTH | 1280 |
DISPLAY_HEIGHT | 768 |
Consumer must provide: volume mounts for /output and /config. Without these mounts,
downloaded files and application configuration are lost on container restart.
Current Recommended Pin
The blueprint pins recommended.main to the following digest-pinned image reference (verified
against merlin production 2026-05-17):
v26.02.3@sha256:c4e1c8b8b9b22b9c39ac7c0499ab712f14ed1b897ffc5c910284dc7a59035e4a
The digest closes the upstream tag-re-push channel: a registry that re-pushes v26.02.3 cannot
silently swap image content for this service. Podman pulls by digest and ignores the human-readable
tag for content resolution. See the
Drift Diagnostics section of the OCI runtime reference for
the rule set the versions module enforces.
Usage
The canonical consumer pattern calls mk {} to inherit the recommended pin, then merges
host-specific identity and volumes via lib.recursiveUpdate:
nixda.zones.private.services.jdownloader = lib.recursiveUpdate
((blueprint "jdownloader").mk {})
{
id = 20;
runtime.oci.volumes = [
"/mnt/storage/downloads:/output"
"/var/lib/jdownloader/config:/config"
];
};
Calling mk {} (no versions argument) inherits the blueprint’s recommended pin and emits one
drift warning per evaluation acknowledging the inheritance. To suppress the warning, supply the
recommended pin explicitly:
nixda.zones.private.services.jdownloader = lib.recursiveUpdate
((blueprint "jdownloader").mk {
versions = (blueprint "jdownloader").recommended;
})
{
id = 20;
runtime.oci.volumes = [
"/mnt/storage/downloads:/output"
"/var/lib/jdownloader/config:/config"
];
};
To override the timezone:
nixda.zones.private.services.jdownloader = lib.recursiveUpdate
((blueprint "jdownloader").mk {})
{
id = 20;
runtime.oci = {
environment.TZ = "America/New_York";
volumes = [
"/mnt/storage/downloads:/output"
"/var/lib/jdownloader/config:/config"
];
};
};
Pinning to a Different Tag
A consumer who needs a different upstream tag must supply the full digest-pinned form per
ADR-0005. Tag-only strings (e.g. "v26.03.0") are rejected at evaluation
time. Look up a tag’s digest with podman manifest inspect jlesage/jdownloader-2:<tag> or
docker manifest inspect:
nixda.zones.private.services.jdownloader = lib.recursiveUpdate
((blueprint "jdownloader").mk {
versions = {
main = "v26.03.1@sha256:<64-lowercase-hex-chars>";
};
})
{
id = 20;
runtime.oci.volumes = [
"/mnt/storage/downloads:/output"
"/var/lib/jdownloader/config:/config"
];
};