High performance self-hosted photo and video management solution.
| Registry | ghcr.io/daemonless/immich |
| Source | https://github.com/immich-app/immich |
| Website | https://immich.app/ |
These tags apply to the immich-server image (set via IMMICH_TAG):
| Tag | Description | Best For |
|---|---|---|
latest |
Current stable release, built from the latest upstream Immich release. | Most users. |
beta |
Beta release built from upstream v3.0.0-rc.0. | Testing upcoming releases early. |
Machine learning (immich-ml, set via IMMICH_ML_TAG) follows the same latest and beta tags.
immich-postgres:latest and :14 are both PostgreSQL 14, matching upstream Immich. New installs can use :18; upgrading an existing database needs a full dump and restore.
Before deploying, ensure your host environment is ready. See the Quick Start Guide for host setup instructions.
1. Save as .env and fill in what is empty:
# Immich for FreeBSD (Daemonless) # Compatible with official Immich environment variables # Docs: https://docs.immich.app/install/environment-variables # Image tag for the Immich server and machine-learning containers. # Defaults to 'latest' (stable). Set to 'beta' to run the Immich 3.0 pre-release. # IMMICH_TAG=latest # Image tag for machine learning (defaults to 'latest'). # The location where your uploaded files are stored UPLOAD_LOCATION=/containers/immich/library # The location where your database files are stored DB_DATA_LOCATION=/containers/immich/postgres # To set a timezone, uncomment the next line and change Etc/UTC to a TZ identifier # https://en.wikipedia.org/wiki/List_of_tz_database_time_zones#List # TZ=Etc/UTC # Connection secret for postgres. Change this to a random password! # Use only characters A-Za-z0-9 (no special characters or spaces) DB_PASSWORD=postgres # Where the server looks for the other three services. The defaults are right # when they all share one network stack, which is what this file sets up. Set # them when postgres, redis and the ML service are somewhere else -- on their # own private segment, or a redis you already run. # DB_HOSTNAME=localhost # REDIS_HOSTNAME=localhost # IMMICH_ML_HOST=localhost # Machine learning: false turns it off (the Machine learning choice does this). # IMMICH_ML_ENABLED=true # Public sharing (the Public sharing choice): the address the proxy is reached at. # PUBLIC_BASE_URL= # The address the server binds. Immich binds loopback unless told otherwise, # which answers nothing if the container has an address of its own. # IMMICH_HOST=0.0.0.0 # The values below this line do not need to be changed ################################################################################### DB_USERNAME=postgres DB_DATABASE_NAME=immich
2. Save as compose.yaml:
# # Immich for FreeBSD (Daemonless) # # Drop-in compatible with official Immich docker-compose.yml # # Prerequisites: # pkg install podman-suite py311-podman-compose # # Usage: # 1. Copy example.env to .env and edit # 2. Run: podman-compose up -d # name: immich services: immich-server: container_name: immich_server image: ghcr.io/daemonless/immich-server:${IMMICH_TAG:-latest} network_mode: host volumes: - ${UPLOAD_LOCATION}:/data - /etc/localtime:/etc/localtime:ro environment: DB_HOSTNAME: ${DB_HOSTNAME:-localhost} REDIS_HOSTNAME: ${REDIS_HOSTNAME:-localhost} IMMICH_MACHINE_LEARNING_URL: http://${IMMICH_ML_HOST:-localhost}:3003 IMMICH_MACHINE_LEARNING_ENABLED: ${IMMICH_ML_ENABLED:-true} # Immich binds loopback unless told otherwise, so it answers nothing on # the host's address -- or on a published port, which forwards to the # container's own and not to its loopback. IMMICH_HOST: ${IMMICH_HOST:-0.0.0.0} env_file: - .env depends_on: - redis - database - immich-machine-learning restart: always immich-machine-learning: container_name: immich_machine_learning image: ghcr.io/daemonless/immich-ml:${IMMICH_ML_TAG:-latest} network_mode: host environment: HF_HOME: /cache/huggingface MPLCONFIGDIR: /tmp volumes: - model-cache:/cache env_file: - .env restart: always # Public links to albums for people with no account. Only with the Public # sharing choice; it reaches the server over localhost and answers on 3000. immich-public-proxy: container_name: immich_public_proxy image: ghcr.io/daemonless/immich-public-proxy:latest network_mode: host profiles: [proxy] environment: IMMICH_URL: http://localhost:2283 PUBLIC_BASE_URL: ${PUBLIC_BASE_URL:-} IPP_PORT: "3000" env_file: - .env depends_on: - immich-server restart: always redis: container_name: immich_redis image: ghcr.io/daemonless/redis:latest network_mode: host volumes: - /etc/localtime:/etc/localtime:ro - redis-data:/config restart: always database: container_name: immich_postgres image: ghcr.io/daemonless/immich-postgres:latest network_mode: host # FreeBSD requires sysvipc for PostgreSQL shared memory annotations: org.freebsd.jail.allow.sysvipc: "true" environment: POSTGRES_PASSWORD: ${DB_PASSWORD} POSTGRES_USER: ${DB_USERNAME} POSTGRES_DB: ${DB_DATABASE_NAME} volumes: - /etc/localtime:/etc/localtime:ro - ${DB_DATA_LOCATION}:/var/lib/postgresql/data restart: always volumes: model-cache: redis-data:
Then run podman-compose up -d.
.env:
# .env
DIRECTOR_PROJECT=immich
DB_HOSTNAME=localhost
REDIS_HOSTNAME=localhost
IMMICH_MACHINE_LEARNING_URL=http://${IMMICH_ML_HOST:-localhost}:3003
IMMICH_MACHINE_LEARNING_ENABLED=true
IMMICH_HOST=0.0.0.0
UPLOAD_LOCATION=/containers/immich/library
DB_DATA_LOCATION=/containers/immich/postgres
DB_PASSWORD=postgres
DB_USERNAME=postgres
DB_DATABASE_NAME=immich
IMMICH_ML_TAG=
IMMICH_ML_ENABLED=
PUBLIC_BASE_URL=
TZ=
appjail-director.yml:
# appjail-director.yml options: - alias: - ip4_inherit: services: immich: name: immich options: - container: 'args:--pull' oci: user: root environment: - DB_HOSTNAME: !ENV '${DB_HOSTNAME}' - REDIS_HOSTNAME: !ENV '${REDIS_HOSTNAME}' - IMMICH_MACHINE_LEARNING_URL: !ENV '${IMMICH_MACHINE_LEARNING_URL}' - IMMICH_MACHINE_LEARNING_ENABLED: !ENV '${IMMICH_MACHINE_LEARNING_ENABLED}' - IMMICH_HOST: !ENV '${IMMICH_HOST}' - UPLOAD_LOCATION: !ENV '${UPLOAD_LOCATION}' - DB_DATA_LOCATION: !ENV '${DB_DATA_LOCATION}' - DB_PASSWORD: !ENV '${DB_PASSWORD}' - DB_USERNAME: !ENV '${DB_USERNAME}' - DB_DATABASE_NAME: !ENV '${DB_DATABASE_NAME}' - IMMICH_ML_TAG: !ENV '${IMMICH_ML_TAG}' - IMMICH_ML_ENABLED: !ENV '${IMMICH_ML_ENABLED}' - PUBLIC_BASE_URL: !ENV '${PUBLIC_BASE_URL}' - TZ: !ENV '${TZ}' volumes: - immich_data: /data - etc_localtime: /etc/localtime database: name: database options: - from: - template: !ENV '${PWD}/immich-postgres-template.conf' volumes: immich_data: device: '/containers/immich/data' etc_localtime: device: '/etc/localtime'
Makejail:
# Makejail
ARG tag=latest
OPTION container=boot
OPTION overwrite=force
OPTION from=ghcr.io/daemonless/immich:${tag}
Save the files above, then run appjail-director up.
PostgreSQL shared memory. PostgreSQL wants System V IPC, which a jail does not get by default. The compose carries the annotation (org.freebsd.jail.allow.sysvipc: "true", read by ocijail) and the director bundle ships immich-postgres-template.conf for the same reason.
Machine learning. immich-ml runs a FreeBSD-native onnxruntime on the CPU; there is no GPU acceleration on FreeBSD. Models (about 1 GB) download on first use into /cache, so the first start is slow and the rest are not.
Network. The stack shares the host's network stack, so the services find each other over localhost and only 2283 needs to reach the outside. Put the parts on networks of their own and the *_HOSTNAME variables name where each one went; fjord does that for you.
Managing it. podman-compose logs -f for every service, podman logs -f immich_server for one; podman-compose restart, podman-compose down, and podman-compose pull && podman-compose up -d to update.
??? question "ML service keeps restarting"
Check memory - the ML service needs at least 2GB RAM:
bash podman logs immich_machine_learning
If you see OOM errors, give it more memory or turn the Machine learning choice off.
??? question "Database connection errors"
Ensure PostgreSQL has started and the sysvipc annotation is working:
bash podman logs immich_postgres
The database needs a few seconds to initialize on first run.
??? question "Photos not uploading from mobile"
Ensure port 2283 is accessible from your network. Check firewall rules:
bash # PF firewall pass in on egress proto tcp to port 2283
??? question "Facial recognition not working"
The ML service downloads models on first use. Check if models are cached:
bash podman exec immich_machine_learning ls -la /cache/huggingface
| Variable | Default | Description |
|---|---|---|
DB_HOSTNAME |
localhost |
|
REDIS_HOSTNAME |
localhost |
|
IMMICH_MACHINE_LEARNING_URL |
http://${IMMICH_ML_HOST:-localhost}:3003 |
|
IMMICH_MACHINE_LEARNING_ENABLED |
true |
|
IMMICH_HOST |
0.0.0.0 |
|
UPLOAD_LOCATION |
/containers/immich/library |
Path to store uploaded media |
DB_DATA_LOCATION |
/containers/immich/postgres |
Path to store database files |
DB_PASSWORD |
postgres |
PostgreSQL database password |
DB_USERNAME |
postgres |
PostgreSQL username |
DB_DATABASE_NAME |
immich |
PostgreSQL database name |
IMMICH_ML_TAG |
`` | Machine learning image tag (defaults to 'latest') |
IMMICH_ML_ENABLED |
`` | false turns machine learning off (set by the choice) |
PUBLIC_BASE_URL |
`` | Address the public proxy is reached at, no trailing slash (optional; it uses the request's host otherwise) |
TZ |
`` | Timezone |
| Path | Description |
|---|---|
/data |
Media storage (mapped to UPLOAD_LOCATION) |
/etc/localtime |
Architectures: amd64
User: bsd (UID/GID via PUID/PGID, defaults to 1000:1000)
Base: FreeBSD 15.1
Need help? Join our Discord community.