feat: export admission violations from validation webhook - #4716
Open
JaydipGabani wants to merge 6 commits into
Open
feat: export admission violations from validation webhook#4716JaydipGabani wants to merge 6 commits into
JaydipGabani wants to merge 6 commits into
Conversation
Track audit and webhook publishing independently and bound status errors. Signed-off-by: Jaydip Gabani <gabanijaydip@gmail.com>
Publish violations asynchronously with bounded memory, shutdown, and metrics. Signed-off-by: Jaydip Gabani <gabanijaydip@gmail.com>
Store admission violations in bounded, recoverable JSONL segments. Signed-off-by: Jaydip Gabani <gabanijaydip@gmail.com>
Export validated webhook results through the shared connection and channel. Signed-off-by: Jaydip Gabani <gabanijaydip@gmail.com>
Add disk-only Helm wiring, reader support, and end-to-end coverage. Signed-off-by: Jaydip Gabani <gabanijaydip@gmail.com>
Document delivery, limits, status, metrics, and disk lifecycle. Signed-off-by: Jaydip Gabani <gabanijaydip@gmail.com>
Contributor
There was a problem hiding this comment.
Pull request overview
Adds best-effort admission violation export through the existing export system, with asynchronous queuing, disk spooling, source-specific status, deployment support, and observability.
Changes:
- Adds bounded asynchronous webhook export and disk-backed admission segments.
- Separates audit and webhook publishing status.
- Adds Helm wiring, metrics, documentation, and end-to-end coverage.
Reviewed changes
Copilot reviewed 56 out of 57 changed files in this pull request and generated 3 comments.
Show a summary per file
| File | Description |
|---|---|
website/docs/metrics.md |
Documents export metrics. |
website/docs/export.md |
Documents admission export behavior. |
test/export/fake-reader/main.go |
Adds admission segment consumption. |
test/export/fake-reader/main_test.go |
Tests reader selection and deletion. |
test/export/denied_pod.yaml |
Adds denied-request fixture. |
test/bats/test.bats |
Exercises admission export end-to-end. |
test/bats/helpers.bash |
Adds export test helpers. |
pkg/webhook/webhook.go |
Injects export dependencies. |
pkg/webhook/stats_reporter.go |
Adds queue and publishing metrics. |
pkg/webhook/stats_reporter_test.go |
Tests new metrics. |
pkg/webhook/policy.go |
Exports validation results. |
pkg/webhook/policy_test.go |
Tests admission payloads. |
pkg/webhook/export.go |
Implements bounded asynchronous publishing. |
pkg/webhook/export_test.go |
Tests queue and shutdown behavior. |
pkg/export/util/util.go |
Extends messages and error aggregation. |
pkg/export/util/util_test.go |
Tests flags and error bounds. |
pkg/export/system_test.go |
Tests shared disk routing. |
pkg/export/disk/admission_file.go |
Implements admission disk spooling. |
pkg/export/disk/admission_file_test.go |
Tests spool lifecycle and recovery. |
pkg/export/disk/test_helpers_test.go |
Updates disk test helpers. |
pkg/export/disk/disk.go |
Integrates admission records into disk driver. |
pkg/export/disk/connection_test.go |
Updates connection lifecycle tests. |
pkg/export/disk/config.go |
Refactors connection configuration. |
pkg/export/disk/config_test.go |
Tests admission defaults. |
pkg/export/disk/cleanup.go |
Extends combined file cleanup. |
pkg/export/disk/cleanup_test.go |
Tests bounded failed cleanup. |
pkg/export/disk/audit_file.go |
Isolates audit retention. |
pkg/export/disk/audit_file_test.go |
Tests admission-file exclusion. |
pkg/controller/export/export_connection_controller.go |
Adds source-specific status updates. |
pkg/controller/export/export_connection_controller_test.go |
Tests status merging and conflicts. |
pkg/controller/connectionstatus/connectionstatus_controller_test.go |
Tests aggregated status shape. |
pkg/audit/manager.go |
Reports audit-specific publishing status. |
pkg/audit/manager_test.go |
Tests audit status reporting. |
manifest_staging/deploy/gatekeeper.yaml |
Updates generated CRDs. |
manifest_staging/charts/gatekeeper/values.yaml |
Adds admission chart settings. |
manifest_staging/charts/gatekeeper/templates/gatekeeper-controller-manager-deployment.yaml |
Deploys exporter volume and reader. |
manifest_staging/charts/gatekeeper/templates/gatekeeper-audit-violation-export-connection.yaml |
Creates shared disk connection. |
manifest_staging/charts/gatekeeper/README.md |
Documents chart values. |
manifest_staging/charts/gatekeeper/crds/connectionpodstatus-customresourcedefinition.yaml |
Updates pod-status schema. |
manifest_staging/charts/gatekeeper/crds/connection-customresourcedefinition.yaml |
Updates connection status schema. |
Makefile |
Adds admission export deployment options. |
main.go |
Wires exporter dependencies. |
go.mod |
Promotes filesystem dependency. |
docs/design/README.md |
Links the design proposal. |
docs/design/admission-violation-export.md |
Defines architecture and semantics. |
config/crd/bases/status.gatekeeper.sh_connectionpodstatuses.yaml |
Updates source CRD schema. |
config/crd/bases/connection.gatekeeper.sh_connections.yaml |
Updates connection CRD schema. |
cmd/build/helmify/static/values.yaml |
Adds source Helm values. |
cmd/build/helmify/static/templates/gatekeeper-audit-violation-export-connection.yaml |
Updates source connection template. |
cmd/build/helmify/static/README.md |
Documents source chart values. |
cmd/build/helmify/replacements.go |
Adds admission argument substitution. |
cmd/build/helmify/main.go |
Generates volume and sidecar wiring. |
cmd/build/helmify/kustomize-for-helm.yaml |
Adds Helm substitution marker. |
apis/status/v1alpha1/zz_generated.deepcopy.go |
Updates generated deep copies. |
apis/status/v1alpha1/connectionpodstatus_types.go |
Defines source-specific status API. |
apis/status/v1alpha1/connectionpodstatus_types_test.go |
Tests status deep copying. |
.github/workflows/disk-export.yaml |
Expands disk export CI coverage. |
Files not reviewed (1)
- apis/status/v1alpha1/zz_generated.deepcopy.go: Generated file
Comment on lines
+244
to
+246
| if conn.admission.cleanupTimer == nil { | ||
| if err := conn.recoverAdmissionFiles(); err != nil { | ||
| return fmt.Errorf("recovering admission files for connection %s: %w", connectionName, err) |
| $(HELM_EXPORT_ARGS) \ | ||
| $(if $(filter disk,$(EXPORT_BACKEND)),$(HELM_DISK_EXPORT_ARGS)) \ | ||
| $(if $(filter dapr,$(EXPORT_BACKEND)),$(HELM_DAPR_EXPORT_ARGS)) \ | ||
| $(if $(and $(filter true,$(ENABLE_EXPORT)),$(filter disk,$(EXPORT_BACKEND))),$(HELM_DISK_EXPORT_ARGS)) \ |
Comment on lines
+93
to
+97
| var auditErr error | ||
| if conn.File != nil { | ||
| auditErr = conn.unlockAndCloseFile() | ||
| } | ||
| return errors.Join(auditErr, conn.closeAdmissionStream(finalizeAdmission)) |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What this PR does / why we need it:
Exports valid constraint violations produced by the validating webhook, including denied requests that are never persisted and request identity unavailable to audit.
Admission handling marshals each violation and attempts a non-blocking enqueue into a per-pod queue bounded at 1,024 messages and 16 MiB. A manager runnable publishes queued records asynchronously through the existing export system, so backend latency and failure cannot change the admission decision. Delivery is best-effort: each publish is attempted once, overload and shutdown loss are reported through metrics and rate-limited logs, and complete encoded JSON records over 64 KiB are dropped rather than truncated.
The supported alpha backend is disk. Admission records use separately prefixed JSONL segments with bounded rotation, retention, free-space protection, file locking, and recovery of complete records from abandoned segments. Audit and admission reuse one
Connection, channel, path, and volume while their files and cleanup remain isolated.This also changes the alpha
ConnectionPodStatusshape: aggregateactiveanderrorsfields are replaced byconnectionErrorsand a source-keyedpublishStatuseslist forauditandwebhook. Each publisher updates only its own entry, so one source cannot clear the other source's failures. Error arrays and in-memory publish error classes are bounded at 500 entries.Helm generator source, staging manifests, the demonstration disk reader, end-to-end coverage, metrics, user documentation, and a design document are included.
Which issue(s) this PR fixes (optional, using
fixes #<issue number>(, fixes #<issue_number>, ...)format, will close the issue(s) when the PR gets merged):Fixes #2798
Special notes for your reviewer:
Start with
docs/design/admission-violation-export.md, then review the commits in order:feat: separate export status by sourcefeat: add admission export queuefeat: add admission disk spoolfeat: wire admission violation exportfeat: deploy admission violation exportdocs: describe admission violation exportAlpha limitations and operator behavior:
exportBackend: disk; Helm rejects other backends.ExportMsg, including details, annotations, labels, and request metadata.emptyDirsurvives a container restart but loses unconsumed records when the pod is replaced.cmd/build/helmify; generated review artifacts are undermanifest_staging. Rootchartsanddeployoutputs are unchanged.Validation:
make native-testgo test -race ./pkg/webhook ./pkg/export/... ./pkg/controller/export ./pkg/audit -count=1make lintmake manifests generatewith a clean tree afterwardcmd/build/helmify/staticandmanifest_staging/charts/gatekeeper