feat: 声明 sandbox 双节点 K3s 集群
This commit is contained in:
@@ -0,0 +1,50 @@
|
||||
---
|
||||
- name: Validate sandbox PostgreSQL inputs
|
||||
ansible.builtin.assert:
|
||||
that:
|
||||
- sandbox_postgresql_k3s_password | length >= 32
|
||||
- sandbox_postgresql_replication_password | length >= 32
|
||||
- inventory_hostname in groups['postgres_primary'] or inventory_hostname in groups['postgres_standby']
|
||||
fail_msg: Missing Bao-provided PostgreSQL credentials or invalid inventory role
|
||||
no_log: true
|
||||
|
||||
- name: Install PostgreSQL packages
|
||||
ansible.builtin.apt:
|
||||
name:
|
||||
- postgresql-{{ sandbox_postgresql_version }}
|
||||
- postgresql-client-{{ sandbox_postgresql_version }}
|
||||
- python3-psycopg2
|
||||
state: present
|
||||
update_cache: true
|
||||
cache_valid_time: 3600
|
||||
|
||||
- name: Check whether synchronous replication has completed bootstrap
|
||||
ansible.builtin.stat:
|
||||
path: /etc/postgresql/{{ sandbox_postgresql_version }}/main/sandbox-synchronous-ready
|
||||
register: sandbox_postgresql_synchronous_marker
|
||||
|
||||
- name: Install sandbox PostgreSQL access policy
|
||||
ansible.builtin.template:
|
||||
src: pg_hba.conf.j2
|
||||
dest: /etc/postgresql/{{ sandbox_postgresql_version }}/main/pg_hba.conf
|
||||
owner: postgres
|
||||
group: postgres
|
||||
mode: "0640"
|
||||
notify: Restart sandbox PostgreSQL
|
||||
|
||||
- name: Install sandbox PostgreSQL server settings
|
||||
ansible.builtin.template:
|
||||
src: sandbox.conf.j2
|
||||
dest: /etc/postgresql/{{ sandbox_postgresql_version }}/main/conf.d/99-sandbox.conf
|
||||
owner: postgres
|
||||
group: postgres
|
||||
mode: "0644"
|
||||
notify: Restart sandbox PostgreSQL
|
||||
|
||||
- name: Configure sandbox PostgreSQL primary
|
||||
ansible.builtin.include_tasks: primary.yml
|
||||
when: inventory_hostname in groups['postgres_primary']
|
||||
|
||||
- name: Configure sandbox PostgreSQL standby
|
||||
ansible.builtin.include_tasks: standby.yml
|
||||
when: inventory_hostname in groups['postgres_standby']
|
||||
@@ -0,0 +1,45 @@
|
||||
---
|
||||
- name: Apply primary PostgreSQL configuration before replication setup
|
||||
ansible.builtin.meta: flush_handlers
|
||||
|
||||
- name: Create K3s PostgreSQL login role
|
||||
community.postgresql.postgresql_user:
|
||||
name: "{{ sandbox_postgresql_user }}"
|
||||
password: "{{ sandbox_postgresql_k3s_password }}"
|
||||
no_password_changes: "{{ not sandbox_postgresql_rotate_passwords }}"
|
||||
role_attr_flags: LOGIN,NOSUPERUSER,NOCREATEDB,NOCREATEROLE,NOREPLICATION
|
||||
state: present
|
||||
become: true
|
||||
become_user: postgres
|
||||
no_log: true
|
||||
environment:
|
||||
PGOPTIONS: -c password_encryption=scram-sha-256
|
||||
|
||||
- name: Create K3s PostgreSQL database
|
||||
community.postgresql.postgresql_db:
|
||||
name: "{{ sandbox_postgresql_database }}"
|
||||
owner: "{{ sandbox_postgresql_user }}"
|
||||
state: present
|
||||
become: true
|
||||
become_user: postgres
|
||||
|
||||
- name: Create PostgreSQL replication login role
|
||||
community.postgresql.postgresql_user:
|
||||
name: "{{ sandbox_postgresql_replication_user }}"
|
||||
password: "{{ sandbox_postgresql_replication_password }}"
|
||||
no_password_changes: "{{ not sandbox_postgresql_rotate_passwords }}"
|
||||
role_attr_flags: LOGIN,REPLICATION,NOSUPERUSER,NOCREATEDB,NOCREATEROLE
|
||||
state: present
|
||||
become: true
|
||||
become_user: postgres
|
||||
no_log: true
|
||||
environment:
|
||||
PGOPTIONS: -c password_encryption=scram-sha-256
|
||||
|
||||
- name: Create physical replication slot for sandbox2
|
||||
community.postgresql.postgresql_slot:
|
||||
name: "{{ sandbox_postgresql_replication_slot }}"
|
||||
slot_type: physical
|
||||
state: present
|
||||
become: true
|
||||
become_user: postgres
|
||||
@@ -0,0 +1,114 @@
|
||||
---
|
||||
- name: Detect whether sandbox2 is already a standby
|
||||
community.postgresql.postgresql_query:
|
||||
login_db: postgres
|
||||
query: SELECT pg_is_in_recovery() AS in_recovery
|
||||
become: true
|
||||
become_user: postgres
|
||||
register: sandbox_postgresql_recovery_state
|
||||
|
||||
- name: Inspect databases before the initial standby seed
|
||||
community.postgresql.postgresql_query:
|
||||
login_db: postgres
|
||||
query: >-
|
||||
SELECT datname FROM pg_database
|
||||
WHERE NOT datistemplate AND datname <> 'postgres'
|
||||
become: true
|
||||
become_user: postgres
|
||||
register: sandbox_postgresql_existing_databases
|
||||
when: not sandbox_postgresql_recovery_state.query_result[0].in_recovery
|
||||
|
||||
- name: Refuse to overwrite a non-empty PostgreSQL node
|
||||
ansible.builtin.assert:
|
||||
that:
|
||||
- sandbox_postgresql_existing_databases.query_result | length == 0
|
||||
fail_msg: Refusing to reseed sandbox2 because it contains non-system databases
|
||||
when: not sandbox_postgresql_recovery_state.query_result[0].in_recovery
|
||||
|
||||
- name: Stop PostgreSQL before the initial standby seed
|
||||
ansible.builtin.service:
|
||||
name: postgresql
|
||||
state: stopped
|
||||
when: not sandbox_postgresql_recovery_state.query_result[0].in_recovery
|
||||
|
||||
- name: Remove the verified-empty standby data directory
|
||||
ansible.builtin.file:
|
||||
path: /var/lib/postgresql/{{ sandbox_postgresql_version }}/main
|
||||
state: absent
|
||||
when: not sandbox_postgresql_recovery_state.query_result[0].in_recovery
|
||||
|
||||
- name: Recreate the standby data directory
|
||||
ansible.builtin.file:
|
||||
path: /var/lib/postgresql/{{ sandbox_postgresql_version }}/main
|
||||
state: directory
|
||||
owner: postgres
|
||||
group: postgres
|
||||
mode: "0700"
|
||||
when: not sandbox_postgresql_recovery_state.query_result[0].in_recovery
|
||||
|
||||
- name: Install standby replication password file
|
||||
ansible.builtin.copy:
|
||||
dest: /var/lib/postgresql/.pgpass
|
||||
content: >-
|
||||
{{ sandbox_postgresql_primary_address }}:5432:*:{{ sandbox_postgresql_replication_user }}:{{ sandbox_postgresql_replication_password }}
|
||||
owner: postgres
|
||||
group: postgres
|
||||
mode: "0600"
|
||||
no_log: true
|
||||
|
||||
- name: Seed sandbox2 from the PostgreSQL primary
|
||||
ansible.builtin.command:
|
||||
argv:
|
||||
- /usr/bin/pg_basebackup
|
||||
- --host={{ sandbox_postgresql_primary_address }}
|
||||
- --username={{ sandbox_postgresql_replication_user }}
|
||||
- --pgdata=/var/lib/postgresql/{{ sandbox_postgresql_version }}/main
|
||||
- --format=plain
|
||||
- --wal-method=stream
|
||||
- --write-recovery-conf
|
||||
- --slot={{ sandbox_postgresql_replication_slot }}
|
||||
become: true
|
||||
become_user: postgres
|
||||
environment:
|
||||
PGPASSFILE: /var/lib/postgresql/.pgpass
|
||||
when: not sandbox_postgresql_recovery_state.query_result[0].in_recovery
|
||||
no_log: true
|
||||
|
||||
- name: Set the standby connection identity
|
||||
ansible.builtin.lineinfile:
|
||||
path: /var/lib/postgresql/{{ sandbox_postgresql_version }}/main/postgresql.auto.conf
|
||||
regexp: ^primary_conninfo =
|
||||
line: >-
|
||||
primary_conninfo = 'host={{ sandbox_postgresql_primary_address }} port=5432
|
||||
user={{ sandbox_postgresql_replication_user }} application_name=sandbox2
|
||||
passfile=/var/lib/postgresql/.pgpass'
|
||||
owner: postgres
|
||||
group: postgres
|
||||
mode: "0600"
|
||||
no_log: true
|
||||
|
||||
- name: Start PostgreSQL standby
|
||||
ansible.builtin.service:
|
||||
name: postgresql
|
||||
enabled: true
|
||||
state: started
|
||||
|
||||
- name: Wait for sandbox2 to enter recovery
|
||||
community.postgresql.postgresql_query:
|
||||
login_db: postgres
|
||||
query: SELECT pg_is_in_recovery() AS in_recovery
|
||||
become: true
|
||||
become_user: postgres
|
||||
register: sandbox_postgresql_standby_ready
|
||||
retries: 12
|
||||
delay: 5
|
||||
until: sandbox_postgresql_standby_ready.query_result[0].in_recovery
|
||||
|
||||
- name: Mark synchronous replication bootstrap complete on the primary
|
||||
ansible.builtin.copy:
|
||||
dest: /etc/postgresql/{{ sandbox_postgresql_version }}/main/sandbox-synchronous-ready
|
||||
content: "sandbox2\n"
|
||||
owner: postgres
|
||||
group: postgres
|
||||
mode: "0644"
|
||||
delegate_to: "{{ groups['postgres_primary'][0] }}"
|
||||
Reference in New Issue
Block a user