Add TLS handling updates#7
Conversation
…oyments The private TLS certificate and CA bundle are now only required when dependency endpoints are configured (mTLS needed for TEE-to-TEE communication) or when no public certificate is set. A TEE that only serves external Internet clients can now operate with just a public certificate, avoiding the overhead of maintaining private TLS infrastructure that would otherwise go unused. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
…port When connecting to a dependency over HTTPS, the server's leaf certificate fingerprint observed during the TLS handshake is now compared against data.tls.private in the dependency's attestation report. This binds the attestation to the actual TLS connection, catching relay proxies that hold a valid CA-signed cert but are not the TEE — independent of Envoy's XFCC forwarding policy. Skipped for plain HTTP endpoints where resp.TLS is nil (transparent proxy to Envoy on loopback). Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
|
Caution Review failedPull request was closed or merged during review WalkthroughThis pull request adds HTTPS server-leaf-certificate binding to dependency attestation: when a dependency is fetched over HTTPS the server computes SHA-256(resp.TLS.PeerCertificates[0].Raw) and requires it to equal report.data.tls.private; the check is skipped for plain HTTP (no TLS state). TLS config validation was made conditional: a private TLS cert/key/CA is required when dependency endpoints are configured or when no public cert is present; public/private validations run only when their paths are provided. TLS certificate verification errors are treated as non-transient (mapped to the non-503 error path). Error handler behavior was changed to preserve handler-controlled fiber.NewError messages for 5xx responses. Documentation and tests were updated. Sequence Diagram(s)sequenceDiagram
participant Client as Attestation Client
participant Server as Attestation Server
participant Dep as Dependency Service
participant TLS as TLS Layer
Client->>Server: Request attestation / trigger dependency fetch
Server->>Dep: HTTP(S) request to dependency
alt HTTPS
Note right of Dep: TLS handshake
Dep-->>TLS: Send leaf certificate
TLS->>Server: Provide resp.TLS with PeerCertificates[0].Raw
Server->>Server: Compute SHA-256(resp.TLS.PeerCertificates[0].Raw) -> serverCertFP
Dep-->>Server: Attestation report (report.data.tls.private + data.tls.client + evidence)
Server->>Server: Require report.data.tls.private == serverCertFP
else HTTP (no TLS)
Dep-->>Server: Attestation report (no server TLS state)
Server->>Server: Skip serverCertFP check
end
Server->>Server: Verify client cert fingerprint (data.tls.client) and nonce and crypto evidence
alt all checks pass
Server-->>Client: Success (verified)
else any e2e or crypto failure
Server-->>Client: E2E verification error (opaque to caller)
end
Estimated code review effort🎯 4 (Complex) | ⏱️ ~45 minutes Poem
🚥 Pre-merge checks | ✅ 1 | ❌ 2❌ Failed checks (1 warning, 1 inconclusive)
✅ Passed checks (1 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches📝 Generate docstrings
🧪 Generate unit tests (beta)
Comment |
There was a problem hiding this comment.
🧹 Nitpick comments (1)
internal/server.go (1)
126-128: Clarify warning scope to include HTTPS dependency server-cert bindingNice addition. Consider mentioning that HTTPS dependency server-certificate binding is also unavailable in this mode, to fully reflect the new verification model.
Suggested wording tweak
- logger.Warn("running without private TLS certificate, dependency mTLS and XFCC client certificate proof are unavailable") + logger.Warn("running without private TLS certificate, dependency mTLS/XFCC client-certificate proof and HTTPS dependency server-certificate binding are unavailable")🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@internal/server.go` around lines 126 - 128, The warning in the Private TLS cert check (the if block testing cfg.PrivateTLSCertPath == "") is incomplete; update the logger.Warn message in internal/server.go to explicitly include that HTTPS dependency server-certificate binding is also unavailable in this mode (alongside dependency mTLS and XFCC client certificate proof), so the warning fully reflects the verification model change.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.
Nitpick comments:
In `@internal/server.go`:
- Around line 126-128: The warning in the Private TLS cert check (the if block
testing cfg.PrivateTLSCertPath == "") is incomplete; update the logger.Warn
message in internal/server.go to explicitly include that HTTPS dependency
server-certificate binding is also unavailable in this mode (alongside
dependency mTLS and XFCC client certificate proof), so the warning fully
reflects the verification model change.
ℹ️ Review info
⚙️ Run configuration
Configuration used: Organization UI
Review profile: CHILL
Plan: Pro
Run ID: fb88d5b0-ee0a-4952-be35-de0fe05ea71b
📒 Files selected for processing (11)
CLAUDE.mdREADME.mddocs/architecture.mddocs/security.mddocs/verification.mdinternal/attestation_test.gointernal/dependencies.gointernal/dependencies_test.gointernal/server.gointernal/tls.gointernal/tls_test.go
TLS certificate verification errors (expired cert, unknown CA, hostname mismatch) are configuration problems, not transient connectivity issues. classifyNetError now checks for *tls.CertificateVerificationError before the *url.Error catch-all, so these errors fall through to 500 instead of being misclassified as *errConnection (503). Transport-level errors (connection refused, reset, DNS) continue to map to 503. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
There was a problem hiding this comment.
🧹 Nitpick comments (1)
internal/dependencies_test.go (1)
211-306: Consider extracting a small helper for report setup in server-cert tests.The repeated construction of
AttestationReportData/AttestationReportis a bit verbose; a helper would reduce duplication and make intent even clearer.🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@internal/dependencies_test.go` around lines 211 - 306, Extract a small test helper to build AttestationReport/AttestationReportData to remove duplication in the server-cert tests: create a function (e.g., makeReportWithTLS or newTestReport) that accepts nonceHex, clientFP, privateFP (allowing empty string), and blob bytes and returns (*AttestationReport, *AttestationReportData or its JSON); then replace repeated inline constructions in TestVerifyDependencyReport_ServerCertSkippedWhenEmpty, TestVerifyDependencyReport_ServerCertMismatch, TestVerifyDependencyReport_ServerCertMissing, and TestVerifyDependencyReport_ServerCertMatch with calls to that helper and reuse reportDataWithClientCert where appropriate; ensure the returned report.Data is set to json.RawMessage of the marshaled report data and the Evidence contains the same fake blob used in the tests so existing verifyDependencyReportOnly calls continue to behave the same.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.
Nitpick comments:
In `@internal/dependencies_test.go`:
- Around line 211-306: Extract a small test helper to build
AttestationReport/AttestationReportData to remove duplication in the server-cert
tests: create a function (e.g., makeReportWithTLS or newTestReport) that accepts
nonceHex, clientFP, privateFP (allowing empty string), and blob bytes and
returns (*AttestationReport, *AttestationReportData or its JSON); then replace
repeated inline constructions in
TestVerifyDependencyReport_ServerCertSkippedWhenEmpty,
TestVerifyDependencyReport_ServerCertMismatch,
TestVerifyDependencyReport_ServerCertMissing, and
TestVerifyDependencyReport_ServerCertMatch with calls to that helper and reuse
reportDataWithClientCert where appropriate; ensure the returned report.Data is
set to json.RawMessage of the marshaled report data and the Evidence contains
the same fake blob used in the tests so existing verifyDependencyReportOnly
calls continue to behave the same.
ℹ️ Review info
⚙️ Run configuration
Configuration used: Organization UI
Review profile: CHILL
Plan: Pro
Run ID: 04b75eb5-6b9c-410a-af1d-02045f777bf4
📒 Files selected for processing (3)
docs/security.mdinternal/dependencies.gointernal/dependencies_test.go
🚧 Files skipped from review as they are similar to previous changes (1)
- internal/dependencies.go
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
The error handler previously replaced all 5xx messages with a generic "internal error". Handler code already uses opaque messages like "attestation failed" and "dependency attestation failed" in fiber.NewError calls, so stripping them hid useful context from callers without adding security value. Now fiberErr.Message is preserved for all status codes. Unhandled errors (plain error values) still fall back to "internal error". Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
|
@coderabbitai full review |
✅ Actions performedFull review triggered. |
Summary by CodeRabbit
New Features
Bug Fixes
Documentation