Vault PKI Verification Runbook
1. Overview
This runbook provides comprehensive verification procedures for the DOMUS HashiCorp Vault PKI infrastructure. Use this for:
-
Daily health checks
-
Post-reboot verification
-
Troubleshooting certificate issuance issues
-
Preparing for Windows EAP-TEAP and BYOD deployments
|
Vault runs on HTTP (not HTTPS) on certmgr-01 Always set If you see this error:
You forgot to set VAULT_ADDR! |
2. Quick Start
# SSH to Vault server
ssh certmgr-01
# Set VAULT_ADDR (REQUIRED!)
export VAULT_ADDR='http://127.0.0.1:8200'
# Check Vault status
vault status
3. Architecture Summary
DOMUS-ROOT-CA (Vault pki/, 20 years: 2026-2046)
├── Serial: 10:E0:16:3C:7C:35:09:14:E2:9C:5B:78:D7:31:F1:50:1D:B6:55:83
├── Algorithm: RSA 4096
│
└── DOMUS-ISSUING-CA (Vault pki_int/, 5 years: 2026-2031)
├── Serial: 3F:83:98:35:4C:D7:8D:E5:99:3C:B1:94:7D:9C:BB:19:67:3F:10:7D
├── Algorithm: RSA 4096
│
└── End-Entity Certificates
├── Servers (domus-server role, 1 year max)
├── Clients (TBD: domus-client role)
├── BYOD (TBD: domus-byod role)
└── Windows (TBD: domus-windows-machine, domus-windows-user)
4. Section 1: Vault Status & Unsealing
4.1. Check Vault Status
# SSH to certmgr-01
ssh certmgr-01
# Set Vault address
export VAULT_ADDR='http://127.0.0.1:8200'
# Check status
vault status
Key Value
--- -----
Seal Type shamir
Initialized true
Sealed false
Total Shares 5
Threshold 3
Version 1.21.2
Storage Type file
Cluster Name vault-cluster-904d4b42
Cluster ID 8a9c3c77-5b4f-3e92-0d38-1f5e7a6b2c9d
HA Enabled false
Key Value
--- -----
Seal Type shamir
Initialized true
Sealed true ← SEALED!
Total Shares 5
Threshold 3
Unseal Progress 0/3
4.2. Unseal Vault (If Sealed)
|
Vault seals after reboot or manual seal operations. You need 3 unseal keys (threshold) to unseal. Unseal keys are stored in:
|
4.2.1. Method 1: Manual Unseal (on certmgr-01)
export VAULT_ADDR='http://127.0.0.1:8200'
# Apply first unseal key (will prompt)
vault operator unseal
# Enter key 1: <paste key>
# Apply second unseal key
vault operator unseal
# Enter key 2: <paste key>
# Apply third unseal key (threshold met)
vault operator unseal
# Enter key 3: <paste key>
# Verify unsealed
vault status | grep Sealed
# Expected: Sealed false
4.2.2. Method 2: Auto-Unseal via netapi (from local workstation)
# On modestus-razer (your workstation)
dsource d000 dev/vault
netapi vault unseal --auto
# Verify
netapi vault status
|
|
5. Section 2: PKI Secrets Engines
5.1. List Secrets Engines
# On certmgr-01
export VAULT_ADDR='http://127.0.0.1:8200'
export VAULT_TOKEN='<token>' # Get from dsec or use root token
vault secrets list -detailed
Path Type Description
---- ---- -----------
cubbyhole/ cubbyhole per-token private secret storage
identity/ identity identity store
pki/ pki DOMUS-ROOT-CA (20 years)
pki_int/ pki DOMUS-ISSUING-CA (5 years)
secret/ kv key/value secret storage
sys/ system system endpoints used for control, policy and debugging
|
Required Engines:
If missing, Vault PKI is not configured! |
6. Section 3: Root CA (pki/)
6.1. Read Root CA Certificate
# On certmgr-01
export VAULT_ADDR='http://127.0.0.1:8200'
# Get root CA certificate
vault read pki/cert/ca -format=json | jq -r '.data.certificate' | openssl x509 -noout -text | grep -E "Subject:|Issuer:|Not Before|Not After|Serial Number"
Serial Number:
10:e0:16:3c:7c:35:09:14:e2:9c:5b:78:d7:31:f1:50:1d:b6:55:83
Issuer: C=US, O=Domus Digitalis, OU=Enterprise PKI, CN=DOMUS-ROOT-CA
Subject: C=US, O=Domus Digitalis, OU=Enterprise PKI, CN=DOMUS-ROOT-CA
Not Before: Jan 25 06:57:11 2026 GMT
Not After : Jan 20 06:57:41 2046 GMT ← 20 years
|
Root CA is self-signed: Subject == Issuer |
7. Section 4: Intermediate CA (pki_int/)
7.1. Read Intermediate CA Certificate
# Get intermediate CA certificate
vault read pki_int/cert/ca -format=json | jq -r '.data.certificate' | openssl x509 -noout -text | grep -E "Subject:|Issuer:|Not Before|Not After|Serial Number"
Serial Number:
3f:83:98:35:4c:d7:8d:e5:99:3c:b1:94:7d:9c:bb:19:67:3f:10:7d
Issuer: C=US, O=Domus Digitalis, OU=Enterprise PKI, CN=DOMUS-ROOT-CA ← Root CA
Subject: CN=DOMUS-ISSUING-CA, OU=Enterprise PKI, O=Domus Digitalis
Not Before: Jan 25 07:05:44 2026 GMT
Not After : Jan 24 07:06:14 2031 GMT ← 5 years
|
Intermediate CA signed by Root:
This proves the chain is correct! |
7.2. Verify Certificate Chain
# Download certificates
vault read pki/cert/ca -format=json | jq -r '.data.certificate' > /tmp/root.crt
vault read pki_int/cert/ca -format=json | jq -r '.data.certificate' > /tmp/intermediate.crt
# Verify chain
openssl verify -CAfile /tmp/root.crt /tmp/intermediate.crt
/tmp/intermediate.crt: OK
|
If you get |
8. Section 5: PKI Roles
8.1. List Roles
vault list pki_int/roles
Keys
----
domus-server
Keys
----
domus-server
domus-client
domus-byod
domus-windows-machine
domus-windows-user
8.2. Inspect domus-server Role
vault read pki_int/roles/domus-server
Key Value
--- -----
allow_bare_domains false
allow_subdomains true
allowed_domains [inside.domusdigitalis.dev domusdigitalis.dev]
enforce_hostnames true
key_bits 2048
key_type rsa
max_ttl 8760h ← 1 year max
require_cn true
8.3. Check for Missing Roles (BYOD/Windows)
# Try to read roles that should exist for full deployment
vault read pki_int/roles/domus-client 2>&1 | grep -q "No value found" && echo "❌ domus-client NOT FOUND"
vault read pki_int/roles/domus-byod 2>&1 | grep -q "No value found" && echo "❌ domus-byod NOT FOUND"
vault read pki_int/roles/domus-windows-machine 2>&1 | grep -q "No value found" && echo "❌ domus-windows-machine NOT FOUND"
vault read pki_int/roles/domus-windows-user 2>&1 | grep -q "No value found" && echo "❌ domus-windows-user NOT FOUND"
|
If roles are missing, you’ll need to create them before deploying Windows EAP-TEAP or BYOD provisioning. See Section 9. |
9. Section 6: Test Certificate Issuance
9.1. Issue Test Certificate (vault CLI)
# On certmgr-01
export VAULT_ADDR='http://127.0.0.1:8200'
export VAULT_TOKEN='<token>'
# Issue test certificate
vault write pki_int/issue/domus-server \
common_name="test-$(date +%s).inside.domusdigitalis.dev" \
ttl=24h \
-format=json > /tmp/test-cert.json
# Verify certificate was issued
cat /tmp/test-cert.json | jq -r '.data.certificate' | openssl x509 -noout -subject -issuer -dates
subject=CN = test-1738047123.inside.domusdigitalis.dev
issuer=CN = DOMUS-ISSUING-CA, OU = Enterprise PKI, O = Domus Digitalis
notBefore=Jan 28 05:32:03 2026 GMT
notAfter=Jan 29 05:32:33 2026 GMT ← 24 hours
9.2. Verify Full Chain
# Extract certificates
cat /tmp/test-cert.json | jq -r '.data.certificate' > /tmp/test.crt
cat /tmp/test-cert.json | jq -r '.data.issuing_ca' > /tmp/issuing.crt
# Verify against root
openssl verify -CAfile /tmp/root.crt -untrusted /tmp/issuing.crt /tmp/test.crt
/tmp/test.crt: OK
|
Certificate Chain Verification:
All three steps must succeed! |
10. Section 7: netapi Vault Commands
10.1. Prerequisites
Run these commands from your local workstation (modestus-razer), not from certmgr-01.
# Load Vault credentials from dsec
dsource d000 dev/vault
# Verify environment variables loaded
env | grep VAULT
# Expected:
# VAULT_ADDR=http://certmgr-01.inside.domusdigitalis.dev:8200
# VAULT_TOKEN=<token>
# VAULT_UNSEAL_KEY_1=<key>
# VAULT_UNSEAL_KEY_2=<key>
# VAULT_UNSEAL_KEY_3=<key>
10.2. Check Vault Status via netapi
# From modestus-razer
netapi vault status
Vault Status: UNSEALED
┏━━━━━━━━━━━━━━┳━━━━━━━━━━━━━━━━━━━━━━━━┓
┃ Property ┃ Value ┃
┡━━━━━━━━━━━━━━╇━━━━━━━━━━━━━━━━━━━━━━━━┩
│ Initialized │ Yes │
│ Sealed │ No │
│ Version │ 1.21.2 │
│ Cluster Name │ vault-cluster-904d4b42 │
│ HA Enabled │ No │
│ Storage Type │ file │
└──────────────┴────────────────────────┘
10.3. List Secrets Engines via netapi
netapi vault secrets-engines
Secrets Engines
┏━━━━━━━━━━┳━━━━━━━━┳━━━━━━━━━━━━━━━━━━━━━━━┓
┃ Path ┃ Type ┃ Description ┃
┡━━━━━━━━━━╇━━━━━━━━╇━━━━━━━━━━━━━━━━━━━━━━━┩
│ pki/ │ pki │ DOMUS-ROOT-CA │
│ pki_int/ │ pki │ DOMUS-ISSUING-CA │
│ secret/ │ kv │ Key/Value Secrets │
└──────────┴────────┴───────────────────────┘
10.5. Issue Certificate via netapi
# Issue certificate with default TTL (1 year)
netapi vault pki-issue test-netapi.inside.domusdigitalis.dev
# Issue with custom TTL (24 hours)
netapi vault pki-issue test-netapi-24h.inside.domusdigitalis.dev --ttl 24h
# Issue and save to specific directory
netapi vault pki-issue web-server.inside.domusdigitalis.dev --ttl 8760h -o /tmp/certs
✓ Certificate issued successfully
Common Name: test-netapi.inside.domusdigitalis.dev
Serial: 3a:1f:5c:89:...
Not After: 2027-01-28 05:45:00 UTC
Files created:
test-netapi.inside.domusdigitalis.dev.crt
test-netapi.inside.domusdigitalis.dev.key
test-netapi.inside.domusdigitalis.dev.chain.crt
11. Section 8: Certificate Revocation List (CRL)
11.1. Check CRL (Root CA)
# Download and view root CRL
curl -s http://certmgr-01.inside.domusdigitalis.dev:8200/v1/pki/crl | openssl crl -inform DER -text -noout | head -20
11.2. Check CRL (Intermediate CA)
# Download and view intermediate CRL
curl -s http://certmgr-01.inside.domusdigitalis.dev:8200/v1/pki_int/crl | openssl crl -inform DER -text -noout | head -20
Certificate Revocation List (CRL):
Version 2 (0x1)
Signature Algorithm: sha256WithRSAEncryption
Issuer: CN=DOMUS-ISSUING-CA, OU=Enterprise PKI, O=Domus Digitalis
Last Update: Jan 28 05:50:00 2026 GMT
Next Update: Jan 31 05:50:00 2026 GMT ← Updated every 72 hours
No Revoked Certificates.
12. Section 9: Create Missing Roles (for BYOD/Windows)
If roles for BYOD or Windows are missing, create them:
12.1. Create domus-client Role (Linux Workstations)
vault write pki_int/roles/domus-client \
allowed_domains="inside.domusdigitalis.dev" \
allow_subdomains=true \
allow_bare_domains=false \
max_ttl=8760h \
key_type=rsa \
key_bits=2048 \
key_usage="DigitalSignature,KeyEncipherment" \
ext_key_usage="ClientAuth" \
require_cn=true \
enforce_hostnames=true
12.2. Create domus-byod Role (Mobile Devices)
vault write pki_int/roles/domus-byod \
allowed_domains="byod.inside.domusdigitalis.dev" \
allow_subdomains=true \
allow_bare_domains=false \
max_ttl=2160h \
key_type=rsa \
key_bits=2048 \
key_usage="DigitalSignature,KeyEncipherment" \
ext_key_usage="ClientAuth" \
require_cn=true \
enforce_hostnames=true \
no_store=false
|
BYOD TTL: 2160h = 90 days (shorter than workstations for security) |
12.3. Create domus-windows-machine Role
vault write pki_int/roles/domus-windows-machine \
allowed_domains="inside.domusdigitalis.dev" \
allow_subdomains=true \
allow_bare_domains=false \
max_ttl=8760h \
key_type=rsa \
key_bits=2048 \
key_usage="DigitalSignature,KeyEncipherment" \
ext_key_usage="ClientAuth" \
require_cn=true \
enforce_hostnames=true
12.4. Create domus-windows-user Role
vault write pki_int/roles/domus-windows-user \
allowed_domains="inside.domusdigitalis.dev" \
allow_subdomains=true \
allow_bare_domains=false \
max_ttl=8760h \
key_type=rsa \
key_bits=2048 \
key_usage="DigitalSignature,KeyEncipherment" \
ext_key_usage="ClientAuth,EmailProtection" \
require_cn=true \
enforce_hostnames=true
13. Section 10: Troubleshooting
13.1. Vault is Sealed After Reboot
Symptoms:
vault status | grep Sealed
Sealed true
Solution:
# Method 1: From local workstation
dsource d000 dev/vault
netapi vault unseal --auto
# Method 2: On certmgr-01
vault operator unseal # Apply 3 keys
13.2. Certificate Issuance Fails
Symptoms:
Error writing data to pki_int/issue/domus-server: Error making API request.
Diagnosis:
# Check if role exists
vault list pki_int/roles | grep domus-server
# Check role configuration
vault read pki_int/roles/domus-server
# Check if CN matches allowed domains
# CN must end with: .inside.domusdigitalis.dev or .domusdigitalis.dev
13.3. Chain Verification Fails
Symptoms:
openssl verify -CAfile root.crt -untrusted intermediate.crt test.crt
unable to get local issuer certificate
Diagnosis:
# Check intermediate was signed by root
openssl x509 -in intermediate.crt -noout -issuer
# Should show: issuer=CN=DOMUS-ROOT-CA
# Check root is self-signed
openssl x509 -in root.crt -noout -subject -issuer
# Subject and Issuer should match
14. Section 11: Daily Checklist
Run this daily to verify Vault PKI health:
# 1. Check status (from workstation)
dsource d000 dev/vault
netapi vault status
# Expected: UNSEALED
# 2. Check secrets engines
netapi vault secrets-engines
# Expected: pki/ and pki_int/ present
# 3. Test certificate issuance
netapi vault pki-issue daily-test-$(date +%Y%m%d).inside.domusdigitalis.dev --ttl 1h
# Expected: Success
# 4. Check CRL is accessible
curl -I http://certmgr-01.inside.domusdigitalis.dev:8200/v1/pki_int/crl
# Expected: HTTP/1.1 200 OK
# 5. Verify backup is recent (on certmgr-01)
ssh certmgr-01 "ls -lh /opt/vault/backups/ | head -5"
# Expected: Recent backup within 24 hours
16. Appendix: Quick Command Reference
| Task | Command |
|---|---|
Check Vault status |
|
Unseal Vault |
|
List PKI roles |
|
Issue certificate |
|
Verify chain |
|
Check CRL |
|
View role config |
|