Repository navigation
test(e2e): prove cert-manager gets a CryptOS certificate over ACME in kind - #294
Merged
Merged
Conversation
… kind Stand up a Root and an ACME-serving Intermediate in-process with the e2e harness (software keys, embedded etcd, no TPM) and let cert-manager in a kind cluster enrol against it with an External Account Binding and an http-01 solver behind Contour. The test checks that the Certificate goes Ready, the chain verifies to the CryptOS root, the SANs are the requested name, the node recorded the serial, the ingress serves it, and a forced renewal yields a new, recorded serial. The handler the test drives is the one the boot serves: the ACME wiring in the boot moves into cinit.NewACMEHandler, and the issued-set recorder is exported as cinit.IssuedRecorder, with no change in behaviour. task e2e:kind runs it on a Linux host with docker and skips without one. The ci-kind-acme workflow runs it on pull requests that touch the ACME path. kind, kubectl, the node image, cert-manager, Contour and the test app are pinned by checksum or digest in test/kind/versions.env. Signed-off-by: Bugs5382 <12115015+Bugs5382@users.noreply.github.com>
Bugs5382
marked this pull request as ready for review
September 30, 2026 09:57
Bugs5382
added a commit
to CryptOS-PKI/docs
that referenced
this pull request
Sep 30, 2026
Add a note to the Kubernetes page that every cryptos pull request touching the ACME code runs cert-manager in a kind cluster against an intermediate, what that test checks, and that the node there runs from the code with software keys rather than from the OS image. Depends on CryptOS-PKI/cryptos-node#294 and should merge after it. Signed-off-by: Bugs5382 <12115015+Bugs5382@users.noreply.github.com>
2 tasks done
Contributor
Author
|
Closing summary: a CI job proves a real Kubernetes client gets a real CryptOS certificate over ACME: the e2e harness runs a Root and an Intermediate with the production ACME handler, and cert-manager in a pinned kind cluster issues and renews a P-384 certificate that chains to the root and shows in the node's issued set. Runs on PRs touching ACME, and locally as task e2e:kind. Closes #293. |
7 tasks
Bugs5382
added a commit
to CryptOS-PKI/docs
that referenced
this pull request
Sep 30, 2026
Add a note to the Kubernetes page that every cryptos pull request touching the ACME code runs cert-manager in a kind cluster against an intermediate, what that test checks, and that the node there runs from the code with software keys rather than from the OS image. Depends on CryptOS-PKI/cryptos-node#294 and should merge after it. Signed-off-by: Bugs5382 <12115015+Bugs5382@users.noreply.github.com>
Merged
4 tasks done
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What and why
Nothing in CI showed that a real Kubernetes client can get a certificate from CryptOS over ACME. This adds a kind job that does exactly that.
pki.acmeblock with an External Account Binding key and goes throughconfig.Parse. The handler is built bycinit.NewACMEHandler, the same function the boot now calls, with the realHTTP01Validatorand the production issued-set recorder. A small TLS front on the kind bridge address proxies to the plain-HTTP ACME origin, the deploymentdocs/acme.mddescribes. Its certificate is issued by the Intermediate, so the cluster trusts it through the root it gets ascaBundle.traefik/whoami. AClusterIssuerpoints at the node with EAB and an http-01 solver through Contour. ACertificateasks for an ECDSA P-384 key.tls.crtverifies to the CryptOS root for the name; the SANs are exactly that name;tls.keymatches the leaf; the serial is in the node's issued set under the ACME profile with the same DER; the ingress serves that serial over HTTPS. A forced renewal (Issuing=True on the status, which is whatcmctl renewdoes) gives a new serial, and the same checks run again./etc/hosts(one line, added and removed by the script) to127.0.0.1:80, which kind maps to Envoy. cert-manager's in-cluster self-check resolves it through a CoreDNShostsentry pointing at Envoy's service. The validator and port 80 are untouched.bootintoNewACMEHandler, which returns the same errors and uses the same validator, andissuedRecorderis exported asIssuedRecorder. The two renamed call sites ininternal/inittests are mechanical.task e2e:kind(Linux with docker) runstest/kind/run.sh. It skips with a message on non-Linux, without docker, or when the pinned kind can't be downloaded. The Go test skips unless the script setsCRYPTOS_E2E_KIND=1, sotask testis unaffected.ci-kind-acme.ymlruns on pull requests only, touchinginternal/acme,internal/config,internal/node,internal/e2e,internal/init/acme.go,test/kindor the workflow itself. It skips drafts, has a 25-minute timeout, runs onubuntu-latestand is not a required check.test/kind/versions.env): kind v0.33.0 and kubectl v1.37.0 by SHA-256 (amd64 and arm64),kindest/node:v1.37.0by digest, cert-manager v1.21.2 and Contour v1.33.7 manifests by SHA-256, andtraefik/whoami:v1.12.0by digest.Design calls:
main, not stacked on feat(config): switch ACME and EST on and off through machine config #286. The test uses the YAMLpki.acmeblock, whichconfig.Parsealready reads onmain. feat(config): switch ACME and EST on and off through machine config #286 changes how the block travels in the proto config, and this test doesn't depend on that.Closes #293
No docs change on the docs site in this PR. Once this merges, a short "Tested in CI with kind and cert-manager" note goes on the Kubernetes use-case page (CryptOS-PKI/docs#31). The repo README lists the new task and workflow.
Verification
golangci-lintv2.12.2,go vet,gofmt,actionlint,shellcheck)go test ./...)task e2e:kind, the CI list)How this was verified
go test ./...passes locally, includinginternal/initafter the refactor.golang.org/x/crypto/acmeclient with EAB and a real http-01 responder on port 80. The directory, account, order, challenge, finalize and download all went through the TLS front, the chain verified to the root, and the serial was in the issued set.ci-kind-acmejob.