feat(postgres): use ESO
This commit is contained in:
@@ -3,7 +3,8 @@ set fallback := true
|
|||||||
export CNPG_NAMESPACE := env("CNPG_NAMESPACE", "postgres")
|
export CNPG_NAMESPACE := env("CNPG_NAMESPACE", "postgres")
|
||||||
export CNPG_CHART_VERSION := env("CNPG_CHART_VERSION", "0.26.0")
|
export CNPG_CHART_VERSION := env("CNPG_CHART_VERSION", "0.26.0")
|
||||||
export CNPG_CLUSTER_CHART_VERSION := env("CNPG_CLUSTER_CHART_VERSION", "0.3.1")
|
export CNPG_CLUSTER_CHART_VERSION := env("CNPG_CLUSTER_CHART_VERSION", "0.3.1")
|
||||||
export VAULT_ENABLED := env("VAULT_ENABLED", "true")
|
export K8S_VAULT_NAMESPACE := env("K8S_VAULT_NAMESPACE", "vault")
|
||||||
|
export EXTERNAL_SECRETS_NAMESPACE := env("EXTERNAL_SECRETS_NAMESPACE", "external-secrets")
|
||||||
|
|
||||||
[private]
|
[private]
|
||||||
default:
|
default:
|
||||||
@@ -44,18 +45,43 @@ uninstall-cnpg:
|
|||||||
create-cluster:
|
create-cluster:
|
||||||
#!/bin/bash
|
#!/bin/bash
|
||||||
set -euo pipefail
|
set -euo pipefail
|
||||||
|
if helm status external-secrets -n ${EXTERNAL_SECRETS_NAMESPACE} &>/dev/null; then
|
||||||
|
echo "External Secrets Operator detected. Creating admin credentials via ExternalSecret..."
|
||||||
|
password=$(just utils::random-password)
|
||||||
|
just vault::put-root postgres/admin username=postgres password="${password}"
|
||||||
|
|
||||||
|
kubectl delete externalsecret postgres-cluster-superuser -n ${CNPG_NAMESPACE} --ignore-not-found
|
||||||
|
gomplate -f postgres-superuser-external-secret.gomplate.yaml | kubectl apply -f -
|
||||||
|
|
||||||
|
echo "Waiting for ExternalSecret to sync..."
|
||||||
|
kubectl wait --for=condition=Ready externalsecret/postgres-cluster-superuser \
|
||||||
|
-n ${CNPG_NAMESPACE} --timeout=60s
|
||||||
|
else
|
||||||
|
echo "External Secrets Operator not found. Creating superuser secret directly..."
|
||||||
|
password=$(just utils::random-password)
|
||||||
|
kubectl delete secret postgres-cluster-superuser -n ${CNPG_NAMESPACE} --ignore-not-found
|
||||||
|
kubectl create secret generic postgres-cluster-superuser -n ${CNPG_NAMESPACE} \
|
||||||
|
--from-literal=username=postgres \
|
||||||
|
--from-literal=password="${password}"
|
||||||
|
|
||||||
|
if helm status vault -n ${K8S_VAULT_NAMESPACE} &>/dev/null; then
|
||||||
|
just vault::put-root postgres/admin username=postgres password="${password}"
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
|
||||||
helm upgrade --install postgres-cluster cnpg/cluster \
|
helm upgrade --install postgres-cluster cnpg/cluster \
|
||||||
--version ${CNPG_CLUSTER_CHART_VERSION} \
|
--version ${CNPG_CLUSTER_CHART_VERSION} \
|
||||||
-n ${CNPG_NAMESPACE} --create-namespace --wait \
|
-n ${CNPG_NAMESPACE} --wait -f postgres-cluster-values.yaml
|
||||||
-f postgres-cluster-values.yaml
|
|
||||||
|
|
||||||
if [ "${VAULT_ENABLED}" != "false" ]; then
|
echo "Waiting for PostgreSQL cluster to be ready..."
|
||||||
just put-admin-credentials-to-vault
|
kubectl wait --for=condition=Ready clusters.postgresql.cnpg.io/postgres-cluster \
|
||||||
fi
|
-n ${CNPG_NAMESPACE} --timeout=300s
|
||||||
|
|
||||||
# Delete Postgres cluster
|
# Delete Postgres cluster
|
||||||
delete-cluster:
|
delete-cluster:
|
||||||
@helm uninstall postgres-cluster -n ${CNPG_NAMESPACE} --ignore-not-found --wait
|
@helm uninstall postgres-cluster -n ${CNPG_NAMESPACE} --ignore-not-found --wait
|
||||||
|
@kubectl delete externalsecret postgres-cluster-superuser -n ${CNPG_NAMESPACE} --ignore-not-found
|
||||||
|
@kubectl delete secret postgres-cluster-superuser -n ${CNPG_NAMESPACE} --ignore-not-found
|
||||||
|
|
||||||
# Print Postgres username
|
# Print Postgres username
|
||||||
admin-username:
|
admin-username:
|
||||||
@@ -67,18 +93,13 @@ admin-password:
|
|||||||
-o jsonpath="{.data.password}" | base64 --decode
|
-o jsonpath="{.data.password}" | base64 --decode
|
||||||
@echo
|
@echo
|
||||||
|
|
||||||
# Put admin credentials to Vault
|
|
||||||
put-admin-credentials-to-vault:
|
|
||||||
@just vault::put-root postgres/admin username=$(just admin-username) password=$(just admin-password)
|
|
||||||
@echo "Admin credentials stored in Vault under 'postgres/admin'."
|
|
||||||
|
|
||||||
# Create Postgres database
|
# Create Postgres database
|
||||||
create-db db_name='':
|
create-db db_name='':
|
||||||
#!/bin/bash
|
#!/bin/bash
|
||||||
set -euo pipefail
|
set -euo pipefail
|
||||||
DB_NAME=${DB_NAME:-{{ db_name }}}
|
DB_NAME=${DB_NAME:-{{ db_name }}}
|
||||||
while [ -z "${DB_NAME}" ]; do
|
while [ -z "${DB_NAME}" ]; do
|
||||||
DB_NAME=$(gum input --prompt="Database name: " --width=80)
|
DB_NAME=$(gum input --prompt="Database name: " --width=100)
|
||||||
done
|
done
|
||||||
if just db-exists ${DB_NAME} &>/dev/null; then
|
if just db-exists ${DB_NAME} &>/dev/null; then
|
||||||
echo "Database ${DB_NAME} already exists" >&2
|
echo "Database ${DB_NAME} already exists" >&2
|
||||||
@@ -108,12 +129,13 @@ delete-db db_name='':
|
|||||||
echo "Database ${DB_NAME} deleted."
|
echo "Database ${DB_NAME} deleted."
|
||||||
|
|
||||||
# Check if database exists
|
# Check if database exists
|
||||||
|
[no-exit-message]
|
||||||
db-exists db_name='':
|
db-exists db_name='':
|
||||||
#!/bin/bash
|
#!/bin/bash
|
||||||
set -euo pipefail
|
set -euo pipefail
|
||||||
DB_NAME=${DB_NAME:-{{ db_name }}}
|
DB_NAME=${DB_NAME:-{{ db_name }}}
|
||||||
while [ -z "${DB_NAME}" ]; do
|
while [ -z "${DB_NAME}" ]; do
|
||||||
DB_NAME=$(gum input --prompt="Database name: " --width=80)
|
DB_NAME=$(gum input --prompt="Database name: " --width=100)
|
||||||
done
|
done
|
||||||
if echo '\l' | just postgres::psql | grep -E "^ *${DB_NAME} *\|" &>/dev/null; then
|
if echo '\l' | just postgres::psql | grep -E "^ *${DB_NAME} *\|" &>/dev/null; then
|
||||||
echo "Database ${DB_NAME} exists."
|
echo "Database ${DB_NAME} exists."
|
||||||
@@ -129,14 +151,14 @@ create-user username='' password='':
|
|||||||
USERNAME=${USERNAME:-"{{ username }}"}
|
USERNAME=${USERNAME:-"{{ username }}"}
|
||||||
PASSWORD=${PASSWORD:-"{{ password }}"}
|
PASSWORD=${PASSWORD:-"{{ password }}"}
|
||||||
while [ -z "${USERNAME}" ]; do
|
while [ -z "${USERNAME}" ]; do
|
||||||
USERNAME=$(gum input --prompt="Username: " --width=80)
|
USERNAME=$(gum input --prompt="Username: " --width=100)
|
||||||
done
|
done
|
||||||
if just user-exists ${USERNAME} &>/dev/null; then
|
if just user-exists ${USERNAME} &>/dev/null; then
|
||||||
echo "User ${USERNAME} already exists" >&2
|
echo "User ${USERNAME} already exists" >&2
|
||||||
exit
|
exit
|
||||||
fi
|
fi
|
||||||
if [ -z "${PASSWORD}" ]; then
|
if [ -z "${PASSWORD}" ]; then
|
||||||
PASSWORD=$(gum input --prompt="Password: " --password --width=80 \
|
PASSWORD=$(gum input --prompt="Password: " --password --width=100 \
|
||||||
--placeholder="Empty to generate a random password")
|
--placeholder="Empty to generate a random password")
|
||||||
fi
|
fi
|
||||||
if [ -z "${PASSWORD}" ]; then
|
if [ -z "${PASSWORD}" ]; then
|
||||||
@@ -164,12 +186,13 @@ delete-user username='':
|
|||||||
echo "User ${USERNAME} deleted."
|
echo "User ${USERNAME} deleted."
|
||||||
|
|
||||||
# Check if user exists
|
# Check if user exists
|
||||||
|
[no-exit-message]
|
||||||
user-exists username='':
|
user-exists username='':
|
||||||
#!/bin/bash
|
#!/bin/bash
|
||||||
set -euo pipefail
|
set -euo pipefail
|
||||||
USERNAME=${USERNAME:-"{{ username }}"}
|
USERNAME=${USERNAME:-"{{ username }}"}
|
||||||
while [ -z "${USERNAME}" ]; do
|
while [ -z "${USERNAME}" ]; do
|
||||||
USERNAME=$(gum input --prompt="Username: " --width=80)
|
USERNAME=$(gum input --prompt="Username: " --width=100)
|
||||||
done
|
done
|
||||||
if echo '\du' | just postgres::psql | grep -E "^ *${USERNAME} *\|" &>/dev/null; then
|
if echo '\du' | just postgres::psql | grep -E "^ *${USERNAME} *\|" &>/dev/null; then
|
||||||
echo "User ${USERNAME} exists."
|
echo "User ${USERNAME} exists."
|
||||||
@@ -185,10 +208,10 @@ grant db_name='' username='':
|
|||||||
DB_NAME=${DB_NAME:-"{{ db_name }}"}
|
DB_NAME=${DB_NAME:-"{{ db_name }}"}
|
||||||
USERNAME=${USERNAME:-"{{ username }}"}
|
USERNAME=${USERNAME:-"{{ username }}"}
|
||||||
while [ -z "${DB_NAME}" ]; do
|
while [ -z "${DB_NAME}" ]; do
|
||||||
DB_NAME=$(gum input --prompt="Database name: " --width=80)
|
DB_NAME=$(gum input --prompt="Database name: " --width=100)
|
||||||
done
|
done
|
||||||
while [ -z "${USERNAME}" ]; do
|
while [ -z "${USERNAME}" ]; do
|
||||||
USERNAME=$(gum input --prompt="Username: " --width=80)
|
USERNAME=$(gum input --prompt="Username: " --width=100)
|
||||||
done
|
done
|
||||||
if ! just psql ${DB_NAME} -U postgres -P pager=off -c "\"SELECT 1;\""; then
|
if ! just psql ${DB_NAME} -U postgres -P pager=off -c "\"SELECT 1;\""; then
|
||||||
echo "Database ${DB_NAME} does not exist." >&2
|
echo "Database ${DB_NAME} does not exist." >&2
|
||||||
@@ -206,10 +229,10 @@ revoke db_name='' username='':
|
|||||||
DB_NAME=${DB_NAME:-"{{ db_name }}"}
|
DB_NAME=${DB_NAME:-"{{ db_name }}"}
|
||||||
USERNAME=${USERNAME:-"{{ username }}"}
|
USERNAME=${USERNAME:-"{{ username }}"}
|
||||||
while [ -z "${DB_NAME}" ]; do
|
while [ -z "${DB_NAME}" ]; do
|
||||||
DB_NAME=$(gum input --prompt="Database name: " --width=80)
|
DB_NAME=$(gum input --prompt="Database name: " --width=100)
|
||||||
done
|
done
|
||||||
while [ -z "${USERNAME}" ]; do
|
while [ -z "${USERNAME}" ]; do
|
||||||
USERNAME=$(gum input --prompt="Username: " --width=80)
|
USERNAME=$(gum input --prompt="Username: " --width=100)
|
||||||
done
|
done
|
||||||
if ! just psql -U postgres ${DB_NAME} -P pager=off -c "\"SELECT 1;\""; then
|
if ! just psql -U postgres ${DB_NAME} -P pager=off -c "\"SELECT 1;\""; then
|
||||||
echo "Database ${DB_NAME} does not exist." >&2
|
echo "Database ${DB_NAME} does not exist." >&2
|
||||||
|
|||||||
@@ -4,3 +4,6 @@ cluster:
|
|||||||
initdb:
|
initdb:
|
||||||
postInitTemplateSQL:
|
postInitTemplateSQL:
|
||||||
- CREATE EXTENSION IF NOT EXISTS vector;
|
- CREATE EXTENSION IF NOT EXISTS vector;
|
||||||
|
|
||||||
|
enableSuperuserAccess: true
|
||||||
|
superuserSecret: postgres-cluster-superuser
|
||||||
|
|||||||
22
postgres/postgres-superuser-external-secret.gomplate.yaml
Normal file
22
postgres/postgres-superuser-external-secret.gomplate.yaml
Normal file
@@ -0,0 +1,22 @@
|
|||||||
|
apiVersion: external-secrets.io/v1
|
||||||
|
kind: ExternalSecret
|
||||||
|
metadata:
|
||||||
|
name: postgres-cluster-superuser
|
||||||
|
namespace: {{ .Env.CNPG_NAMESPACE }}
|
||||||
|
spec:
|
||||||
|
refreshInterval: 1h
|
||||||
|
secretStoreRef:
|
||||||
|
name: vault-secret-store
|
||||||
|
kind: ClusterSecretStore
|
||||||
|
target:
|
||||||
|
name: postgres-cluster-superuser
|
||||||
|
creationPolicy: Owner
|
||||||
|
data:
|
||||||
|
- secretKey: username
|
||||||
|
remoteRef:
|
||||||
|
key: postgres/admin
|
||||||
|
property: username
|
||||||
|
- secretKey: password
|
||||||
|
remoteRef:
|
||||||
|
key: postgres/admin
|
||||||
|
property: password
|
||||||
Reference in New Issue
Block a user