1.0.0 Release IaaS

This commit is contained in:
2026-03-15 04:41:02 +09:00
commit a7365da431
292 changed files with 36059 additions and 0 deletions

View File

@@ -0,0 +1,35 @@
[Quadlet]
DefaultDependencies=false
[Unit]
Description=CA
After=network-online.target
Wants=network-online.target
[Container]
Image=docker.io/smallstep/step-ca:{{ version['containers']['step'] }}
ContainerName=ca
HostName=ca
PublishPort=9000:9000/tcp
Volume=%h/containers/ca/certs:/home/step/certs:ro
Volume=%h/containers/ca/secrets:/home/step/secrets:ro
Volume=%h/containers/ca/config:/home/step/config:rw
Volume=%h/containers/ca/db:/home/step/db:rw
Volume=%h/containers/ca/templates:/home/step/templates:rw
Environment="TZ=Asia/Seoul"
Environment="PWDPATH=/run/secrets/STEP_CA_PASSWORD"
Secret=STEP_CA_PASSWORD,target=/run/secrets/STEP_CA_PASSWORD
[Service]
Restart=always
RestartSec=10s
TimeoutStopSec=120
[Install]
WantedBy=default.target

View File

@@ -0,0 +1,61 @@
{
"root": "/home/step/certs/ilnmors_root_ca.crt",
"federatedRoots": null,
"crt": "/home/step/certs/ilnmors_intermediate_ca.crt",
"key": "/home/step/secrets/ilnmors_intermediate_ca.key",
"address": ":9000",
"insecureAddress": "",
"dnsNames": [
"{{ infra_uri['ca']['domain'] }}"
],
"logger": {
"format": "text"
},
"db": {
"type": "badgerv2",
"dataSource": "/home/step/db",
"badgerFileLoadingMode": ""
},
"authority": {
"policy": {
"x509": {
"allow": {
"dns": [
"ilnmors.internal",
"*.ilnmors.internal"
]
},
"allowWildcardNames": true
}
},
"provisioners": [
{
"type": "ACME",
"name": "acme@ilnmors.internal",
"claims": {
"defaultTLSCertDuration": "2160h0m0s",
"enableSSHCA": true,
"disableRenewal": false,
"allowRenewalAfterExpiry": false,
"disableSmallstepExtensions": false
},
"options": {
"x509": {},
"ssh": {}
}
}
],
"template": {},
"backdate": "1m0s"
},
"tls": {
"cipherSuites": [
"TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256",
"TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256"
],
"minVersion": 1.2,
"maxVersion": 1.3,
"renegotiation": false
},
"commonName": "ilnmors Online CA"
}

View File

@@ -0,0 +1,6 @@
{
"ca-url": "https://{{ infra_uri['ca']['domain'] }}:{{ infra_uri['ca']['ports']['https'] }}",
"ca-config": "/home/step/config/ca.json",
"fingerprint": "215c851d2d0d2dbf90fc3507425207c29696ffd587c640c94a68dddb1d84d8e8",
"root": "/home/step/certs/ilnmors_root_ca.crt"
}

View File

@@ -0,0 +1,8 @@
{
"subject": {{ toJson .Subject }},
"keyUsage": ["certSign", "crlSign"],
"basicConstraints": {
"isCA": true,
"maxPathLen": 0
}
}

View File

@@ -0,0 +1,54 @@
# https://github.com/grafana/grafana/blob/main/conf/defaults.ini
[paths]
data = /var/lib/grafana
logs = /var/log/grafana
plugins = /var/lib/grafana/plugins
provisioning = /etc/grafana/provisioning
[server]
protocol = http
http_port = 3000
domain = grafana.ilnmors.internal
root_url = http://grafana.ilnmors.internal/
router_logging = false
[database]
type = postgres
host = {{ infra_uri['postgresql']['domain'] }}:{{ infra_uri['postgresql']['ports']['tcp'] }}
name = grafana_db
user = grafana
password = $__file{/run/secrets/GF_DB_PASSWORD}
ssl_mode = verify-full
ca_cert_path = /etc/ssl/grafana/ilnmors_root_ca.crt
[auth.ldap]
enabled = true
config_file = /etc/grafana/ldap.toml
allow_sign_up = true
[auth]
disable_login_form = false
allow_anonymous_device_id_auth = false
[security]
# local admin
admin_user = local_admin
# local password
admin_password = $__file{/run/secrets/GF_ADMIN_PASSWORD}
cookie_secure = true
cookie_samesite = lax
allow_embedding = false
# [smtp]
# enabled = true
# host = localhost:25
# from_address = alert@ilnmors.internal
# from_name = Grafana-Infra
[analytics]
reporting_enabled = false
check_for_updates = false
[log]
mode = console
level = info

View File

@@ -0,0 +1,47 @@
# https://github.com/lldap/lldap/blob/main/example_configs/grafana_ldap_config.toml
[[servers]]
host = "{{ infra_uri['ldap']['domain'] }}"
port = {{ infra_uri['ldap']['ports']['ldaps'] }}
# Activate STARTTLS or LDAPS
use_ssl = true
# true = STARTTLS, false = LDAPS
start_tls = false
tls_ciphers = []
min_tls_version = ""
ssl_skip_verify = false
root_ca_cert = "/etc/ssl/grafana/ilnmors_root_ca.crt"
# mTLS option, it is not needed
# client_cert = "/path/to/client.crt"
# client_key = "/path/to/client.key"
bind_dn = "uid=grafana,ou=people,dc=ilnmors,dc=internal"
bind_password = "$__file{/run/secrets/LDAP_BIND_PASSWORD}"
search_filter = "(|(uid=%s)(mail=%s))"
search_base_dns = ["dc=ilnmors,dc=internal"]
[servers.attributes]
member_of = "memberOf"
email = "mail"
name = "displayName"
surname = "sn"
username = "uid"
group_search_filter = "(&(objectClass=groupOfUniqueNames)(uniqueMember=%s))"
group_search_base_dns = ["ou=groups,dc=ilnmors,dc=internal"]
group_search_filter_user_attribute = "uid"
[[servers.group_mappings]]
group_dn = "cn=lldap_admin,ou=groups,dc=ilnmors,dc=internal"
org_role = "Admin"
grafana_admin = true
[[servers.group_mappings]]
group_dn = "cn=admins,ou=groups,dc=ilnmors,dc=internal"
org_role = "Editor"
grafana_admin = false
[[servers.group_mappings]]
group_dn = "cn=users,ou=groups,dc=ilnmors,dc=internal"
org_role = "Viewer"
grafana_admin = false

View File

@@ -0,0 +1,29 @@
# https://github.com/grafana/grafana/blob/main/conf/provisioning/datasources/sample.yaml
apiVersion: 1
datasources:
- name: Prometheus
type: prometheus
url: https://prometheus.ilnmors.internal:9090
access: proxy
isDefault: true
jsonData:
tlsAuth: false
tlsAuthWithCACert: true
httpMethod: POST
secureJsonData:
tlsCACert: "$__file{/etc/ssl/grafana/ilnmors_root_ca.crt}"
- name: Loki
type: loki
url: https://loki.ilnmors.internal:3100
access: proxy
jsonData:
tlsAuth: false
tlsAuthWithCACert: true
# Tenent value set "to solve no org id"
httpHeaderName1: "X-Scope-OrgID"
maxLines: 1000
secureJsonData:
tlsCACert: "$__file{/etc/ssl/grafana/ilnmors_root_ca.crt}"
httpHeaderValue1: "ilnmors.internal"

View File

@@ -0,0 +1,43 @@
[Quadlet]
DefaultDependencies=false
[Unit]
Description=Grafana
After=postgresql.service ldap.service
Requires=postgresql.service ldap.service
[Container]
Image=docker.io/grafana/grafana:{{ version['containers']['grafana'] }}
ContainerName=grafana
HostName=grafana
AddHost={{ infra_uri['postgresql']['domain'] }}:host-gateway
AddHost={{ infra_uri['ldap']['domain'] }}:host-gateway
AddHost={{ infra_uri['prometheus']['domain'] }}:host-gateway
AddHost={{ infra_uri['loki']['domain'] }}:host-gateway
PublishPort=3000:3000/tcp
Volume=%h/containers/grafana/data:/var/lib/grafana:rw
Volume=%h/containers/grafana/etc:/etc/grafana:ro
Volume=%h/containers/grafana/ssl:/etc/ssl/grafana:ro
Environment="TZ=Asia/Seoul"
Environment="GF_PATHS_CONFIG=/etc/grafana/grafana.ini"
# plugin
# Environment="GF_INSTALL_PLUGINS=grafana-clock-panel,grafana-simple-json-datasource"
Environment="GF_FEATURE_TOGGLES_EXPAND_ENV_VARS=true"
Secret=GF_DB_PASSWORD,target=/run/secrets/GF_DB_PASSWORD
Secret=LDAP_BIND_PASSWORD,target=/run/secrets/LDAP_BIND_PASSWORD
Secret=GF_ADMIN_PASSWORD,target=/run/secrets/GF_ADMIN_PASSWORD
[Service]
Restart=always
RestartSec=10s
TimeoutStopSec=120
[Install]
WantedBy=default.target

View File

@@ -0,0 +1,64 @@
[Quadlet]
DefaultDependencies=false
[Unit]
Description=LDAP
After=postgresql.service
Requires=postgresql.service
[Container]
Image=docker.io/lldap/lldap:{{ version['containers']['ldap'] }}
ContainerName=ldap
HostName=ldap
# They are at the same host (for Pasta, it is needed)
AddHost={{ infra_uri['postgresql']['domain'] }}:host-gateway
# For LDAPS - 636 > 6360 nftables
PublishPort=6360:6360/tcp
# Web UI
PublishPort=17170:17170/tcp
Volume=%h/containers/ldap/data:/data:rw
Volume=%h/containers/ldap/ssl:/etc/ssl/ldap:ro
# Default
Environment="TZ=Asia/Seoul"
# Domain
Environment="LLDAP_LDAP_BASE_DN=dc=ilnmors,dc=internal"
# LDAPS
Environment="LLDAP_LDAPS_OPTIONS__ENABLED=true"
Environment="LLDAP_LDAPS_OPTIONS__CERT_FILE=/etc/ssl/ldap/ldap.crt"
Environment="LLDAP_LDAPS_OPTIONS__KEY_FILE=/etc/ssl/ldap/ldap.key"
# Secret files' Path
Environment="LLDAP_KEY_SEED_FILE=/run/secrets/LLDAP_KEY_SEED"
Environment="LLDAP_JWT_SECRET_FILE=/run/secrets/LLDAP_JWT_SECRET"
# SMTP options > you can set all of these at the /data/config.toml instead of Environment
# Only `LLDAP_SMTP_OPTIONS__PASSWORD` will be injected by secret
# LLDAP_SMTP_OPTIONS__ENABLE_PASSWORD_RESET=true
# LLDAP_SMTP_OPTIONS__SERVER=smtp.example.com
# LLDAP_SMTP_OPTIONS__PORT=465
# LLDAP_SMTP_OPTIONS__SMTP_ENCRYPTION=TLS
# LLDAP_SMTP_OPTIONS__USER=no-reply@example.com
# LLDAP_SMTP_OPTIONS__PASSWORD=PasswordGoesHere
# LLDAP_SMTP_OPTIONS__FROM=no-reply <no-reply@example.com>
# LLDAP_SMTP_OPTIONS__TO=admin <admin@example.com>
# Database
Secret=LLDAP_DATABASE_URL,type=env
# Secrets
Secret=LLDAP_KEY_SEED,target="/run/secrets/LLDAP_KEY_SEED"
Secret=LLDAP_JWT_SECRET,target="/run/secrets/LLDAP_JWT_SECRET"
[Service]
Restart=always
RestartSec=10s
TimeoutStopSec=120
[Install]
WantedBy=default.target

View File

@@ -0,0 +1,46 @@
---
server:
http_listen_address: "::"
http_listen_port: 3100
http_tls_config:
cert_file: /etc/ssl/loki/loki.crt
key_file: /etc/ssl/loki/loki.key
#memberlist:
# join_members: ["localhost"]
# bind_addr: ['::']
# bind_port: 7946
schema_config:
configs:
- from: "2023-01-01"
store: tsdb
object_store: filesystem
schema: v13
index:
prefix: index_
period: 24h
limits_config:
retention_period: 30d
reject_old_samples: true
reject_old_samples_max_age: 168h
common:
instance_addr: localhost
path_prefix: /loki
replication_factor: 1
storage:
filesystem:
chunks_directory: /loki/chunks
rules_directory: /loki/rules
ring:
kvstore:
store: inmemory
compactor:
working_directory: /loki/compactor
delete_request_store: filesystem
compaction_interval: 10m
retention_enabled: true
retention_delete_delay: 2h

View File

@@ -0,0 +1,32 @@
[Quadlet]
DefaultDependencies=false
[Unit]
Description=Loki
After=network-online.target
Wants=network-online.target
[Container]
Image=docker.io/grafana/loki:{{ version['containers']['loki'] }}
ContainerName=loki
HostName=loki
PublishPort=3100:3100/tcp
Volume=%h/containers/loki/data:/loki:rw
Volume=%h/containers/loki/etc:/etc/loki:ro
Volume=%h/containers/loki/ssl:/etc/ssl/loki:ro
Environment="TZ=Asia/Seoul"
Exec=--config.file=/etc/loki/loki.yaml
[Service]
Restart=always
RestartSec=10s
TimeoutStopSec=120
[Install]
WantedBy=default.target

View File

@@ -0,0 +1,12 @@
ARG PG_VER={{ version['containers']['postgresql'] }}
FROM docker.io/library/postgres:${PG_VER}
ARG VECTORCHORD_VER={{ version['containers']['vectorchord'] }}
RUN apt update && \
apt install -y wget postgresql-${PG_MAJOR}-pgvector && \
wget -nv -O /tmp/vchord.deb https://github.com/tensorchord/VectorChord/releases/download/${VECTORCHORD_VER}/postgresql-${PG_MAJOR}-vchord_${VECTORCHORD_VER}-1_amd64.deb && \
apt install -y /tmp/vchord.deb && \
apt purge -y wget && apt autoremove -y && \
rm -rf /tmp/vchord.deb /var/lib/apt/lists/*

View File

@@ -0,0 +1,28 @@
# @authcomment@
# TYPE DATABASE USER ADDRESS METHOD
# Local host `trust`
local all all trust
# Local monitoring connection (host - infra VM) `trust`
hostssl postgres alloy {{ hostvars['fw']['network4']['infra']['server'] }}/32 trust
hostssl postgres alloy {{ hostvars['fw']['network6']['infra']['server'] }}/128 trust
hostssl postgres alloy {{ hostvars['fw']['network4']['subnet']['lla'] }} trust
hostssl postgres alloy {{ hostvars['fw']['network6']['subnet']['lla'] }} trust
# Local connection (in postgresql container) needs password (127.0.0.1 - container loopback)
host all all 127.0.0.1/32 scram-sha-256
host all all ::1/128 scram-sha-256
# Local connection (host - infra VM) needs password (169.254.1.0/24 - link_local subnet for containers in pasta mode)
hostssl all all {{ hostvars['fw']['network4']['infra']['server'] }}/32 scram-sha-256
hostssl all all {{ hostvars['fw']['network6']['infra']['server'] }}/128 scram-sha-256
hostssl all all {{ hostvars['fw']['network4']['subnet']['lla'] }} scram-sha-256
hostssl all all {{ hostvars['fw']['network6']['subnet']['lla'] }} scram-sha-256
# auth VM
hostssl all all {{ hostvars['fw']['network4']['auth']['server'] }}/32 scram-sha-256
hostssl all all {{ hostvars['fw']['network6']['auth']['server'] }}/128 scram-sha-256
# app VM (Applications, 192.168.10.13)
hostssl all all {{ hostvars['fw']['network4']['app']['server'] }}/32 scram-sha-256
hostssl all all {{ hostvars['fw']['network6']['app']['server'] }}/128 scram-sha-256

View File

@@ -0,0 +1,41 @@
#------------------------------------------------------------------------------
# CUSTOMIZED OPTIONS
#------------------------------------------------------------------------------
# Add settings for extensions here
# Listen_address
listen_addresses = '*'
# Max connections
max_connections = 250
# listen_port
port = 5432
# SSL
ssl = on
ssl_ca_file = '/etc/ssl/postgresql/ilnmors_root_ca.crt'
ssl_cert_file = '/etc/ssl/postgresql/postgresql.crt'
ssl_key_file = '/etc/ssl/postgresql/postgresql.key'
ssl_ciphers = 'HIGH:!aNULL:!MD5'
ssl_prefer_server_ciphers = on
# log
log_destination = 'stderr'
log_checkpoints = on
log_temp_files = 0
log_min_duration_statement = 500
# IO
track_io_timing = on
## immich_config
shared_preload_libraries = 'vchord.so'
search_path = '"$user", public'
max_wal_size = 5GB
shared_buffers = 512MB
wal_compression = on
work_mem = 16MB
autovacuum_vacuum_scale_factor = 0.1
autovacuum_analyze_scale_factor = 0.05
autovacuum_vacuum_cost_limit = 1000
effective_io_concurrency = 200
random_page_cost = 1.2

View File

@@ -0,0 +1,36 @@
[Quadlet]
DefaultDependencies=false
[Unit]
Description=PostgreSQL
After=network-online.target
Wants=network-online.target
[Container]
Image=ilnmors.internal/{{ node['name'] }}/postgres:pg{{ version['containers']['postgresql'] }}-vectorchord{{ version['containers']['vectorchord'] }}
ContainerName=postgresql
HostName=postgresql
PublishPort=5432:5432/tcp
Volume=%h/containers/postgresql/data:/var/lib/postgresql:rw
Volume=%h/containers/postgresql/config:/config:ro
Volume=%h/containers/postgresql/ssl:/etc/ssl/postgresql:ro
Volume=%h/containers/postgresql/init:/docker-entrypoint-initdb.d/:ro
Volume=%h/containers/postgresql/backups:/backups:rw
Environment="TZ=Asia/Seoul"
# This option is only for init process, after init custom config file `pg_hba.conf` will control this option.
Environment="POSTGRES_HOST_AUTH_METHOD=trust"
Exec=postgres -c 'config_file=/config/postgresql.conf' -c 'hba_file=/config/pg_hba.conf'
[Service]
Restart=always
RestartSec=10s
TimeoutStopSec=120
[Install]
WantedBy=default.target

View File

@@ -0,0 +1,18 @@
[Unit]
Description=PostgreSQL Cluster Backup Service
After=postgresql.service
BindsTo=postgresql.service
[Service]
Type=oneshot
# logging
StandardOutput=journal
StandardError=journal
ExecStartPre=/usr/bin/podman exec postgresql sh -c "mkdir -p /backups/cluster && chown postgres:root /backups/cluster && chmod 770 /backups/cluster"
# Run the script
ExecStart=/usr/bin/podman exec -u postgres postgresql sh -c 'pg_dumpall -U postgres --schema-only | grep -v -E "CREATE ROLE postgres" > /backups/cluster/pg_cluster_$(date "+%%Y-%%m-%%d").sql'
ExecStart=/usr/bin/podman exec -u postgres postgresql sh -c "find /backups/cluster -maxdepth 1 -type f -mtime +7 -delete"
ExecStart=/usr/bin/podman exec postgresql sh -c "chown -R postgres:root /backups/cluster && chmod 660 /backups/cluster/*"

View File

@@ -0,0 +1,17 @@
[Unit]
Description=Run PostgreSQL Cluster Backup service every day
[Timer]
# Execute service after 1 min on booting
OnBootSec=1min
# Execute service every day 00:00
OnCalendar=*-*-* 00:00:00
# Random time to postpone the timer
RandomizedDelaySec=15min
# When timer is activated, Service also starts.
Persistent=true
[Install]
WantedBy=timers.target

View File

@@ -0,0 +1,19 @@
[Unit]
Description=PostgreSQL Data %i Backup Service
After=postgresql.service
BindsTo=postgresql.service
[Service]
Type=oneshot
# logging
StandardOutput=journal
StandardError=journal
ExecStartPre=/usr/bin/podman exec postgresql sh -c "mkdir -p /backups/%i && chown postgres:root /backups/%i && chmod 770 /backups/%i"
# Run the script
ExecStart=/usr/bin/podman exec -u postgres postgresql sh -c 'printf "\\connect %i_db\n" > /backups/%i/pg_%i_$(date "+%%Y-%%m-%%d").sql'
ExecStart=/usr/bin/podman exec -u postgres postgresql sh -c 'pg_dump -U postgres -d %i_db --data-only >> /backups/%i/pg_%i_$(date "+%%Y-%%m-%%d").sql'
ExecStart=/usr/bin/podman exec -u postgres postgresql sh -c "find /backups/%i -maxdepth 1 -type f -mtime +7 -delete"
ExecStart=/usr/bin/podman exec postgresql sh -c "chown -R postgres:root /backups/%i && chmod 660 /backups/%i/*"

View File

@@ -0,0 +1,17 @@
[Unit]
Description=Run %i Data Backup service every day
[Timer]
# Execute service after 1 min on booting
OnBootSec=1min
# Execute service every day 00:00
OnCalendar=*-*-* 00:00:00
# Random time to postpone the timer
RandomizedDelaySec=15min
# When timer is activated, Service also starts.
Persistent=true
[Install]
WantedBy=timers.target

View File

@@ -0,0 +1,32 @@
# my global config
global:
scrape_interval: 15s # Set the scrape interval to every 15 seconds. Default is every 1 minute.
evaluation_interval: 15s # Evaluate rules every 15 seconds. The default is every 1 minute.
# scrape_timeout is set to the global default (10s).
# Alertmanager configuration
alerting:
alertmanagers:
- static_configs:
- targets:
# - alertmanager:9093
# Load rules once and periodically evaluate them according to the global 'evaluation_interval'.
rule_files:
- "/etc/prometheus/rules.yaml"
# A scrape configuration containing exactly one endpoint to scrape:
# Here it's Prometheus itself.
scrape_configs:
# The job name is added as a label `job=<job_name>` to any timeseries scraped from this config.
- job_name: "prometheus"
# metrics_path defaults to '/metrics'
scheme: "https"
tls_config:
ca_file: "/etc/ssl/prometheus/ilnmors_root_ca.crt"
server_name: "{{ infra_uri['prometheus']['domain'] }}"
static_configs:
- targets: ["localhost:9090"]
# The label name is added as a label `label_name=<label_value>` to any timeseries scraped from this config.
labels:
instance: "{{ node['name'] }}"

View File

@@ -0,0 +1,38 @@
groups:
- name: node_exporters_heartbeat
rules:
{% for instance in ['vmm', 'fw', 'infra', 'auth', 'app'] %}
- alert: {{ instance }}_node_exporter_down
expr: |
(present_over_time(up{instance="{{ instance }}"}[5m]) or on() vector(0)) == 0
for: 30s
labels:
severity: critical
annotations:
summary: "Exporter heartbeat is down: {{ instance }}"
description: "{{ instance }} exporter is down for 5 mins"
{% endfor %}
- name: postgresql_heartbeat
rules:
- alert: Postgresql_Down
expr: |
(present_over_time(pg_up{instance="infra", job="postgres"}[5m]) or on() vector(0)) == 0
for: 30s
labels:
severity: critical
annotations:
summary: "Postgresql Heartbeat Lost: postgresql"
description: "postgresql node is down for 5 mins."
- name: Certificate_expiry_check
rules:
{% for filename in ['root.crt', 'intermediate.crt', 'crowdsec.crt', 'blocky.crt', 'postgresql.crt', 'ldap.crt', 'prometheus.crt', 'loki.crt', 'dsm.crt'] %}
- alert: {{ filename | replace('.', '_') }}_is_expired_soon
expr: |
max(x509_cert_not_after{filename="{{ filename }}"}) - time() < 2592000
for: 1d
labels:
severity: critical
annotations:
summary: "{{ filename }} is expired in 30 days"
description: "{{ filename }} is expired in 30 days."
{% endfor %}

View File

@@ -0,0 +1,9 @@
# Additionally, a certificate and a key file are needed.
tls_server_config:
cert_file: "/etc/ssl/prometheus/prometheus.crt"
key_file: "/etc/ssl/prometheus/prometheus.key"
# Passwords are hashed with bcrypt: https://github.com/prometheus/exporter-toolkit/blob/master/docs/web-configuration.md#about-bcrypt
#basic_auth_users:
# alice: $2y$10$mDwo.lAisC94iLAyP81MCesa29IzH37oigHC/42V2pdJlUprsJPze
# bob: $2y$10$hLqFl9jSjoAAy95Z/zw8Ye8wkdMBM8c5Bn1ptYqP/AXyV0.oy0S8m

View File

@@ -0,0 +1,38 @@
[Quadlet]
DefaultDependencies=false
[Unit]
Description=Prometheus
After=network-online.target
Wants=network-online.target
[Container]
Image=docker.io/prom/prometheus:{{ version['containers']['prometheus'] }}
ContainerName=prometheus
HostName=prometheus
PublishPort=9090:9090/tcp
Volume=%h/containers/prometheus/data:/prometheus:rw
Volume=%h/containers/prometheus/etc:/etc/prometheus:ro
Volume=%h/containers/prometheus/ssl:/etc/ssl/prometheus:ro
Environment="TZ=Asia/Seoul"
Exec=--config.file=/etc/prometheus/prometheus.yaml \
--web.config.file=/etc/prometheus/web-config.yaml \
--web.enable-remote-write-receiver \
--storage.tsdb.path=/prometheus \
--storage.tsdb.retention.time=30d \
--storage.tsdb.retention.size=15GB \
--storage.tsdb.wal-compression
[Service]
Restart=always
RestartSec=10s
TimeoutStopSec=120
[Install]
WantedBy=default.target

View File

@@ -0,0 +1,26 @@
[Quadlet]
DefaultDependencies=false
[Unit]
Description=x509-Exporter
After=network-online.target
Wants=network-online.target
[Container]
Image=docker.io/enix/x509-certificate-exporter:{{ version['containers']['x509-exporter'] }}
ContainerName=x509-exporter
HostName=X509-exporter
Volume=%h/containers/x509-exporter/certs:/certs:ro
PublishPort=9793:9793
Exec=--listen-address :9793 --watch-dir=/certs
[Service]
Restart=always
RestartSec=10s
TimeoutStopSec=120
[Install]
WantedBy=default.target