Files
Deploy-Laboratory/ansible/playbooks/verify/04-12.yml
2026-03-29 09:08:01 +08:00

178 lines
7.9 KiB
YAML

- name: Deploy+Verify 04-12 nodejs TLS Ingress
hosts: k3s_server
become: true
run_once: true
vars:
k3s_kubeconfig: /etc/rancher/k3s/k3s.yaml
verify_teardown: "{{ (VERIFY_TEARDOWN | default('1')) | string }}"
nodejs_manifest_src: "{{ playbook_dir }}/../../files/04-12/04-12-nodejs-demo.yaml"
nodejs_manifest_dest: /tmp/nodejs-demo-04-12.yaml
# extra var 或环境变量(与 04-07 一致)
_nodejs_tls_entry_base: "{{ NODEJS_TLS_ENTRY_BASE | default(lookup('env', 'NODEJS_TLS_ENTRY_BASE') | default('', true), true) | trim }}"
_nodejs_tls_host: "{{ NODEJS_TLS_HOST | default(lookup('env', 'NODEJS_TLS_HOST') | default('', true), true) | trim }}"
create_nodejs_demo_tls_secret: "{{ (lookup('env', 'CREATE_NODEJS_DEMO_TLS_SECRET') | default('0', true) | trim) == '1' }}"
# 与清单 Ingress 默认 host 对齐;未 export NODEJS_TLS_* 时仍可用自签 + 默认 host
nodejs_verify_entry_base: "{{ (_nodejs_tls_entry_base | length > 0) | ternary(_nodejs_tls_entry_base, 'https://app.example.local') }}"
nodejs_verify_path: "/api/"
nodejs_verify_host: "{{ (_nodejs_tls_host | length > 0) | ternary(_nodejs_tls_host, 'app.example.local') }}"
# 自签实验室路径或显式 NODEJS_TLS_* 时跑 openssl/curl
nodejs_http_check_enabled: "{{ (create_nodejs_demo_tls_secret | bool) or ((_nodejs_tls_entry_base | length > 0) and (_nodejs_tls_host | length > 0)) }}"
_nodejs_tls_authority: "{{ nodejs_verify_entry_base | trim | regex_replace('^https?://', '') | regex_replace('/.*$', '') }}"
nodejs_tls_connect_host: "{{ _nodejs_tls_authority | regex_replace(':([0-9]+)$', '') }}"
nodejs_tls_connect_port: "{{ (_nodejs_tls_authority | regex_replace('^[^:]*:', '') | int) if (':' in _nodejs_tls_authority) else 443 }}"
tasks:
- name: Check TLS secret exists (nodejs-demo-tls)
ansible.builtin.shell: |
set -e
KUBECONFIG={{ k3s_kubeconfig }} kubectl -n default get secret nodejs-demo-tls
args:
executable: /bin/bash
changed_when: false
failed_when: false
register: nodejs_tls_secret_check
- name: Create self-signed nodejs-demo-tls (lab opt-in, matches Ingress host in manifest)
when:
- nodejs_tls_secret_check.rc != 0
- create_nodejs_demo_tls_secret | bool
ansible.builtin.shell: |
set -euo pipefail
export KUBECONFIG={{ k3s_kubeconfig }}
HOST={{ nodejs_verify_host | quote }}
TMP=$(mktemp -d)
trap 'rm -rf "$TMP"' EXIT
echo "[OC-ASSERT] assertion=nodejs_tls_selfsigned phase=cluster probe=openssl_san host=${HOST}"
if openssl req -help 2>&1 | grep -q -- -addext; then
openssl req -x509 -nodes -days 365 -newkey rsa:2048 \
-keyout "$TMP/tls.key" -out "$TMP/tls.crt" \
-subj "/CN=${HOST}" \
-addext "subjectAltName=DNS:${HOST}"
else
: >"$TMP/cnf"
printf '%s\n' '[req]' 'distinguished_name = req_distinguished_name' 'x509_extensions = v3_ca' 'prompt = no' >>"$TMP/cnf"
printf '%s\n' '[req_distinguished_name]' "CN = ${HOST}" >>"$TMP/cnf"
printf '%s\n' '[v3_ca]' 'subjectAltName = @alt_names' '[alt_names]' "DNS.1 = ${HOST}" >>"$TMP/cnf"
openssl req -x509 -nodes -days 365 -newkey rsa:2048 \
-keyout "$TMP/tls.key" -out "$TMP/tls.crt" \
-config "$TMP/cnf" -extensions v3_ca
fi
kubectl create secret tls nodejs-demo-tls \
--cert="$TMP/tls.crt" --key="$TMP/tls.key" -n default \
--dry-run=client -o yaml | kubectl apply -f -
args:
executable: /bin/bash
register: nodejs_tls_autocreate
changed_when: true
- name: Remember autocreated TLS secret for teardown
ansible.builtin.set_fact:
nodejs_tls_secret_autocreated: true
when:
- create_nodejs_demo_tls_secret | bool
- nodejs_tls_autocreate is defined
- not (nodejs_tls_autocreate.skipped | default(false))
- (nodejs_tls_autocreate.rc | default(1)) == 0
- name: Re-read TLS secret (after optional create)
ansible.builtin.shell: |
set -e
KUBECONFIG={{ k3s_kubeconfig }} kubectl -n default get secret nodejs-demo-tls
args:
executable: /bin/bash
changed_when: false
failed_when: false
register: nodejs_tls_secret_check
- name: Gate when TLS secret missing
when: nodejs_tls_secret_check.rc != 0
ansible.builtin.include_role:
name: verify_common
tasks_from: gate-debug-end-play.yml
vars:
verify_gate_message: "[GATE] skipped doc_id=04-12 reason=missing_tls_secret secret=nodejs-demo-tls namespace=default hint=export CREATE_NODEJS_DEMO_TLS_SECRET=1 or kubectl create secret tls"
- name: Copy nodejs demo manifest
ansible.builtin.copy:
src: "{{ nodejs_manifest_src }}"
dest: "{{ nodejs_manifest_dest }}"
mode: "0644"
- name: Apply nodejs demo manifest
ansible.builtin.shell: |
set -e
KUBECONFIG={{ k3s_kubeconfig }} kubectl apply -f {{ nodejs_manifest_dest }}
args:
executable: /bin/bash
changed_when: true
- name: Rollout status nodejs-demo
ansible.builtin.include_role:
name: verify_common
tasks_from: kubectl-rollout-status.yml
vars:
verify_rollout_ref: deployment/nodejs-demo
- name: Assert Service targetPort matches expected (optional)
when: nodejs_expected_target_port is defined and (nodejs_expected_target_port | int) > 0
ansible.builtin.shell: |
set -euo pipefail
exp="{{ nodejs_expected_target_port | int }}"
got=$(KUBECONFIG={{ k3s_kubeconfig }} kubectl get svc nodejs-demo -n default -o jsonpath='{.spec.ports[0].targetPort}')
echo "svc/nodejs-demo targetPort=$got expected=$exp"
test "$got" = "$exp"
args:
executable: /bin/bash
changed_when: false
- name: Assert Endpoints exist
ansible.builtin.include_role:
name: verify_common
tasks_from: kubectl-endpoints-ready.yml
vars:
verify_endpoints_service: nodejs-demo
verify_endpoints_assertion_label: nodejs_demo_endpoints
- name: TLS SNI + certificate subject (openssl)
when: nodejs_http_check_enabled | default(false)
ansible.builtin.include_role:
name: verify_common
tasks_from: tls-openssl-sni.yml
vars:
verify_tls_connect_host: "{{ nodejs_tls_connect_host }}"
verify_tls_port: "{{ nodejs_tls_connect_port }}"
verify_tls_servername: "{{ nodejs_verify_host }}"
verify_tls_expect_subject_substring: "{{ nodejs_verify_host }}"
verify_tls_assertion_label: nodejs_demo_tls_sni_handshake
- name: HTTPS check nodejs demo (path/host)
when: nodejs_http_check_enabled | default(false)
ansible.builtin.include_role:
name: verify_common
tasks_from: http-curl-expect.yml
vars:
verify_http_entry_base: "{{ nodejs_verify_entry_base }}"
verify_http_path: "{{ nodejs_verify_path | default('/api/') }}"
verify_http_host_header: "{{ nodejs_verify_host }}"
verify_http_assertion_label: nodejs_tls_ingress_entry_http
verify_http_tls_insecure: "{{ (create_nodejs_demo_tls_secret | bool) or ((lookup('env', 'NODEJS_TLS_CURL_INSECURE') | default('0', true) | trim) == '1') }}"
- name: Teardown when VERIFY_TEARDOWN=1
when: verify_teardown == "1"
ansible.builtin.shell: |
set -e
KUBECONFIG={{ k3s_kubeconfig }} kubectl delete -f {{ nodejs_manifest_dest }} --ignore-not-found=true
args:
executable: /bin/bash
changed_when: true
- name: Delete autocreated TLS secret on teardown
when:
- verify_teardown == "1"
- nodejs_tls_secret_autocreated | default(false) | bool
ansible.builtin.shell: |
set -e
KUBECONFIG={{ k3s_kubeconfig }} kubectl delete secret nodejs-demo-tls -n default --ignore-not-found=true
args:
executable: /bin/bash
changed_when: true