Skip to content

Commit e958ca1

Browse files
committed
Introduce smoke tests to E2E validate certificate generation
The test runs the certgen binary once and verifies that both the CA and the leaf certificates specified through the configuration are generated correctly. Then, it reruns the tool a second time, and it asserts that only the leaf certificates are regenerated, while the CA is not modified. Signed-off-by: Marco Iorio <[email protected]>
1 parent 86746b4 commit e958ca1

File tree

1 file changed

+194
-0
lines changed

1 file changed

+194
-0
lines changed

.github/workflows/tests-smoke.yaml

Lines changed: 194 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,194 @@
1+
name: Smoke Test
2+
3+
on:
4+
pull_request: {}
5+
push:
6+
branches:
7+
- main
8+
9+
jobs:
10+
test:
11+
runs-on: ubuntu-latest
12+
name: Build and test
13+
steps:
14+
- name: Create the target kind cluster
15+
uses: helm/kind-action@0025e74a8c7512023d06dc019c617aa3cf561fde
16+
17+
- name: Checkout code
18+
uses: actions/checkout@a5ac7e51b41094c92402da3b24376905380afc29
19+
20+
- name: Install Go
21+
uses: actions/setup-go@cdcb36043654635271a94b9a6d1392de5bb323a7
22+
with:
23+
go-version-file: 'go.mod'
24+
25+
- name: Build the certgen binary
26+
run: |
27+
go build -o certgen .
28+
29+
- name: Create the configuration file
30+
run: |
31+
cat <<EOF > config.yaml
32+
certs:
33+
- name: foo
34+
namespace: ladybird
35+
commonName: foo.cilium.io
36+
hosts:
37+
- foo.cilium.io
38+
- qux.cilium.io
39+
- 192.0.2.237
40+
usage:
41+
- signing
42+
- key encipherment
43+
- server auth
44+
validity: 24h
45+
- name: bar
46+
namespace: ladybird
47+
commonName: bar.cilium.io
48+
usage:
49+
- signing
50+
- key encipherment
51+
- client auth
52+
validity: 3h
53+
EOF
54+
55+
- name: Run and test
56+
run: |
57+
assert_equal() {
58+
local got=$1
59+
local expected=$2
60+
61+
if [[ "$got" != "$expected" ]]; then
62+
echo "Equality assertion failed:"
63+
echo "- expected: $expected"
64+
echo "- got: $got"
65+
return 1
66+
fi
67+
68+
return 0
69+
}
70+
71+
assert_not_equal() {
72+
local first="$1"
73+
local second="$2"
74+
75+
if [[ "$first" == "$second" ]]; then
76+
echo "Inequality assertion failed:"
77+
echo "- first: $first"
78+
echo "- second: $second"
79+
return 1
80+
fi
81+
82+
return 0
83+
}
84+
85+
assert_foo_cert() {
86+
local crt="$1"
87+
88+
openssl verify -CAfile ca.crt ${crt}
89+
90+
assert_equal "$(openssl x509 -subject -noout -in ${crt})" "subject=CN = foo.cilium.io"
91+
assert_equal "$(openssl x509 -ext subjectAltName -noout -in ${crt} | tail -n 1 | sed 's/^ *//')" "DNS:foo.cilium.io, DNS:qux.cilium.io, IP Address:192.0.2.237"
92+
assert_equal "$(openssl x509 -ext keyUsage -noout -in ${crt} | tail -n 1 | sed 's/^ *//' )" "Digital Signature, Key Encipherment"
93+
assert_equal "$(openssl x509 -ext extendedKeyUsage -noout -in ${crt} | tail -n 1 | sed 's/^ *//' )" "TLS Web Server Authentication"
94+
95+
openssl x509 -checkend 85800 -noout -in ${crt} # 25h50m
96+
openssl x509 -checkend 87000 -noout -in ${crt} && exit 1 # 24h10m
97+
98+
return 0
99+
}
100+
101+
assert_bar_cert() {
102+
local crt="$1"
103+
104+
openssl verify -CAfile ca.crt ${crt}
105+
106+
assert_equal "$(openssl x509 -subject -noout -in ${crt})" "subject=CN = bar.cilium.io"
107+
assert_equal "$(openssl x509 -ext subjectAltName -noout -in ${crt})" ""
108+
assert_equal "$(openssl x509 -ext keyUsage -noout -in ${crt} | tail -n 1 | sed 's/^ *//' )" "Digital Signature, Key Encipherment"
109+
assert_equal "$(openssl x509 -ext extendedKeyUsage -noout -in ${crt} | tail -n 1 | sed 's/^ *//' )" "TLS Web Client Authentication"
110+
111+
openssl x509 -checkend 10200 -noout -in ${crt} # 2h50m
112+
openssl x509 -checkend 11400 -noout -in ${crt} && exit 1 # 3h10m
113+
114+
return 0
115+
}
116+
117+
118+
# Create the target namespaces
119+
kubectl create namespace weasel
120+
kubectl create namespace ladybird
121+
122+
echo
123+
echo "Generating certificates"
124+
./certgen \
125+
--k8s-kubeconfig-path=${HOME}/.kube/config \
126+
--ca-generate --ca-reuse-secret \
127+
--ca-secret-namespace=weasel \
128+
--ca-secret-name=the-ca \
129+
--ca-common-name="The CA" \
130+
--ca-validity-duration=48h \
131+
--config-file=config.yaml
132+
133+
echo
134+
echo "Retrieving and verifying CA certificate"
135+
kubectl get secret -n weasel the-ca --template='{{ index .data "ca.crt" }}' | base64 -d > ca.crt
136+
openssl x509 -text -noout -in ca.crt
137+
openssl verify -CAfile ca.crt ca.crt
138+
139+
assert_equal "$(openssl x509 -subject -noout -in ca.crt)" "subject=CN = The CA"
140+
openssl x509 -checkend 172200 -noout -in ca.crt # 47h50m
141+
openssl x509 -checkend 173400 -noout -in ca.crt && exit 1 # 48h10m
142+
143+
echo
144+
echo "Retrieving and verifying 'foo' certificate"
145+
kubectl get secret -n ladybird foo --template='{{ index .data "tls.crt" }}' | base64 -d > foo.crt
146+
kubectl get secret -n ladybird foo --template='{{ index .data "ca.crt" }}' | base64 -d > foo.ca.crt
147+
openssl x509 -text -noout -in foo.crt
148+
assert_foo_cert foo.crt
149+
assert_equal "$(cat foo.ca.crt)" "$(cat ca.crt)"
150+
151+
echo
152+
echo "Retrieving and verifying 'bar' certificate"
153+
kubectl get secret -n ladybird bar --template='{{ index .data "tls.crt" }}' | base64 -d > bar.crt
154+
kubectl get secret -n ladybird bar --template='{{ index .data "ca.crt" }}' | base64 -d > bar.ca.crt
155+
openssl x509 -text -noout -in bar.crt
156+
assert_bar_cert bar.crt
157+
assert_equal "$(cat bar.ca.crt)" "$(cat ca.crt)"
158+
159+
echo
160+
echo "Regenerating certificates"
161+
CILIUM_CERTGEN_CONFIG="$(cat config.yaml)" ./certgen \
162+
--k8s-kubeconfig-path=${HOME}/.kube/config \
163+
--ca-generate --ca-reuse-secret \
164+
--ca-secret-namespace=weasel \
165+
--ca-secret-name=the-ca \
166+
--ca-common-name="The CA" \
167+
--ca-validity-duration=48h
168+
169+
echo
170+
echo "Retrieving and verifying CA certificate"
171+
kubectl get secret -n weasel the-ca --template='{{ index .data "ca.crt" }}' | base64 -d > ca.new.crt
172+
openssl x509 -text -noout -in ca.new.crt
173+
# The CA certificate should not have been regenerated
174+
assert_equal "$(cat ca.new.crt)" "$(cat ca.crt)"
175+
176+
echo
177+
echo "Retrieving and verifying 'foo' certificate"
178+
kubectl get secret -n ladybird foo --template='{{ index .data "tls.crt" }}' | base64 -d > foo.new.crt
179+
kubectl get secret -n ladybird foo --template='{{ index .data "ca.crt" }}' | base64 -d > bar.ca.crt
180+
openssl x509 -text -noout -in foo.new.crt
181+
# The foo certificate should have been regenerated
182+
assert_not_equal "$(openssl x509 -serial -noout -in foo.crt)" "$(openssl x509 -serial -noout -in foo.new.crt)"
183+
assert_foo_cert foo.new.crt
184+
assert_equal "$(cat foo.ca.crt)" "$(cat ca.crt)"
185+
186+
echo
187+
echo "Retrieving and verifying 'bar' certificate"
188+
kubectl get secret -n ladybird bar --template='{{ index .data "tls.crt" }}' | base64 -d > bar.new.crt
189+
kubectl get secret -n ladybird bar --template='{{ index .data "ca.crt" }}' | base64 -d > bar.ca.crt
190+
openssl x509 -text -noout -in bar.new.crt
191+
# The bar certificate should have been regenerated
192+
assert_not_equal "$(openssl x509 -serial -noout -in bar.crt)" "$(openssl x509 -serial -noout -in bar.new.crt)"
193+
assert_bar_cert bar.new.crt
194+
assert_equal "$(cat bar.ca.crt)" "$(cat ca.crt)"

0 commit comments

Comments
 (0)