JuliusBrussee/caveman · error

secretbox: payload KMS decrypt: %w

Error message

secretbox: payload KMS decrypt: %w

What it means

DecryptPayloadKey's KMS path (kms.DecryptPayload) failed within its 10-second timeout while unwrapping an artifact data-encryption key. The KMS envelope is restricted to the payload KEK and the legacy secrets key; the wrapped error states whether this is a transport failure or a key-permission problem.

Source

Thrown at shared/platform/secretbox/secretbox.go:151

	}
	nonce, ct := envelope[:ns], envelope[ns:]
	plain, err := gcm.Open(nil, nonce, ct, nil)
	if err != nil {
		return nil, fmt.Errorf("aes-gcm open: %w", err)
	}
	return plain, nil
}

// DecryptPayloadKey unwraps an artifact data-encryption key. KMS envelopes are
// restricted to the configured payload key plus the explicit legacy secrets
// key used before key separation.
func DecryptPayloadKey(envelope []byte) ([]byte, error) {
	if kms.IsEnvelope(envelope) {
		ctx, cancel := context.WithTimeout(context.Background(), 10*time.Second)
		defer cancel()
		plaintext, err := kms.DecryptPayload(ctx, envelope)
		if err != nil {
			return nil, fmt.Errorf("secretbox: payload KMS decrypt: %w", err)
		}
		return plaintext, nil
	}
	return Decrypt(envelope)
}

func useKMS() bool {
	return strings.EqualFold(strings.TrimSpace(os.Getenv("CAVE_KMS_PROVIDER")), kms.ProviderScaleway)
}

// ResolveEnvironmentSecret loads a boot-time secret. In production plaintext
// environment variables are rejected: operators must provide a base64-encoded
// secretbox/KMS envelope in ciphertextEnv. Local development may continue using
// plaintextEnv. An entirely absent optional secret returns an empty string.
func ResolveEnvironmentSecret(plaintextEnv, ciphertextEnv string) (string, error) {
	plain := strings.TrimSpace(os.Getenv(plaintextEnv))
	encoded := strings.TrimSpace(os.Getenv(ciphertextEnv))
	production := runtimeenv.IsProduction()

View on GitHub (pinned to 766dce6b13)

Solutions

  1. Retry the unwrap — transient KMS errors are common under load
  2. Verify the envelope was sealed with the payload KEK or the allowed legacy key, not another KMS key
  3. Check credentials and key enablement in Scaleway for the payload key
  4. If the KEK was rotated, ensure decryption access to the prior key version during transition
Defensive patterns

Strategy: retry

When it happens

Trigger: Thrown at shared/platform/secretbox/secretbox.go:151 when the library encounters an invalid state.

Common situations: See trigger scenarios.


AI-assisted analysis of JuliusBrussee/caveman@766dce6b13 (2026-08-18). Data as JSON: /api/errors/89462ca9c00208bd. Report an issue: GitHub.