parent
cdcc389e94
commit
65eabc1ef9
106
immich.nomad.hcl
106
immich.nomad.hcl
|
@ -2,7 +2,7 @@
|
|||
|
||||
job [[ .immich.instance | toJSON ]] {
|
||||
|
||||
[[ template "common/job_start.tpl" . ]]
|
||||
[[ template "common/job_start" . ]]
|
||||
|
||||
[[ $c := merge .immich.server . -]]
|
||||
|
||||
|
@ -12,31 +12,13 @@ job [[ .immich.instance | toJSON ]] {
|
|||
mode = "bridge"
|
||||
}
|
||||
|
||||
volume "data" {
|
||||
type = [[ .immich.volumes.data.type | toJSON ]]
|
||||
source = [[ .immich.volumes.data.source | toJSON ]]
|
||||
[[- if ne .immich.volumes.data.type "host" ]]
|
||||
access_mode = "single-node-writer"
|
||||
attachment_mode = "file-system"
|
||||
[[- end ]]
|
||||
}
|
||||
|
||||
[[- if .immich.typesense.enabled ]]
|
||||
volume "typesense" {
|
||||
type = [[ .immich.volumes.typesense.type | toJSON ]]
|
||||
source = [[ .immich.volumes.typesense.source | toJSON ]]
|
||||
[[- if ne .immich.volumes.typesense.type "host" ]]
|
||||
access_mode = "single-node-writer"
|
||||
attachment_mode = "file-system"
|
||||
[[- end ]]
|
||||
}
|
||||
[[- end ]]
|
||||
[[ template "common/volumes" $c.volumes ]]
|
||||
|
||||
service {
|
||||
name = "[[ .immich.instance ]][[ .consul.suffix ]]"
|
||||
port = 3001
|
||||
|
||||
[[ template "common/connect.tpl" $c ]]
|
||||
[[ template "common/connect" $c ]]
|
||||
|
||||
check {
|
||||
type = "http"
|
||||
|
@ -67,9 +49,9 @@ job [[ .immich.instance | toJSON ]] {
|
|||
"[[ $s.traefik.instance ]].http.routers.[[ .immich.instance ]]-share[[ .consul.suffix ]].rule=Host(`[[ (urlParse $c.public_url).Hostname ]]`) && PathPrefix(`[[ (urlParse $c.public_url).Path ]]/share/`)",
|
||||
"[[ $c.traefik.instance ]].http.routers.[[ .immich.instance ]]-share[[ .consul.suffix ]].entrypoints=[[ join $c.traefik.entrypoints "," ]]",
|
||||
[[- if not (regexp.Match "^/?$" (urlParse $c.public_url).Path) ]]
|
||||
"[[ $s.traefik.instance ]].http.routers.[[ .immich.instance ]]-share[[ .consul.suffix ]].middlewares=[[ .immich.instance ]]-headers[[ .consul.suffix ]],[[ .immich.instance ]]-prefix[[ $c.consul.suffix ]],[[ template "common/traefik_middlewares.tpl" $s.traefik ]]",
|
||||
"[[ $s.traefik.instance ]].http.routers.[[ .immich.instance ]]-share[[ .consul.suffix ]].middlewares=[[ .immich.instance ]]-headers[[ .consul.suffix ]],[[ .immich.instance ]]-prefix[[ $c.consul.suffix ]],[[ template "common/traefik_middlewares" $s.traefik ]]",
|
||||
[[- else ]]
|
||||
"[[ $s.traefik.instance ]].http.routers.[[ .immich.instance ]]-share[[ .consul.suffix ]].middlewares=[[ .immich.instance ]]-headers[[ .consul.suffix ]],[[ template "common/traefik_middlewares.tpl" $s.traefik ]]",
|
||||
"[[ $s.traefik.instance ]].http.routers.[[ .immich.instance ]]-share[[ .consul.suffix ]].middlewares=[[ .immich.instance ]]-headers[[ .consul.suffix ]],[[ template "common/traefik_middlewares" $s.traefik ]]",
|
||||
[[- end ]]
|
||||
|
||||
# Main app router
|
||||
|
@ -77,15 +59,15 @@ job [[ .immich.instance | toJSON ]] {
|
|||
[[- if not (regexp.Match "^/?$" (urlParse $c.public_url).Path) ]] && PathPrefix(`[[ (urlParse $c.public_url).Path ]]`)[[ end ]]",
|
||||
"[[ $c.traefik.instance ]].http.routers.[[ .immich.instance ]][[ .consul.suffix ]].entrypoints=[[ join $c.traefik.entrypoints "," ]]",
|
||||
[[- if not (regexp.Match "^/?$" (urlParse $c.public_url).Path) ]]
|
||||
"[[ $c.traefik.instance ]].http.routers.[[ .immich.instance ]][[ .consul.suffix ]].middlewares=[[ .immich.instance ]]-headers[[ .consul.suffix ]],[[ .immich.instance ]]-prefix[[ $c.consul.suffix ]],[[ template "common/traefik_middlewares.tpl" $c.traefik ]]",
|
||||
"[[ $c.traefik.instance ]].http.routers.[[ .immich.instance ]][[ .consul.suffix ]].middlewares=[[ .immich.instance ]]-headers[[ .consul.suffix ]],[[ .immich.instance ]]-prefix[[ $c.consul.suffix ]],[[ template "common/traefik_middlewares" $c.traefik ]]",
|
||||
[[- else ]]
|
||||
"[[ $c.traefik.instance ]].http.routers.[[ .immich.instance ]][[ .consul.suffix ]].middlewares=[[ .immich.instance ]]-headers[[ .consul.suffix ]],[[ template "common/traefik_middlewares.tpl" $c.traefik ]]",
|
||||
"[[ $c.traefik.instance ]].http.routers.[[ .immich.instance ]][[ .consul.suffix ]].middlewares=[[ .immich.instance ]]-headers[[ .consul.suffix ]],[[ template "common/traefik_middlewares" $c.traefik ]]",
|
||||
[[- end ]]
|
||||
]
|
||||
}
|
||||
|
||||
# Wait for external services to be ready before continuing
|
||||
[[ template "common/task.wait_for.tpl" $c ]]
|
||||
[[ template "common/task.wait_for" $c ]]
|
||||
|
||||
[[ $c := merge .immich.server . -]]
|
||||
# The main immich API server
|
||||
|
@ -111,18 +93,17 @@ job [[ .immich.instance | toJSON ]] {
|
|||
|
||||
env {
|
||||
REDIS_HOSTNAME = "127.0.0.1"
|
||||
TYPESENSE_HOST = "127.0.0.1"
|
||||
IMMICH_MEDIA_LOCATION = "/data"
|
||||
}
|
||||
|
||||
[[ template "common/file_env.tpl" $c.env ]]
|
||||
[[ template "common/file_env" $c.env ]]
|
||||
|
||||
volume_mount {
|
||||
volume = "data"
|
||||
destination = "/data"
|
||||
}
|
||||
|
||||
[[ template "common/resources.tpl" $c.resources ]]
|
||||
[[ template "common/resources" $c.resources ]]
|
||||
|
||||
}
|
||||
|
||||
|
@ -155,66 +136,20 @@ job [[ .immich.instance | toJSON ]] {
|
|||
|
||||
env {
|
||||
REDIS_HOSTNAME = "127.0.0.1"
|
||||
TYPESENSE_HOST = "127.0.0.1"
|
||||
IMMICH_MEDIA_LOCATION = "/data"
|
||||
}
|
||||
|
||||
[[ template "common/file_env.tpl" $c.env ]]
|
||||
[[ template "common/file_env" $c.env ]]
|
||||
|
||||
volume_mount {
|
||||
volume = "data"
|
||||
destination = "/data"
|
||||
}
|
||||
|
||||
[[ template "common/resources.tpl" $c.resources ]]
|
||||
[[ template "common/resources" $c.resources ]]
|
||||
}
|
||||
|
||||
[[- if .immich.typesense.enabled ]]
|
||||
[[ $c := merge .immich.typesense . ]]
|
||||
|
||||
# Typesense is a vector database used to get fast search responses
|
||||
task "typesense" {
|
||||
driver = [[ $c.nomad.driver | toJSON ]]
|
||||
# Also run as an unprivileged user
|
||||
user = 3001
|
||||
|
||||
lifecycle {
|
||||
hook = "prestart"
|
||||
sidecar = true
|
||||
}
|
||||
|
||||
config {
|
||||
image = [[ $c.image | toJSON ]]
|
||||
readonly_rootfs = true
|
||||
args = [
|
||||
"--api-address=127.0.0.1",
|
||||
"--peering-address=127.0.0.1"
|
||||
]
|
||||
pids_limit = 500
|
||||
}
|
||||
|
||||
vault {
|
||||
policies = ["[[ .immich.instance ]][[ .consul.suffix ]]"]
|
||||
env = false
|
||||
disable_file = true
|
||||
}
|
||||
|
||||
env {
|
||||
TYPESENSE_DATA_DIR = "/data"
|
||||
}
|
||||
|
||||
[[ template "common/file_env.tpl" $c.env ]]
|
||||
|
||||
volume_mount {
|
||||
volume = "typesense"
|
||||
destination = "/data"
|
||||
}
|
||||
|
||||
[[ template "common/resources.tpl" $c.resources ]]
|
||||
}
|
||||
[[- end ]]
|
||||
|
||||
[[ template "common/task.redis.tpl" dict "resources" .immich.redis.resources ]]
|
||||
[[ template "common/task.redis" dict "resources" .immich.redis.resources ]]
|
||||
}
|
||||
|
||||
[[- if .immich.machine_learning.enabled ]]
|
||||
|
@ -227,19 +162,12 @@ job [[ .immich.instance | toJSON ]] {
|
|||
mode = "bridge"
|
||||
}
|
||||
|
||||
volume "ml" {
|
||||
type = [[ .immich.volumes.ml.type | toJSON ]]
|
||||
source = [[ .immich.volumes.ml.source | toJSON ]]
|
||||
[[- if ne .immich.volumes.ml.type "host" ]]
|
||||
access_mode = "single-node-writer"
|
||||
attachment_mode = "file-system"
|
||||
[[- end ]]
|
||||
}
|
||||
[[ template "common/volumes" $c.volumes ]]
|
||||
|
||||
service {
|
||||
name = "[[ .immich.instance ]]-ml[[ .consul.suffix ]]"
|
||||
port = 3003
|
||||
[[ template "common/connect.tpl" $c ]]
|
||||
[[ template "common/connect" $c ]]
|
||||
}
|
||||
|
||||
[[ $c := merge .immich.machine_learning . ]]
|
||||
|
@ -257,7 +185,7 @@ job [[ .immich.instance | toJSON ]] {
|
|||
TMPDIR = "/local"
|
||||
MPLCONFIGDIR = "/local"
|
||||
MACHINE_LEARNING_HOST = "127.0.0.1"
|
||||
[[ template "common/proxy_env.tpl" $c ]]
|
||||
[[ template "common/proxy_env" $c ]]
|
||||
}
|
||||
|
||||
volume_mount {
|
||||
|
@ -265,7 +193,7 @@ job [[ .immich.instance | toJSON ]] {
|
|||
destination = "/cache"
|
||||
}
|
||||
|
||||
[[ template "common/resources.tpl" $c.resources ]]
|
||||
[[ template "common/resources" $c.resources ]]
|
||||
}
|
||||
}
|
||||
[[- end ]]
|
||||
|
|
|
@ -1,17 +0,0 @@
|
|||
#!/bin/sh
|
||||
|
||||
set -euo pipefail
|
||||
|
||||
# Initialize random passwords if needed
|
||||
|
||||
if ! vault kv list [[ .vault.prefix ]]kv/service 2>/dev/null | grep -q -E '^[[ .immich.instance ]]$'; then
|
||||
vault kv put [[ .vault.prefix ]]kv/service/[[ .immich.instance ]] \
|
||||
typesense_api_key=$(pwgen -s -n 50 1)
|
||||
fi
|
||||
|
||||
for PWD in typesense_api_key; do
|
||||
if ! vault kv get -field ${PWD} [[ .vault.prefix ]]kv/service/[[ .immich.instance ]] >/dev/null 2>&1; then
|
||||
vault kv patch [[ .vault.prefix ]]kv/service/[[ .immich.instance ]] \
|
||||
${PWD}=$(pwgen -s -n 50 1)
|
||||
fi
|
||||
done
|
|
@ -6,7 +6,7 @@ immich:
|
|||
instance: immich
|
||||
|
||||
# Immich version
|
||||
version: v1.90.2
|
||||
version: v1.91.0
|
||||
|
||||
# API server settings
|
||||
server:
|
||||
|
@ -17,7 +17,6 @@ immich:
|
|||
# Additional env to set ni the container
|
||||
env:
|
||||
DB_URL: '{{ with secret "[[ .vault.prefix ]]database/creds/[[ .immich.instance ]]" }}postgres://{{ .Data.username }}:{{ urlquery .Data.password }}@localhost:5432/[[ .immich.instance ]]{{ end }}'
|
||||
TYPESENSE_API_KEY: '{{ with secret "[[ .vault.prefix ]]kv/service/[[ .immich.instance ]]" }}{{ .Data.data.typesense_api_key }}{{ end }}'
|
||||
NODE_OPTIONS: --max-old-space-size={{ env "NOMAD_MEMORY_LIMIT" }}
|
||||
|
||||
# Resource allocation
|
||||
|
@ -73,6 +72,12 @@ immich:
|
|||
- compression@file
|
||||
middlewares: []
|
||||
|
||||
# Volumes used for data storage
|
||||
volumes:
|
||||
data:
|
||||
type: csi
|
||||
source: '[[ .immich.instance ]]-data'
|
||||
|
||||
# The microservices do the bulk of media handling (thumbnails etc.)
|
||||
microservices:
|
||||
|
||||
|
@ -82,7 +87,6 @@ immich:
|
|||
# Env vars to set in the container
|
||||
env:
|
||||
DB_URL: '{{ with secret "[[ .vault.prefix ]]database/creds/[[ .immich.instance ]]" }}postgres://{{ .Data.username }}:{{ urlquery .Data.password }}@localhost:5432/[[ .immich.instance ]]{{ end }}'
|
||||
TYPESENSE_API_KEY: '{{ with secret "[[ .vault.prefix ]]kv/service/[[ .immich.instance ]]" }}{{ .Data.data.typesense_api_key }}{{ end }}'
|
||||
NODE_OPTIONS: --max-old-space-size={{ env "NOMAD_MEMORY_LIMIT" }}
|
||||
|
||||
# Resource allocation
|
||||
|
@ -108,24 +112,11 @@ immich:
|
|||
cpu: 1024
|
||||
memory: 1536
|
||||
|
||||
# Typesense is a database for fast search result
|
||||
typesense:
|
||||
|
||||
# Typesense is also an optional component and can be disabled
|
||||
enabled: true
|
||||
|
||||
# DOcker image to use
|
||||
image: typesense/typesense:0.25.1
|
||||
|
||||
# Environment var to set in the container
|
||||
env:
|
||||
TYPESENSE_API_KEY: '{{ with secret "[[ .vault.prefix ]]kv/service/[[ .immich.instance ]]" }}{{ .Data.data.typesense_api_key }}{{ end }}'
|
||||
|
||||
# Resource allocation
|
||||
resources:
|
||||
cpu: 100
|
||||
memory: 512
|
||||
memory_max: 768
|
||||
volumes:
|
||||
# Volume used for models cache
|
||||
ml:
|
||||
type: csi
|
||||
source: '[[ .immich.instance ]]-ml'
|
||||
|
||||
# Redis task will use a common template
|
||||
# We just set custom resources allocation
|
||||
|
@ -134,16 +125,3 @@ immich:
|
|||
cpu: 20
|
||||
memory: 64
|
||||
|
||||
# Volumes used for data persistance
|
||||
volumes:
|
||||
data:
|
||||
type: csi
|
||||
source: '[[ .immich.instance ]]-data'
|
||||
|
||||
ml:
|
||||
type: csi
|
||||
source: '[[ .immich.instance ]]-ml'
|
||||
|
||||
typesense:
|
||||
type: csi
|
||||
source: '[[ .immich.instance ]]-typesense'
|
||||
|
|
Loading…
Reference in New Issue