Deploy Zealot with Nomad guide
Zealot support deployments using Nomad, it use HCL language to configure.
Setupâ
Using Nomadâ
First, follow the official tutorial to install nomad, this binary file contains the client and server. It is recommended to follow the tutorials to walk through it if you don't know it.
The following file will create the postgres, redis and zealot services.
For the existing external database and cache services,
you can delete the corresponding port
, service
and task
and edit the template variables in the zealot
task.
job "zealot" {
type = "service"
datacenters = "dc1" // modify
update {
max_parallel = 1
min_healthy_time = "30s"
auto_revert = true
}
group "zealot" {
network {
port "zealot" {
to = 80
}
port "postgres" {
to = 5678
}
port "redis" {
to = 6379
}
}
service {
name = "zealot"
port = "zealot"
provider = "nomad"
// Register to traefik
// tags = [
// "traefik.enable=true",
// "traefik.http.routers.zealot.entrypoints=web, websecure",
// "traefik.http.routers.zealot.rule=Host(`zealot.example.com`)",
// ]
}
service {
name = "postgres"
port = "postgres"
provider = "nomad"
// Register to traefik
// tags = [
// "traefik.enable=true",
// "traefik.tcp.routers.postgres.rule=HostSNI(`*`)",
// "traefik.tcp.routers.postgres.entrypoints=postgres",
// ]
}
service {
name = "redis"
port = "redis"
provider = "nomad"
// Register to traefik
// tags = [
// "traefik.enable=true",
// "traefik.tcp.routers.redis.rule=HostSNI(`*`)",
// "traefik.tcp.routers.redis.entrypoints=redis",
// ]
}
task "zealot" {
driver = "docker"
config {
image = "ghcr.io/tryzealot/zealot:latest"
ports = ["zealot"]
// modify
volumes = [
"/tmp/zealot/uploads:/app/public/uploads",
"/tmp/zealot/backups:/app/public/backups",
]
// Register to homepage dashboard
// labels = {
// "homepage.group" = "Dev"
// "homepage.name" = "Zealot"
// "homepage.icon" = "mdi-progress-download"
// "homepage.href" = "https://zealot.example.com"
// "homepage.description" = "Beta App Distribution"
// }
}
// Zealot example config
// https://github.com/tryzealot/zealot-docker/blob/master/config.env
template {
destination = "local/config.env"
change_mode = "restart"
env = true
data = <<-EOF
ZEALOT_APPEARANCE = dark
ZEALOT_DOMAIN = zealot.example.com
ZEALOT_GUEST_MODE = false
ZEALOT_REGISTER_ENABLED = true
EOF
}
template {
destination = "secrets/secret.env"
change_mode = "restart"
env = true
data = <<-EOF
# admin account
ZEALOT_ADMIN_EMAIL = admin@zealot.com
ZEALOT_ADMIN_PASSWORD = ze@l0t
# datbase
ZEALOT_POSTGRES_HOST = {{ env "NOMAD_IP_postgres" }}
ZEALOT_POSTGRES_PORT = {{ env "NOMAD_PORT_postgres" }}
ZEALOT_POSTGRES_USERNAME = "zealot"
ZEALOT_POSTGRES_PASSWORD = "zealot"
ZEALOT_POSTGRES_DB_NAME = "zealot"
# cache
REDIS_URL = redis://{{ env "NOMAD_ARRR_redis" }}/0
# secret token
SECRET_TOKEN = $${ sha256(uuidv5("url", "zealot.ews.im")) }
EOF
}
resources {
cpu = 500
memory = 500
memory_max = 1000
}
}
task "postgres" {
driver = "docker"
lifecycle {
hook = "prestart"
sidecar = true
}
config {
image = "postgres:14-alpine"
ports = ["postgres"]
volumes = [
"secrets/init-role.sql:/init-role.sql",
"secrets/init-db.sql:/init-db.sql"
]
}
env {
POSTGRES_INITDB_ARGS = "--data-checksums"
POSTGRES_USER = "zealot"
POSTGRES_PASSWORD = "zealot"
POSTGRES_DB = "zealot"
}
resources{
cpu = 512
memory = 200
memory_max = 512
}
}
task "redis" {
driver = "docker"
lifecycle {
hook = "prestart"
sidecar = true
}
config {
image = "redis:5-alpine"
ports = ["redis"]
}
resources {
cpu = 200
memory = 200
}
}
}
}
Save the file and execute the command nomad job run zealot.nomad
.
Using Terraformâ
Both Terraform and Nomad are the same company.
Following the offical tutorials to install terraform, nomad plugin,
copy the zealot.nomad
in previous step and edit a new file named main.tf
:
resource "nomad_job" "jobs" {
jobspec = file("${path.module}/zealot.nomad")
}
Execute terraform plan
to ensure, then deploy terraform apply
.
External Storagesâ
Nomad supports multi-cluster management, and in many cases the storage deployed by the service cannot be mounted directly to the corresponding file system, but is more often placed on top of a shared file storage protocol, such as SMB, NFS, S3, etc.
CSIâ
Nomad currently supports the CSI in a limited capability (Nomad 1.5). Nomad can utilize CSI volumes, but it can not automatically create, destroy, or manage them in any capacity. Volumes have to be created externally and then registered with Nomad. You can find a list of plugins in the Kubernetes CSI Developer Documentation.
Plugin | Schemes | Compatible | terraform nomad resource |
---|---|---|---|
kubernetes-csi-driver-smb | smb | Unknown | Unknown |
kubernetes-csi-driver-nfs | nfs | Supported | nomad_volume |
kubernetes-csi-driver-iscsi | iscsi | Supported | Supported |
democraticcsi/democratic-csi | smb/nfs/iscsi | Supported | nomad_external_volume |
rocketduck/csi-plugin-nfs | nfs | Supported | nomad_external_volume |