{"record":{"id":"688dbd952af439c3","repo":"valyala/fasthttp","slug":"cannot-load-tls-key-pair-from-cert-file-q-and-key","errorCode":null,"errorMessage":"cannot load tls key pair from cert file=%q and key file=%q: %w","messagePattern":"cannot load tls key pair from cert file=%q and key file=%q: %w","errorType":"error_code","errorClass":null,"httpStatus":null,"severity":"error","filePath":"server.go","lineNumber":1931,"sourceCode":"\tif err != nil {\n\t\treturn err\n\t}\n\n\ts.mu.Lock()\n\ts.appendCertLocked(&cert)\n\ts.mu.Unlock()\n\n\treturn nil\n}\n\nfunc loadX509KeyPair(certFile, keyFile string) (tls.Certificate, error) {\n\tif certFile == \"\" && keyFile == \"\" {\n\t\treturn tls.Certificate{}, errNoCertOrKeyProvided\n\t}\n\n\tcert, err := tls.LoadX509KeyPair(certFile, keyFile)\n\tif err != nil {\n\t\treturn tls.Certificate{}, fmt.Errorf(\"cannot load tls key pair from cert file=%q and key file=%q: %w\", certFile, keyFile, err)\n\t}\n\treturn cert, nil\n}\n\n// AppendCertEmbed does the same as AppendCert but using in-memory data.\nfunc (s *Server) AppendCertEmbed(certData, keyData []byte) error {\n\tcert, err := x509KeyPair(certData, keyData)\n\tif err != nil {\n\t\treturn err\n\t}\n\n\ts.mu.Lock()\n\ts.appendCertLocked(&cert)\n\ts.mu.Unlock()\n\n\treturn nil\n}\n","sourceCodeStart":1913,"sourceCodeEnd":1949,"githubUrl":"https://github.com/valyala/fasthttp/blob/c96f600972c6f4a7a30d664257b340ebe9d60124/server.go#L1913-L1949","documentation":"Returned by Server.AppendCert when tls.LoadX509KeyPair fails to read or parse the certificate and key files. The library wraps the crypto/tls error with both file paths so misconfigured TLS assets are easy to diagnose. The server cannot enable TLS without a valid key pair.","triggerScenarios":"Calling AppendCert (or ListenAndServeTLS configuration paths) with certFile/keyFile paths that don't exist, are unreadable (permissions), contain invalid PEM, have a key that doesn't match the certificate, or are expired/malformed certificates.","commonSituations":"Typo in cert/key paths relative to the working directory; secrets mounted with wrong permissions in Kubernetes; concatenating fullchain incorrectly; key regenerated while cert stayed old (mismatch); Let's Encrypt renewal replaced files while old data cached.","solutions":["Verify both files exist and are readable by the server user (ls -l; fix paths/permissions).","Validate the pair offline: openssl x509 -noout -modulus -in cert; openssl rsa -noout -modulus -in key — confirm hashes match.","Ensure the cert file contains the full chain in PEM format and the key is PEM (not DER/encrypted without handling).","Renew/replace the certificate if expired, and redeploy both files together."],"exampleFix":"// before\napp.AppendCert(\"/etc/certs/cert.pem\", \"/etc/certs/key.pem\") // key mismatch\n// after\n# regenerate matching pair, then:\nerr := app.AppendCert(\"/etc/certs/fullchain.pem\", \"/etc/certs/privkey.pem\")\nif err != nil { log.Fatal(err) }","handlingStrategy":"validation","validationCode":"func validateCertFiles(certFile, keyFile string) error {\n    cert, err := os.ReadFile(certFile)\n    if err != nil { return fmt.Errorf(\"cert unreadable: %w\", err) }\n    key, err := os.ReadFile(keyFile)\n    if err != nil { return fmt.Errorf(\"key unreadable: %w\", err) }\n    if _, err := tls.X509KeyPair(cert, key); err != nil {\n        return fmt.Errorf(\"invalid pair: %w\", err)\n    }\n    return nil\n}","typeGuard":null,"tryCatchPattern":"if err := app.AppendCert(certFile, keyFile); err != nil {\n    if strings.Contains(err.Error(), \"cannot load tls key pair\") {\n        log.Fatalf(\"check cert/key paths, permissions, and matching pair: %v\", err)\n    }\n    log.Fatal(err)\n}","preventionTips":["Pre-validate cert/key with openssl or tls.X509KeyPair in CI.","Mount secrets with correct permissions and paths in orchestrators.","Always deploy cert and key together as one versioned unit.","Use fullchain PEM for certs; monitor expiry and rotate proactively."],"tags":["go","tls","certificates"],"backgroundTag":"tls-key-pair-load-failed","analyzedSha":"c96f600972c6f4a7a30d664257b340ebe9d60124","analyzedAt":"2026-08-31T22:48:28.265Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-08T05:18:18.240Z"}