5776dbe1bf
ups role: NUT server on home.debyl.io for the CyberPower PR1500RT2U that backs both it and truenas.localdomain, with staged shutdown (TrueNAS sheds at t+2min, host at 10% charge) and best-effort IPMI power-on when mains returns. The 10% threshold leans on ignorelb + override.battery.charge.low rather than a custom poller, because CyberPower asserts its own low-battery flag far too early. Credentials come from vault vars; nothing sensitive is templated in the clear. Nextcloud background jobs: both instances have backgroundjobs_mode "cron", which expects an external caller every ~5 minutes, and nothing was calling. The personal instance had not run a background job since 2026-05-14 and skudak since 2024-11-20. Consequently trash and file versions never expired, stale chunked uploads accumulated, calendar reminders never fired, and nextcloud.log was never rotated -- which quietly made the existing log_rotate_size cap inert. Added a systemd timer per instance, skipping cleanly when the container is down or in maintenance so deploy windows don't show up as failed units. Trash retention on the personal instance: the default "auto" only expires when disk space demands it, so 66 GB of >30-day deletions sat on a host with 1.3 TB free -- effectively unbounded. "auto, 30" makes the 30-day expiry unconditional while still purging early under pressure. Image bumps: nextcloud 33.0.0 -> 34.0.2 (both cloud and skudak-cloud) greg-time-bot 3.9.25 -> 3.10.0 fulfillr 20260723.2044 -> 20260728.2155 (prod and dev) The fulfillr bump records what is already deployed: both containers were rolled to that image on 2026-07-29 for SCRUM-156 (digital product releases + customer update campaign). Committing it keeps the repo from claiming an older tag than the host is actually running, which would otherwise roll fulfillr backwards on the next clean-checkout deploy. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
181 lines
6.2 KiB
YAML
181 lines
6.2 KiB
YAML
---
|
|
- name: create required skudak cloud volumes
|
|
become: true
|
|
ansible.builtin.file:
|
|
path: "{{ item }}"
|
|
state: directory
|
|
owner: "{{ podman_subuid.stdout }}"
|
|
group: "{{ podman_subuid.stdout }}"
|
|
mode: 0755
|
|
notify: restorecon podman
|
|
loop:
|
|
- "{{ cloud_skudak_path }}/apps"
|
|
- "{{ cloud_skudak_path }}/config"
|
|
- "{{ cloud_skudak_path }}/data"
|
|
- "{{ cloud_skudak_path }}/mysql"
|
|
- "{{ cloud_skudak_path }}/scripts"
|
|
|
|
- name: unshare chown the skudak cloud volumes
|
|
become: true
|
|
become_user: "{{ podman_user }}"
|
|
changed_when: false
|
|
ansible.builtin.command: |
|
|
podman unshare chown -R 33:33 {{ cloud_skudak_path }}/apps {{ cloud_skudak_path }}/data {{ cloud_skudak_path}}/config
|
|
|
|
- name: flush handlers
|
|
ansible.builtin.meta: flush_handlers
|
|
|
|
- name: copy skudak cloud libresign setup script
|
|
become: true
|
|
ansible.builtin.template:
|
|
src: nextcloud/libresign-setup.sh.j2
|
|
dest: "{{ cloud_skudak_path }}/scripts/libresign-setup.sh"
|
|
owner: "{{ podman_subuid.stdout }}"
|
|
group: "{{ podman_subuid.stdout }}"
|
|
mode: 0755
|
|
notify: restorecon podman
|
|
|
|
- import_tasks: podman/podman-check.yml
|
|
vars:
|
|
container_name: skudak-cloud-db
|
|
container_image: "{{ db_image }}"
|
|
|
|
- name: create skudak-cloud-db container
|
|
become: true
|
|
become_user: "{{ podman_user }}"
|
|
containers.podman.podman_container:
|
|
name: skudak-cloud-db
|
|
image: "{{ db_image }}"
|
|
restart_policy: on-failure:3
|
|
log_driver: journald
|
|
network:
|
|
- shared
|
|
env:
|
|
MYSQL_ROOT_PASSWORD: "{{ cloud_skudak_db_root_pass }}"
|
|
MYSQL_DATABASE: skucloud
|
|
MYSQL_PASSWORD: "{{ cloud_skudak_db_pass }}"
|
|
MYSQL_USER: skucloud
|
|
volumes:
|
|
- "{{ cloud_skudak_path }}/mysql:/var/lib/mysql"
|
|
|
|
- name: create systemd startup job for skudak-cloud-db
|
|
include_tasks: podman/systemd-generate.yml
|
|
vars:
|
|
container_name: skudak-cloud-db
|
|
|
|
- import_tasks: podman/podman-check.yml
|
|
vars:
|
|
container_name: skudak-cloud
|
|
container_image: "{{ image }}"
|
|
|
|
- name: create skudak cloud container
|
|
become: true
|
|
become_user: "{{ podman_user }}"
|
|
containers.podman.podman_container:
|
|
name: skudak-cloud
|
|
image: "{{ image }}"
|
|
restart_policy: on-failure:3
|
|
log_driver: journald
|
|
network:
|
|
- shared
|
|
env:
|
|
MYSQL_PASSWORD: "{{ cloud_skudak_db_pass }}"
|
|
MYSQL_DATABASE: skucloud
|
|
MYSQL_HOST: skudak-cloud-db
|
|
MYSQL_USER: skucloud
|
|
volumes:
|
|
- "{{ cloud_skudak_path }}/apps:/var/www/html/custom_apps"
|
|
- "{{ cloud_skudak_path }}/data:/var/www/html/data"
|
|
- "{{ cloud_skudak_path }}/config:/var/www/html/config"
|
|
- "{{ cloud_skudak_path }}/scripts/libresign-setup.sh:/docker-entrypoint-hooks.d/before-starting/libresign-setup.sh:ro"
|
|
ports:
|
|
- "8090:80"
|
|
|
|
- name: create systemd startup job for cloud
|
|
include_tasks: podman/systemd-generate.yml
|
|
vars:
|
|
container_name: skudak-cloud
|
|
|
|
# Install poppler-utils for pdfsig/pdfinfo (LibreSign handles java/pdftk/jsignpdf via occ)
|
|
# This needs to be reinstalled on each container recreation
|
|
- name: install poppler-utils in skudak-cloud
|
|
become: true
|
|
become_user: "{{ podman_user }}"
|
|
ansible.builtin.command:
|
|
cmd: >
|
|
podman exec -u 0 skudak-cloud
|
|
sh -c "apt-get update && apt-get install -y --no-install-recommends
|
|
poppler-utils && rm -rf /var/lib/apt/lists/*"
|
|
register: poppler_install
|
|
changed_when: "'is already the newest version' not in poppler_install.stdout"
|
|
failed_when: false
|
|
|
|
- name: disable nextcloud signup link in config
|
|
become: true
|
|
ansible.builtin.lineinfile:
|
|
path: "{{ cloud_skudak_path }}/config/config.php"
|
|
regexp: "^\\s*'simpleSignUpLink\\.shown'\\s*=>"
|
|
line: " 'simpleSignUpLink.shown' => false,"
|
|
insertbefore: '^\);'
|
|
create: false
|
|
failed_when: false
|
|
|
|
# Add cloud.skudak.com to Nextcloud trusted_domains
|
|
- name: add cloud.skudak.com to nextcloud trusted_domains
|
|
become: true
|
|
become_user: "{{ podman_user }}"
|
|
ansible.builtin.command: >
|
|
podman exec -u www-data skudak-cloud
|
|
php occ config:system:set trusted_domains 1 --value="cloud.skudak.com"
|
|
register: trusted_domain_result
|
|
changed_when: "'System config value trusted_domains' in trusted_domain_result.stdout"
|
|
failed_when: false
|
|
|
|
# This instance was left at loglevel 0 (DEBUG) and had written a 64 GB
|
|
# nextcloud.log, almost entirely repeated deprecation notices. 2 = Warning,
|
|
# which is both the Nextcloud default and what the home instance already uses.
|
|
- name: set nextcloud loglevel for skudak-cloud
|
|
become: true
|
|
become_user: "{{ podman_user }}"
|
|
ansible.builtin.command: >
|
|
podman exec -u www-data skudak-cloud
|
|
php occ config:system:set loglevel --value 2 --type integer
|
|
register: skudak_loglevel
|
|
changed_when: "'System config value loglevel' in skudak_loglevel.stdout"
|
|
failed_when: false
|
|
|
|
# Unbounded by default; see the equivalent task in containers/home/cloud.yml.
|
|
- name: cap nextcloud log rotation size for skudak-cloud
|
|
become: true
|
|
become_user: "{{ podman_user }}"
|
|
ansible.builtin.command: >
|
|
podman exec -u www-data skudak-cloud
|
|
php occ config:system:set log_rotate_size --value 10485760 --type integer
|
|
register: skudak_log_rotate
|
|
changed_when: "'System config value log_rotate_size' in skudak_log_rotate.stdout"
|
|
failed_when: false
|
|
|
|
- include_tasks: containers/cloud-cron.yml
|
|
vars:
|
|
cron_name: skudak-cloud
|
|
cron_container: skudak-cloud
|
|
cron_script_path: /usr/local/bin/skudak-cloud-cron.sh
|
|
|
|
- include_tasks: containers/cloud-backup.yml
|
|
vars:
|
|
backup_name: skudak-cloud
|
|
data_path: "{{ cloud_skudak_path }}/data"
|
|
config_path: "{{ cloud_skudak_path }}/config"
|
|
db_container: skudak-cloud-db
|
|
ssh_key_path: /etc/ssh/backup_keys/skudak-cloud
|
|
ssh_key_content: "{{ cloud_skudak_backup_ssh_key }}"
|
|
ssh_user: skucloud
|
|
remote_path: /mnt/glacier/skudakcloud
|
|
script_path: /usr/local/bin/skudak-cloud-backup.sh
|
|
# skudakcloud/data is mode 770, so the receiving side needs traversable
|
|
# dirs. This flag was hand-added on the host and was being silently
|
|
# reverted by every `make deploy TAGS=skudak-cloud`; it now lives in git.
|
|
backup_rsync_extra_args: "--chmod=Du=rwx,Dgo=rx"
|
|
# Staggered so both instances finish before the 05:00 TrueNAS snapshot.
|
|
backup_oncalendar: "*-*-* 04:30:00"
|