From 41e55585d32cd889962c74aedf92533cbebdb39f Mon Sep 17 00:00:00 2001 From: josep-tecnativa Date: Thu, 28 Nov 2024 16:41:51 +0100 Subject: [PATCH 1/3] [ADD] HBA_EXTRA_RULES support to allow custom pg_hba.conf rules --- Dockerfile | 3 ++- README.md | 13 +++++++++++++ autoconf-entrypoint | 19 +++++++++++++++++++ 3 files changed, 34 insertions(+), 1 deletion(-) diff --git a/Dockerfile b/Dockerfile index 209a1ea..08b305e 100644 --- a/Dockerfile +++ b/Dockerfile @@ -15,7 +15,8 @@ ENV CERTS="{}" \ WAN_DATABASES='["all"]' \ WAN_HBA_TPL="{connection} {db} {user} {cidr} {meth}" \ WAN_TLS=1 \ - WAN_USERS='["all"]' + WAN_USERS='["all"]' \ + HBA_EXTRA_RULES="" RUN apk add --no-cache python3 \ && mkdir -p /etc/postgres \ && chmod a=rwx /etc/postgres diff --git a/README.md b/README.md index 8aac63c..ba467bc 100644 --- a/README.md +++ b/README.md @@ -105,4 +105,17 @@ Wether to enable or not TLS in WAN connections. Users allowed to connect from WAN. +#### `HBA_EXTRA_RULES` + +JSON array of additional pg_hba.conf rules to append. Each array element should be a string representing a valid pg_hba.conf line. + +Example HBA_EXTRA_RULES format in an .env file: + +HBA_EXTRA_RULES=["host all all 192.168.1.0/24 md5", "hostssl mydb myuser 10.0.0.0/8 scram-sha-256"] + +This adds the following lines to pg_hba.conf: + +host all all 192.168.1.0/24 md5 +hostssl mydb myuser 10.0.0.0/8 scram-sha-256 + [`Dockerfile`]: https://github.com/Tecnativa/docker-postgres-autoconf/blob/master/Dockerfile diff --git a/autoconf-entrypoint b/autoconf-entrypoint index cbb8b49..710526f 100755 --- a/autoconf-entrypoint +++ b/autoconf-entrypoint @@ -33,6 +33,7 @@ WAN_USERS = json.loads(os.environ["WAN_USERS"]) PGSSLCERT = os.environ.get("PGSSLCERT") PGSSLKEY = os.environ.get("PGSSLKEY") PGSSLROOTCERT = os.environ.get("PGSSLROOTCERT") +HBA_EXTRA_RULES = os.environ.get("HBA_EXTRA_RULES", "") # Configuration file templates CONF_FOLDER = "/etc/postgres" @@ -86,6 +87,17 @@ for filen in (PGSSLCERT, PGSSLKEY, PGSSLROOTCERT): if ssl_conf: ssl_conf.append("ssl = on") +# Parse extra rules for pg_hba.conf +extra_hba_rules = [] +if HBA_EXTRA_RULES: + try: + extra_hba_rules = json.loads(HBA_EXTRA_RULES) + if not isinstance(extra_hba_rules, list): + raise ValueError("HBA_EXTRA_RULES must be a JSON array") + except json.JSONDecodeError: + print("Invalid JSON in HBA_EXTRA_RULES", file=sys.stderr) + sys.exit(1) + # Generate LAN auth configuration for interface in netifaces.interfaces(): for type_, addresses in netifaces.ifaddresses(interface).items(): @@ -123,6 +135,13 @@ if WAN_CONNECTION != "hostssl" or ssl_conf: ) ) +# Append extra rules to hba_conf +for rule in extra_hba_rules: + if not isinstance(rule, str): + print("Each rule in HBA_EXTRA_RULES must be a string", file=sys.stderr) + sys.exit(1) + hba_conf.append(rule) + # Write postgres configuration files with open(CONF_FILE, "w") as conf_file: conf_file.write( From 80ddfb7c6815395083b8170f7fdd397cd56a97b0 Mon Sep 17 00:00:00 2001 From: josep-tecnativa Date: Thu, 28 Nov 2024 16:49:27 +0100 Subject: [PATCH 2/3] [ADD] Tests to check if new feature works --- tests/test.py | 42 ++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 42 insertions(+) diff --git a/tests/test.py b/tests/test.py index f43ff18..4ab52a8 100755 --- a/tests/test.py +++ b/tests/test.py @@ -299,6 +299,48 @@ def test_certs_falsy_lan(self): with self.assertRaises(ProcessExecutionError): self._check_password_auth("example.localdomain") + def test_hba_extra_rules_added(self): + """Test that HBA_EXTRA_RULES lines are added to pg_hba.conf.""" + if "9.6" in self.image: + self.skipTest("HBA_EXTRA_RULES not supported in PostgreSQL 9.6") + # Define custom HBA rules + hba_extra_rules = [ + "host test_db custom_user 0.0.0.0/0 trust", + "hostssl all all 192.168.0.0/16 md5", + ] + + # Start the Postgres container with HBA_EXTRA_RULES + self.postgres_container = docker( + "run", + "-d", + "--name", + "postgres_test_hba_extra_rules", + "--network", + "lan", + "-e", + "POSTGRES_DB=test_db", + "-e", + "POSTGRES_USER=test_user", + "-e", + "POSTGRES_PASSWORD=test_password", + "-e", + "HBA_EXTRA_RULES=" + json.dumps(hba_extra_rules), + CONF_EXTRA, + self.image, + ).strip() + + # Give the container some time to initialize + time.sleep(10) + + # Read the pg_hba.conf file content from the container + hba_conf = docker( + "exec", self.postgres_container, "cat", "/etc/postgres/pg_hba.conf" + ).strip() + + # Check that each rule in hba_extra_rules is present in the file + for rule in hba_extra_rules: + self.assertIn(rule, hba_conf) + if __name__ == "__main__": unittest.main() From eba6aff02687eb239a45a53d04251066afd5c7d6 Mon Sep 17 00:00:00 2001 From: josep-tecnativa Date: Fri, 29 Nov 2024 08:34:10 +0100 Subject: [PATCH 3/3] [IMP] Add pushing PR images to be able to test it correctly --- .github/workflows/ci.yaml | 29 ++++++++++++++++++----------- 1 file changed, 18 insertions(+), 11 deletions(-) diff --git a/.github/workflows/ci.yaml b/.github/workflows/ci.yaml index a131748..925a15d 100644 --- a/.github/workflows/ci.yaml +++ b/.github/workflows/ci.yaml @@ -16,10 +16,8 @@ jobs: - uses: actions/checkout@v2 - uses: actions/setup-python@v1 - name: Set PY - run: - echo "PY=$(python -c 'import hashlib, - sys;print(hashlib.sha256(sys.version.encode()+sys.executable.encode()).hexdigest())')" - >> $GITHUB_ENV + run: | + echo "PY=$(python -c 'import hashlib,sys;print(hashlib.sha256(sys.version.encode()+sys.executable.encode()).hexdigest())')" >> $GITHUB_ENV - uses: actions/cache@v1 with: path: ~/.cache/pre-commit @@ -32,7 +30,6 @@ jobs: strategy: fail-fast: false matrix: - # Test modern Odoo versions with latest Postgres version pg_version: - "16" - "15" @@ -45,29 +42,39 @@ jobs: env: # Indicates what's the equivalent to tecnativa/postgres-autoconf:latest image LATEST_RELEASE: "16-alpine" - # Variables found by default in Docker Hub builder DOCKER_REPO: tecnativa/postgres-autoconf DOCKER_TAG: ${{ matrix.pg_version }}-alpine GIT_SHA1: ${{ github.sha }} + IS_PR: ${{ github.event_name == 'pull_request' }} steps: - # Prepare - uses: actions/checkout@v2 - uses: actions/setup-python@v1 - run: pip install -r tests/ci-requirements.txt + # Build images - run: ./hooks/build # Test - run: python -m unittest tests.test -v + - name: Set Docker Tag + run: | + if [ "${{ env.IS_PR }}" = "true" ]; then + echo "DOCKER_TAG=${{ matrix.pg_version }}-test-pr${{ github.event.number }}" >> $GITHUB_ENV + else + echo "DOCKER_TAG=${{ matrix.pg_version }}-alpine" >> $GITHUB_ENV + fi + - name: Tag Docker Image for PR + if: env.IS_PR + run: docker tag ${{ env.DOCKER_REPO }}:${{ matrix.pg_version }}-alpine ${{ env.DOCKER_REPO }}:${{ env.DOCKER_TAG }} # Push - - name: push to docker hub - if: github.repository == 'Tecnativa/docker-postgres-autoconf' && github.ref == 'refs/heads/master' + - name: Push Docker Image to Docker Hub + if: github.repository == 'Tecnativa/docker-postgres-autoconf' && (env.IS_PR || github.ref == 'refs/heads/master') env: REGISTRY_HOST: docker.io REGISTRY_TOKEN: ${{ secrets.DOCKERHUB_TOKEN }} REGISTRY_USERNAME: ${{ secrets.DOCKERHUB_LOGIN }} run: ./hooks/push - - name: push to github registry - if: github.repository == 'Tecnativa/docker-postgres-autoconf' && github.ref == 'refs/heads/master' + - name: Push Docker Image to GitHub Registry + if: github.repository == 'Tecnativa/docker-postgres-autoconf' && (env.IS_PR || github.ref == 'refs/heads/master') env: REGISTRY_HOST: ghcr.io REGISTRY_TOKEN: ${{ secrets.BOT_TOKEN }}