Skip to main content

Key Manager Extension

The Key Manager Extension allows you to delegate key management operations to an external service via an HTTPS webhook. Use this to integrate with HSMs, KMSs, or key management systems not natively supported by SPIRL.

How it works

The Trust Domain Server calls the extension webhook for each key operation — key creation, public key retrieval, signing, and key release. The webhook is responsible for managing key material and returning results. The Trust Domain Server never receives or stores private key bytes.

How to Deploy

Step 1 — Implement the Webhook

The extension must implement the following REST endpoints:

POST /keys

Create a new key. The Trust Domain Server calls this when it needs to generate a new signing key.

Request:

{
"key_id": "signing-key-2026-01",
"key_type": "EC-P256"
}

Response (HTTP 201):

{
"public_key": "-----BEGIN PUBLIC KEY-----\nMFkwEwYH....\n-----END PUBLIC KEY-----",
"fingerprint": "sha256:a1b2c3d4e5f6..."
}

GET /keys

List all keys managed by this extension.

Response:

{
"keys": [
{
"key_id": "signing-key-2026-01",
"public_key": "-----BEGIN PUBLIC KEY-----\nMFkwEwYH....\n-----END PUBLIC KEY-----",
"fingerprint": "sha256:a1b2c3d4e5f6..."
}
]
}

POST /keys/{id}/sign

Sign data with the specified key.

Request:

{
"digest": "<base64-encoded digest>",
"hash_algorithm": "SHA-256"
}

Response:

{
"signature": "<base64-encoded signature>",
"key_fingerprint": "sha256:a1b2c3d4e5f6..."
}

POST /keys/{id}/release

Indicate that a key is no longer in active use and may be deleted after a grace period.

Request body: empty

Response: 200 OK

Step 2 — Update cluster configuration

section: KeyManager
schema: v1
spec:
extensions:
webhook:
webhookURL: "https://my-kms-bridge.internal/key-manager"
caCertPath: /etc/spirl/kms-ca.pem
timeout: "10s"

Apply it using spirlctl:

spirlctl config set trust-domain-deployment --id <deployment-id> key-manager.yaml

Or using Terraform:

resource "spirl_cluster_config" "key_manager" {
cluster_id = spirl_cluster.my_cluster.id
sections = {
KeyManager = <<-YAML
section: KeyManager
schema: v1
spec:
extensions:
webhook:
webhookURL: "https://my-kms-bridge.internal/key-manager"
timeout: "10s"
YAML
}
}

Once a configuration document passes validation and is stored, the Defakto control plane syncs it to your Trust Domain Servers automatically. No server or agent restart is required.

Configuration Reference

FieldRequiredDefaultDescription
webhookURLYesBase URL of the key manager extension (HTTP or HTTPS). Endpoint paths are appended automatically.
authTypeNononeAuthentication type for outbound requests: none or bearer.
tokenPathNo/var/run/secrets/kubernetes.io/serviceaccount/tokenPath to a file containing the bearer token. Required when authType is bearer.
timeoutNo30sPer-request timeout in Go duration format (e.g. 10s, 1m).
caCertPathNoPath to a PEM file containing custom CA certificates for TLS verification of the webhook endpoint. When empty, the system root certificates are used.

Step 3 — Verify

On startup, the Trust Domain Server calls GET /keys to discover existing keys. Check the Trust Domain Server logs to confirm the extension was initialized and keys were discovered.

Security Considerations

  • TLS required. The webhook must be served over HTTPS. Use caCertPath for private CAs.
  • Webhook availability. The Trust Domain Server cannot sign SVIDs if the webhook is unreachable. Ensure high availability and tune timeout accordingly.
  • Key release. Implement POST /keys/{id}/release correctly. Deleting a key before outstanding SVIDs expire will cause verification failures for relying parties.
  • Authentication. Implement mutual TLS or bearer token authentication on the webhook to prevent unauthorized key operations.