From 36d6be271e8c2ce1b80574203a91538e7751a787 Mon Sep 17 00:00:00 2001 From: Sergey Malyuk Date: Fri, 19 Dec 2025 12:16:06 +0300 Subject: [PATCH 1/5] add postgres1c role --- roles/postgres1c/README.md | 40 +++++++++ roles/postgres1c/defaults/main.yml | 1 + .../files/postgres1c_backup.service | 9 ++ roles/postgres1c/handlers/main.yml | 2 + roles/postgres1c/meta/main.yml | 14 +++ .../postgres1c/molecule/default/converge.yml | 10 +++ .../postgres1c/molecule/default/molecule.yml | 22 +++++ .../molecule/default/secrets/postgresql.yaml | 2 + roles/postgres1c/molecule/default/verify.yml | 58 ++++++++++++ roles/postgres1c/tasks/backup.yaml | 40 +++++++++ roles/postgres1c/tasks/main.yml | 88 +++++++++++++++++++ roles/postgres1c/templates/backup.sh.j2 | 35 ++++++++ .../templates/postgres1c_backup.timer.j2 | 12 +++ 13 files changed, 333 insertions(+) create mode 100644 roles/postgres1c/README.md create mode 100644 roles/postgres1c/defaults/main.yml create mode 100644 roles/postgres1c/files/postgres1c_backup.service create mode 100644 roles/postgres1c/handlers/main.yml create mode 100644 roles/postgres1c/meta/main.yml create mode 100644 roles/postgres1c/molecule/default/converge.yml create mode 100644 roles/postgres1c/molecule/default/molecule.yml create mode 100644 roles/postgres1c/molecule/default/secrets/postgresql.yaml create mode 100644 roles/postgres1c/molecule/default/verify.yml create mode 100644 roles/postgres1c/tasks/backup.yaml create mode 100644 roles/postgres1c/tasks/main.yml create mode 100644 roles/postgres1c/templates/backup.sh.j2 create mode 100644 roles/postgres1c/templates/postgres1c_backup.timer.j2 diff --git a/roles/postgres1c/README.md b/roles/postgres1c/README.md new file mode 100644 index 0000000..f006c5b --- /dev/null +++ b/roles/postgres1c/README.md @@ -0,0 +1,40 @@ +postgres1c +========= + +Installs postgrespro1c (https://1c.postgres.ru/) as a system service. + +Requirements +------------ + +Linux (tested on Ubuntu 22.04) + +Role Variables +-------------- + +`postgres1c_major_ver`: major version of the distribution to be installed +`postgres1c_postgres_pw`: password for user 'postgres' +`postgres1c_postgres_pw_path`: path to the (Ansible-encrypted) YAML file containing a password (see `molecule/default/secrets/`) + +Dependencies +------------ + +None + +Example Playbook +---------------- + +See `molecule/default/coverge.yaml` for an example. + +License +------- + +BSD + +Author Information +------------------ + +Danilkin Danila (MIPT) and Alexander Gorelyshev + +Genlab, LLC + +corvus-migratorius@proton.me diff --git a/roles/postgres1c/defaults/main.yml b/roles/postgres1c/defaults/main.yml new file mode 100644 index 0000000..ed97d53 --- /dev/null +++ b/roles/postgres1c/defaults/main.yml @@ -0,0 +1 @@ +--- diff --git a/roles/postgres1c/files/postgres1c_backup.service b/roles/postgres1c/files/postgres1c_backup.service new file mode 100644 index 0000000..efa8453 --- /dev/null +++ b/roles/postgres1c/files/postgres1c_backup.service @@ -0,0 +1,9 @@ +[Unit] +Description=Backup 1C script +Documentation=https://github.com/corvus-migratorius/genlab-ansible + +[Service] +User=postgres +Group=postgres +Type=oneshot +ExecStart=/bin/bash /opt/postgres1c_backup/backup.sh diff --git a/roles/postgres1c/handlers/main.yml b/roles/postgres1c/handlers/main.yml new file mode 100644 index 0000000..a7118c7 --- /dev/null +++ b/roles/postgres1c/handlers/main.yml @@ -0,0 +1,2 @@ +--- +# handlers file for oneget diff --git a/roles/postgres1c/meta/main.yml b/roles/postgres1c/meta/main.yml new file mode 100644 index 0000000..3000cb4 --- /dev/null +++ b/roles/postgres1c/meta/main.yml @@ -0,0 +1,14 @@ +--- +galaxy_info: + role_name: postgres1c + namespace: genlab + author: Danila Danilkin + description: Install PostgreSQL (1C version) as a system service + platforms: + - name: "Ubuntu" + versions: [ "jammy" ] + company: Genlab, LLC + license: BSD + min_ansible_version: "2.1" + galaxy_tags: [] +dependencies: [] diff --git a/roles/postgres1c/molecule/default/converge.yml b/roles/postgres1c/molecule/default/converge.yml new file mode 100644 index 0000000..a22500b --- /dev/null +++ b/roles/postgres1c/molecule/default/converge.yml @@ -0,0 +1,10 @@ +--- +- name: Converge + hosts: all + roles: + - role: genlab.common.postgres1c + postgres1c_version: 15 + postgres1c_postgres_pw_path: "secrets/postgresql.yaml" + postgres1c_backup_timer: "Sat *-*-* 02:00:00" + postgres1c_backup_compression: "5" + # backup enabled by default at /var/backups/postgres1c/backup_.dump diff --git a/roles/postgres1c/molecule/default/molecule.yml b/roles/postgres1c/molecule/default/molecule.yml new file mode 100644 index 0000000..a2a1072 --- /dev/null +++ b/roles/postgres1c/molecule/default/molecule.yml @@ -0,0 +1,22 @@ +--- +dependency: + name: galaxy +driver: + name: docker +platforms: + - name: ubuntu + image: geerlingguy/docker-${MOLECULE_DISTRO:-ubuntu2204}-ansible:latest + pre_build_image: true + command: ${MOLECULE_DOCKER_COMMAND:-""} + volumes: + - /sys/fs/cgroup:/sys/fs/cgroup:rw + cgroupns_mode: host + privileged: true +provisioner: + name: ansible +verifier: + name: ansible +lint: | + set -e + yamllint . + ansible-lint . diff --git a/roles/postgres1c/molecule/default/secrets/postgresql.yaml b/roles/postgres1c/molecule/default/secrets/postgresql.yaml new file mode 100644 index 0000000..976da31 --- /dev/null +++ b/roles/postgres1c/molecule/default/secrets/postgresql.yaml @@ -0,0 +1,2 @@ +--- +postgres1c_postgres_pw: 12345 diff --git a/roles/postgres1c/molecule/default/verify.yml b/roles/postgres1c/molecule/default/verify.yml new file mode 100644 index 0000000..f15af2e --- /dev/null +++ b/roles/postgres1c/molecule/default/verify.yml @@ -0,0 +1,58 @@ +--- +- name: Verify + hosts: all + gather_facts: false + tasks: + - name: "Include default role vars" + ansible.builtin.include_vars: + dir: "{{ lookup('env', 'MOLECULE_PROJECT_DIRECTORY') }}/defaults/" + extensions: [ 'yml' ] + + - name: "Get 'postgres' user password" + tags: [postgres1c] + ansible.builtin.include_vars: + file: "secrets/postgresql.yaml" + + - name: "Check that PostgreSQL server responds to the 'postgres' user credentials" + register: postgres1c__verify_db_version + community.postgresql.postgresql_info: + login_host: localhost + login_user: postgres + login_password: "{{ postgres1c_postgres_pw }}" + filter: "version" + + - name: "Verify that correct PostgreSQL version is installed" + ansible.builtin.assert: + that: postgres1c__verify_db_version.version.major == postgres1c_major_ver + success_msg: > + Detected expected PostgreSQL version + '{{ postgres1c__verify_db_version.version.major }}' + ({{ postgres1c__verify_db_version.version }})" + fail_msg: > + Expected PostgreSQL version '{{ postgres1c_major_ver }}'; + Actual '{{ postgres1c__verify_db_version.version.major }}' + ({{ postgres1c__verify_db_version.version.major }})" + + - name: Start service postgrespro-1c (i.e. do nothing and throw fail if it start) + ansible.builtin.service: + name: "postgrespro-1c-{{ postgres1c_version }}" + state: started + register: start_postgrespro1c + failed_when: start_postgrespro1c.changed + + - name: Create a new database with name "test" + tags: [postgres1c] + become: true + become_user: postgres + community.postgresql.postgresql_db: + name: test + comment: "test-db" + login_unix_socket: "/tmp" + + - name: Test backup without cron + tags: [postgres1c] + become: true + become_user: postgres + ansible.builtin.command: /opt/postgres1c_backup/backup.sh + args: + creates: /var/backups/postgres1c/backup_test.tar diff --git a/roles/postgres1c/tasks/backup.yaml b/roles/postgres1c/tasks/backup.yaml new file mode 100644 index 0000000..c004932 --- /dev/null +++ b/roles/postgres1c/tasks/backup.yaml @@ -0,0 +1,40 @@ +- name: "Create opt script directory and backup directory" + ansible.builtin.file: + path: "{{ item }}" + state: directory + owner: postgres + group: postgres + mode: "0770" + loop: + - "/var/backups/postgres1c" + - "/opt/postgres1c_backup" + +- name: "Copy backup script" + ansible.builtin.template: + src: "backup.sh.j2" + dest: "/opt/postgres1c_backup/backup.sh" + owner: postgres + group: postgres + mode: "0770" + +- name: "Copy backup service" + ansible.builtin.copy: + src: "postgres1c_backup.service" + dest: "/etc/systemd/system/" + owner: root + group: root + mode: "0770" + +- name: "Copy backup timer" + ansible.builtin.template: + src: "postgres1c_backup.timer.j2" + dest: "/etc/systemd/system/postgres1c_backup.timer" + owner: root + group: root + mode: "0770" + +- name: "Start backup timer" + ansible.builtin.systemd_service: + name: "postgres1c_backup.timer" + state: started + enabled: true diff --git a/roles/postgres1c/tasks/main.yml b/roles/postgres1c/tasks/main.yml new file mode 100644 index 0000000..6f12c2a --- /dev/null +++ b/roles/postgres1c/tasks/main.yml @@ -0,0 +1,88 @@ +--- +- name: "Ensure ACL is installed" + tags: [postgres1c] + ansible.builtin.apt: + name: acl + state: present + update_cache: true + cache_valid_time: 3600 + +- name: "Install PostgreSQL distribution for 1C" + tags: [postgres1c] + block: + - name: "Сheck if already installed" + tags: [postgres1c] + check_mode: true + ansible.builtin.package: + name: "postgrespro-1c-{{ postgres1c_version }}-contrib" + state: present + + rescue: + - name: "Download the offical postgrespro1c installation script" + tags: [postgres1c] + ansible.builtin.get_url: + url: "https://repo.postgrespro.ru/1c/1c-{{ postgres1c_version }}/keys/pgpro-repo-add.sh" + dest: "/root/pgpro-repo-add.sh" + mode: '0755' + + - name: "Add repos using the installation script" + tags: [postgres1c] + changed_when: false + ansible.builtin.command: + cmd: "/root/pgpro-repo-add.sh" + + - name: "Install the 'postgrespro1c' package (and force apt update)" + tags: [postgres1c] + ansible.builtin.apt: + name: "postgrespro-1c-{{ postgres1c_version }}-contrib" + state: present + update_cache: true # we just added new repo, so we need to apt update + + - name: "Ensure the 'ru_RU.UTF-8' locale exists" + tags: [postgres1c] + community.general.locale_gen: + name: ru_RU.UTF-8 + state: present + + - name: "Run initdb" + tags: [postgres1c] + changed_when: false + ansible.builtin.command: + cmd: "/opt/pgpro/1c-{{ postgres1c_version }}/bin/pg-setup initdb --locale ru_RU.UTF-8" + + - name: "Enable postgrespro1c service" + tags: [postgres1c] + changed_when: false + ansible.builtin.command: + cmd: "/opt/pgpro/1c-{{ postgres1c_version }}/bin/pg-setup service enable" + + - name: "Start postgrespro1c service" + tags: [postgres1c] + changed_when: false + ansible.builtin.command: + cmd: "/opt/pgpro/1c-{{ postgres1c_version }}/bin/pg-setup service start" + +- name: "Install psycopg2 (to connect to postgres)" + tags: [postgres1c] + ansible.builtin.package: + name: "python3-psycopg2" + state: present + +- name: "Get 'postgres' user password" + tags: [postgres1c] + ansible.builtin.include_vars: + file: "{{ postgres1c_postgres_pw_path }}" + +- name: "Set password for user 'postgres' via the Unix socket" + tags: [postgres1c] + become: true + become_user: postgres + community.postgresql.postgresql_user: + db: "postgres" + name: "postgres" + password: "{{ postgres1c_postgres_pw }}" + login_unix_socket: "/tmp" + +- name: "Create local postgres1c backup with systemd-timer" + tags: [postgres1c, postgres1c-backup] + ansible.builtin.include_tasks: backup.yaml diff --git a/roles/postgres1c/templates/backup.sh.j2 b/roles/postgres1c/templates/backup.sh.j2 new file mode 100644 index 0000000..6e6e2bb --- /dev/null +++ b/roles/postgres1c/templates/backup.sh.j2 @@ -0,0 +1,35 @@ +#!/bin/bash + +set -eu -o pipefail + +readonly POSTGRES_VER={{ postgres1c_version }} +readonly POSTGRES_COMPRESS={{ postgres1c_backup_compression }} + +echo "Starting 1C backup at $(date +F'%Y-%m-%d %H:%M:%S')" + +# db list array +echo "getting a list of database names via psql ..." +databases=($(/opt/pgpro/1c-${POSTGRES_VER}/bin/psql -t -A -c "SELECT datname FROM pg_database WHERE datname <> ALL ('{template0,template1,postgres}')")) +echo "database names: ${databases[@]}" + +# get current seconds since shell invocation +start_time=$SECONDS + +# iterate over the db list array +for db in "${databases[@]}"; do + start_one_time=$SECONDS + echo "${db} - backup started" + + # local backup command (don't forget to sync to a remote server by borg or some other tool) + # -Fc: "custom format" https://www.postgresql.org/docs/current/app-pgdump.html + # -Z: compression + /opt/pgpro/1c-${POSTGRES_VER}/bin/pg_dump -d ${db} -Fc -Z ${POSTGRES_COMPRESS} -f /var/backups/postgres1c/backup_${db}.dump + + # notify about the db dump completion + echo "${db} - backup done" + total_one_time=$(($SECONDS - start_one_time)) + echo "${db} - total time: ${total_one_time} sec" +done + +total_time=$(($SECONDS - start_time)) +echo "job completed at $(date); total time elapsed: ${total_time} sec" diff --git a/roles/postgres1c/templates/postgres1c_backup.timer.j2 b/roles/postgres1c/templates/postgres1c_backup.timer.j2 new file mode 100644 index 0000000..b8329f0 --- /dev/null +++ b/roles/postgres1c/templates/postgres1c_backup.timer.j2 @@ -0,0 +1,12 @@ +[Unit] +Description=Run backup 1C script. +Documentation=https://github.com/corvus-migratorius/genlab-ansible + +[Timer] +Unit=postgres1c_backup.service +OnCalendar={{ postgres1c_backup_timer }} +Persistent=true +AccuracySec=1min + +[Install] +WantedBy=timers.target From 4f3d092511f3c33821bbbeb97a33b75ce407dcd3 Mon Sep 17 00:00:00 2001 From: Sergey Malyuk Date: Fri, 19 Dec 2025 12:31:40 +0300 Subject: [PATCH 2/5] fix role and ansible-lint errors --- roles/postgres1c/meta/main.yml | 2 +- roles/postgres1c/molecule/default/verify.yml | 9 ++++++--- 2 files changed, 7 insertions(+), 4 deletions(-) diff --git a/roles/postgres1c/meta/main.yml b/roles/postgres1c/meta/main.yml index 3000cb4..b69744e 100644 --- a/roles/postgres1c/meta/main.yml +++ b/roles/postgres1c/meta/main.yml @@ -6,7 +6,7 @@ galaxy_info: description: Install PostgreSQL (1C version) as a system service platforms: - name: "Ubuntu" - versions: [ "jammy" ] + versions: ["jammy", "noble"] company: Genlab, LLC license: BSD min_ansible_version: "2.1" diff --git a/roles/postgres1c/molecule/default/verify.yml b/roles/postgres1c/molecule/default/verify.yml index f15af2e..c72a98c 100644 --- a/roles/postgres1c/molecule/default/verify.yml +++ b/roles/postgres1c/molecule/default/verify.yml @@ -2,11 +2,14 @@ - name: Verify hosts: all gather_facts: false + vars: + postgres1c_major_ver: 15 + postgres1c_version: 15 tasks: - name: "Include default role vars" ansible.builtin.include_vars: dir: "{{ lookup('env', 'MOLECULE_PROJECT_DIRECTORY') }}/defaults/" - extensions: [ 'yml' ] + extensions: ['yml'] - name: "Get 'postgres' user password" tags: [postgres1c] @@ -37,8 +40,8 @@ ansible.builtin.service: name: "postgrespro-1c-{{ postgres1c_version }}" state: started - register: start_postgrespro1c - failed_when: start_postgrespro1c.changed + register: postgres1c_start_postgrespro1c + failed_when: postgres1c_start_postgrespro1c.changed - name: Create a new database with name "test" tags: [postgres1c] From c1bcb9c3e89de8bb7fb9e5f0a1a77123030d8aee Mon Sep 17 00:00:00 2001 From: Sergey Malyuk Date: Fri, 19 Dec 2025 12:32:54 +0300 Subject: [PATCH 3/5] update meta --- README.md | 1 + galaxy.yml | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index 756cd56..dd72194 100644 --- a/README.md +++ b/README.md @@ -21,6 +21,7 @@ - [nginx](roles/nginx/README.md) - [nginx_docker](roles/nginx_docker/README.md) - [node_exporter](roles/node_exporter/README.md) +- [postgres1c](roles/postgres1c/README.md) - [prometheus](roles/prometheus/README.md) - [promtail](roles/promtail/README.md) - [rclone_yandex](roles/rclone_yandex/README.md) diff --git a/galaxy.yml b/galaxy.yml index a800451..a948bd5 100644 --- a/galaxy.yml +++ b/galaxy.yml @@ -1,7 +1,7 @@ --- namespace: genlab name: common -version: 0.29.0 +version: 0.30.0 readme: README.md authors: - Alexander Gorelyshev (corvus-migratorius@proton.me) From f1737698e8b8161e2dea216271ad300cbc3f3d35 Mon Sep 17 00:00:00 2001 From: Sergey Malyuk Date: Fri, 19 Dec 2025 12:39:43 +0300 Subject: [PATCH 4/5] update dependencies --- requirements.yml | 2 ++ roles/postgres1c/README.md | 2 +- 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/requirements.yml b/requirements.yml index 7cac208..94b4b69 100644 --- a/requirements.yml +++ b/requirements.yml @@ -7,3 +7,5 @@ collections: - name: community.crypto - name: maxhoesel.borgbackup - name: lucasheld.uptime_kuma + - name: community.postgresql + diff --git a/roles/postgres1c/README.md b/roles/postgres1c/README.md index f006c5b..c3e5177 100644 --- a/roles/postgres1c/README.md +++ b/roles/postgres1c/README.md @@ -18,7 +18,7 @@ Role Variables Dependencies ------------ -None +- community.postgresql Example Playbook ---------------- From c702c7ee464a88431adfdef86288178938aa3733 Mon Sep 17 00:00:00 2001 From: Sergey Malyuk Date: Fri, 19 Dec 2025 12:43:11 +0300 Subject: [PATCH 5/5] fix ansible-lint error --- requirements.yml | 1 - 1 file changed, 1 deletion(-) diff --git a/requirements.yml b/requirements.yml index 94b4b69..ce80faa 100644 --- a/requirements.yml +++ b/requirements.yml @@ -8,4 +8,3 @@ collections: - name: maxhoesel.borgbackup - name: lucasheld.uptime_kuma - name: community.postgresql -