59d837f6e7
The v1.25 kyverno-json engine adapter and policies were authored but never
validated against the real `kj` binary — the test suite
`pytest.skip("kj not installed")` when `kj` was absent, masking the bug.
With `kj` v0.0.3 now installed, the 3 failing-fixture tests
(stack-ir/plan-json/regression) showed 0 fails (all passed falsely). Root
causes (3 substrate bugs) and fixes:
1. ENGINE — bare-list output format. `kj scan --output json` emits a bare
JSON LIST at the top level (NOT `{"results": [...]}`); each entry has
`resource` + `results[].rules[]` with `violations[]` (fail) / `error`
string (eval error) / neither (pass). The v1.25 `_translate` did
`out.get("results", [])` on a dict → `out` is a list → returned `[]` →
emitted a single KJ_NO_RESULTS pass PCR. Rewrote `_translate` to parse
the real v0.0.3 nested shape (policy.metadata.name, rule.name,
violations[].errors[].field/detail/value). Future-proofs to also accept
the legacy dict shape. Preserves RESULT_MAP, severity-from-annotation,
is_configured(), _skipped_not_configured, _error_pcr, the temp-file
payload write, and the subprocess invocation.
2. ENGINE — `.json` policies not loaded by `kj`. The upstream loader
(pkg/policy/load.go) uses fileinfo.IsYaml() which only matches
`.yaml`/`.yml` — `.json` files are silently skipped (0 policies).
Nova policies are authored as `.json` (TestPolicyFilesExist asserts the
filenames). Added `_materialize_yaml_policy_dir`: mirrors the source
tree to a temp dir, copying every `.json` policy to a `.yaml` twin
(JSON is a valid YAML subset, verified against kj v0.0.3). Source
`.json` files remain untouched.
3. POLICIES — `validate` wrapper + check syntax. Removed the `validate`
wrapper from all 16 policies (kj v0.0.3 ignores `validate`-wrapped
rules — `assert` goes directly under the rule). Fixed the check syntax:
a check entry is `expression: expected_value` (e.g.
`(regex_match(..., @)): true`), not `field: (expression)` (which
compared a bool to nothing → "types not comparable"). For per-resource
checks over stack-IR/plan-JSON, `~.resources` (descendant anchor) is
required for per-element iteration; a plain path applies to the whole
array. For type-scoped rules (s3/ebs encryption, iam/db/kms), the type
guard is folded into the expression (`type == '...' && !<has-prop>`)
so non-matching resources short-circuit to false. cap-013 dedup uses
`max(map(&length(@), values(group_by(adapters, &@)))) == `1`` (no
`duplicates` JMESPath fn exists). Preserved all policy metadata
(apiVersion, kind, metadata.name, severity + title annotations) —
TestPolicyValidity/TestPolicyFilesExist still pass.
INSTALL SCRIPT — the v1.25 `go install .../cmd/kj@latest` failed: the
`cmd/kj` path does not exist in v0.0.3 (upstream produces a binary named
`kyverno-json`). Fixed to `go install github.com/kyverno/kyverno-json@latest`
+ symlink `kyverno-json` → `kj` (GOBIN and /usr/local/bin fallbacks).
Idempotent: short-circuits when `kj` is already on PATH and working.
Verification: `which kj` → /usr/local/bin/kj; `kj version` → v0.0.3.
test_kyverno_json_engine + test_stack_ir_policies + test_plan_json_policies
+ test_meta_policies + test_regression_policies: 36 passed, 0 skips
(_require_kj no longer skips). Full suite (excluding pre-existing hang in
test_verify_regression_mode.py): 776 passed, 6 failed — all 6 failures are
pre-existing (confirmed by stashing this commit's diff and re-running);
the only in-scope-acceptable failure is
test_module_standards.py::test_all_l1_have_required_files (dynamodb
extension drift, data-engineer's later wave).
---ci---
project: acdl
phase: 3
milestone: v1.26
status: execute
wave: W0.5
---
65 lines
2.5 KiB
Bash
65 lines
2.5 KiB
Bash
#!/usr/bin/env bash
|
|
# scripts/install-kyverno-json.sh — install the kj CLI (v1.25, REQ-294;
|
|
# fixed v1.26 P3 W0.5).
|
|
#
|
|
# Installs the kyverno-json CLI via `go install` (D-115). The binary is a
|
|
# Go project — not a Python package. Cached via the Go module cache.
|
|
#
|
|
# v1.26 P3 W0.5 fix: the v1.25 script ran
|
|
# go install github.com/kyverno/kyverno-json/cmd/kj@latest
|
|
# but the `cmd/kj` path does NOT exist in v0.0.3 — the upstream
|
|
# `go install github.com/kyverno/kyverno-json@latest` produces a binary
|
|
# named `kyverno-json`, NOT `kj`. The v1.25 invocation failed silently
|
|
# (the test suite masked it via `pytest.skip("kj not installed")`). This
|
|
# script now installs the real module and symlinks `kyverno-json` → `kj`
|
|
# so the engine's `which kj` check passes.
|
|
#
|
|
# Usage: bash scripts/install-kyverno-json.sh
|
|
# Exits 0 on success, 1 if Go is not installed, 2 if `kj version` fails.
|
|
set -euo pipefail
|
|
|
|
if ! command -v go >/dev/null 2>&1; then
|
|
echo "ERROR: Go toolchain not found. Install Go (https://go.dev/dl/) first." >&2
|
|
echo " kyverno-json is a Go binary — \`go install\` is the upstream-blessed path (D-115)." >&2
|
|
exit 1
|
|
fi
|
|
|
|
GOBIN="${GOBIN:-${HOME}/go/bin}"
|
|
|
|
# Idempotent: if kj is already on PATH and working, short-circuit.
|
|
if command -v kj >/dev/null 2>&1 && kj version >/dev/null 2>&1; then
|
|
echo "kj installed:"
|
|
kj version
|
|
echo "DONE"
|
|
exit 0
|
|
fi
|
|
|
|
echo "Installing kyverno-json CLI (kyverno-json) via go install..."
|
|
# The upstream module produces a binary named `kyverno-json` (NOT `kj`).
|
|
# The v1.25 `go install .../cmd/kj@latest` path does not exist in v0.0.3.
|
|
go install github.com/kyverno/kyverno-json@latest
|
|
|
|
# The binary is named `kyverno-json`, not `kj`. Symlink it as `kj` for
|
|
# the engine's `which kj` check (kyverno_json_engine.py::_which_kj).
|
|
if [ -x "${GOBIN}/kyverno-json" ] && ! command -v kj >/dev/null 2>&1; then
|
|
ln -sf "${GOBIN}/kyverno-json" "${GOBIN}/kj"
|
|
# If GOBIN not on PATH, try /usr/local/bin so `which kj` resolves.
|
|
if ! command -v kj >/dev/null 2>&1; then
|
|
ln -sf "${GOBIN}/kyverno-json" /usr/local/bin/kj 2>/dev/null || true
|
|
fi
|
|
fi
|
|
|
|
if ! command -v kj >/dev/null 2>&1; then
|
|
if [ -x "${GOBIN}/kyverno-json" ]; then
|
|
echo "kyverno-json installed to ${GOBIN}/kyverno-json but 'kj' is not on PATH." >&2
|
|
echo "add ${GOBIN} to PATH or symlink: ln -sf ${GOBIN}/kyverno-json /usr/local/bin/kj" >&2
|
|
"${GOBIN}/kyverno-json" version
|
|
exit 0
|
|
fi
|
|
echo "ERROR: kj not found on PATH after go install (checked ${GOBIN})." >&2
|
|
exit 2
|
|
fi
|
|
|
|
echo "kj installed:"
|
|
kj version
|
|
echo "DONE" |