Skip to content

Commit

Permalink
fix: handle expired certificates
Browse files Browse the repository at this point in the history
  • Loading branch information
adityathebe authored and moshloop committed Oct 23, 2024
1 parent 7f44e56 commit d0d9cf8
Show file tree
Hide file tree
Showing 3 changed files with 60 additions and 13 deletions.
33 changes: 21 additions & 12 deletions pkg/health/health_cert_manager.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,36 +16,45 @@ func SetDefaultCertificateExpiryWarningPeriod(p time.Duration) {
}

func GetCertificateHealth(obj *unstructured.Unstructured) (*HealthStatus, error) {
if _renewalTime, ok := obj.Object["status"].(map[string]any)["renewalTime"]; ok {
if renewalTimeString := _renewalTime.(string); ok {
renewalTime, err := time.Parse(time.RFC3339, renewalTimeString)
if _notAfter, ok := obj.Object["status"].(map[string]any)["notAfter"]; ok {
if notAfter := _notAfter.(string); ok {
notAfterTime, err := time.Parse(time.RFC3339, notAfter)
if err != nil {
return nil, fmt.Errorf("failed to parse renewal time (%s): %v", renewalTimeString, err)
return nil, fmt.Errorf("failed to parse notAfter time(%s): %v", notAfter, err)
}

if time.Since(renewalTime) > time.Minute*5 {
if notAfterTime.Before(time.Now()) {
return &HealthStatus{
Health: HealthUnhealthy,
Status: "Expired",
Message: "Certificate has expired",
Ready: true,
}, nil
}

if time.Until(notAfterTime) < defaultCertExpiryWarningPeriod {
return &HealthStatus{
Health: HealthWarning,
Status: HealthStatusWarning,
Message: fmt.Sprintf("Certificate should have been renewed at %s", renewalTimeString),
Message: fmt.Sprintf("Certificate is expiring soon (%s)", notAfter),
Ready: true,
}, nil
}
}
}

if _notAfter, ok := obj.Object["status"].(map[string]any)["notAfter"]; ok {
if notAfter := _notAfter.(string); ok {
notAfterTime, err := time.Parse(time.RFC3339, notAfter)
if _renewalTime, ok := obj.Object["status"].(map[string]any)["renewalTime"]; ok {
if renewalTimeString := _renewalTime.(string); ok {
renewalTime, err := time.Parse(time.RFC3339, renewalTimeString)
if err != nil {
return nil, fmt.Errorf("failed to parse notAfter time(%s): %v", notAfter, err)
return nil, fmt.Errorf("failed to parse renewal time (%s): %v", renewalTimeString, err)
}

if time.Until(notAfterTime) < defaultCertExpiryWarningPeriod {
if time.Since(renewalTime) > time.Minute*5 {
return &HealthStatus{
Health: HealthWarning,
Status: HealthStatusWarning,
Message: fmt.Sprintf("Certificate is expiring soon (%s)", notAfter),
Message: fmt.Sprintf("Certificate should have been renewed at %s", renewalTimeString),
Ready: true,
}, nil
}
Expand Down
7 changes: 6 additions & 1 deletion pkg/health/health_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -84,7 +84,12 @@ func TestNamespace(t *testing.T) {
}

func TestCertificate(t *testing.T) {
assertAppHealth(t, "./testdata/about-to-expire.yaml", "Warning", health.HealthWarning, true)
assertAppHealth(t, "./testdata/certificate-expired.yaml", "Expired", health.HealthUnhealthy, true)

assertAppHealthWithOverwrite(t, "./testdata/about-to-expire.yaml", map[string]string{
"2024-06-26T12:25:46Z": time.Now().Add(time.Hour).UTC().Format("2006-01-02T15:04:05Z"),
}, health.HealthStatusWarning, health.HealthWarning, true)

assertAppHealth(t, "./testdata/certificate-healthy.yaml", "Issued", health.HealthHealthy, true)
b := "../resource_customizations/cert-manager.io/Certificate/testdata/"
assertAppHealth(t, b+"degraded_configError.yaml", "ConfigError", health.HealthUnhealthy, true)
Expand Down
33 changes: 33 additions & 0 deletions pkg/health/testdata/certificate-expired.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
apiVersion: cert-manager.io/v1
kind: Certificate
metadata:
creationTimestamp: "2023-12-01T10:15:32Z"
generation: 1
labels:
kustomize.toolkit.fluxcd.io/name: nginx
kustomize.toolkit.fluxcd.io/namespace: flux-system
name: expired-homelab-cert
namespace: nginx-ingress
resourceVersion: "32456789"
uid: 9e45b2c8-156d-42a1-bc34-7d592f3a1e4d
spec:
commonName: home.flanksource.com
dnsNames:
- home.flanksource.com
- "*.home.flanksource.com"
issuerRef:
kind: ClusterIssuer
name: letsencrypt-production
secretName: expired-homelab-cert
status:
conditions:
- lastTransitionTime: "2024-01-01T10:15:38Z"
message: Certificate has expired
observedGeneration: 1
reason: Expired
status: "False"
type: Ready
notAfter: "2024-01-01T10:15:37Z"
notBefore: "2023-12-01T10:15:38Z"
renewalTime: "2024-01-01T10:15:37Z"
revision: 1

0 comments on commit d0d9cf8

Please sign in to comment.