Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 13 additions & 6 deletions .github/scripts/install-asdecided.sh
Original file line number Diff line number Diff line change
@@ -1,15 +1,22 @@
#!/usr/bin/env bash
set -euo pipefail

version="${1:-0.23.1}"
version="${1:-0.26.0}"
version="${version#v}"
if [[ "$version" != "0.23.1" ]]; then
echo "::error::No verified checksum is recorded for asdecided-core $version"
exit 1
fi

archive="asdecided-x86_64-unknown-linux-gnu.tar.gz"
digest="51cce8025a7cb2f8b2caea93a8ea71be0ad8c5c316fd0ecced688267bf97b8ac"
case "$version" in
0.23.1)
digest="51cce8025a7cb2f8b2caea93a8ea71be0ad8c5c316fd0ecced688267bf97b8ac"
;;
0.26.0)
digest="4d7f2fa85686af8d1006aa530928f60e2cd3d13d8560b303495f2784d1b8bbed"
;;
*)
echo "::error::No verified checksum is recorded for asdecided-core $version"
exit 1
;;
esac
install_dir="${RUNNER_TEMP}/asdecided-${version}"
download="${RUNNER_TEMP}/${archive}"
url="https://github.com/asdecided/core/releases/download/v${version}/${archive}"
Expand Down
9 changes: 6 additions & 3 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -32,14 +32,14 @@ jobs:
cache: pip

- name: Install AsDecided (external CLI on PATH, never an import)
run: bash .github/scripts/install-asdecided.sh 0.23.1
run: bash .github/scripts/install-asdecided.sh 0.26.0

- name: Install the harness
run: pip install -e ".[dev]"

- name: Validate every fixture corpus
run: |
for bench in search-artifacts find-decisions get-artifact get-related get-summary; do
for bench in search-artifacts find-decisions get-artifact get-related get-summary sentry; do
decided validate "$bench/corpus"
done

Expand All @@ -48,6 +48,9 @@ jobs:

- name: Gate every benchmark against its committed baseline
run: |
for bench in search-artifacts find-decisions get-artifact get-related get-summary; do
for bench in search-artifacts find-decisions get-artifact get-related get-summary sentry; do
python "$bench/run.py" --check
done

- name: Verify Sentry at the supported 5,000-decision scale
run: python sentry/run.py --scale --corpus-size 5000
1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ corpus.
| [`get-artifact/`](get-artifact/) | Exact-id resolution contract: alias and case-insensitive hits, duplicate and not-found error shapes. Conformance gated at 1.0. |
| [`get-related/`](get-related/) | Relationship-edge retrieval: exact incoming AND outgoing edge sets per artifact. Conformance gated at 1.0. |
| [`get-summary/`](get-summary/) | Portfolio summary contract: counts by type, empty-corpus shape, byte stability. Conformance gated at 1.0. |
| [`sentry/`](sentry/) | Deterministic decision-to-code enforcement: 80 contract cases plus generated 5,000-decision scale evidence for recall, clean-pass behaviour, attribution, diff isolation, SARIF, gate parity, and byte determinism. |
| [`gitchameleon/`](gitchameleon/) | External evidence run (scaffold): does grounding in recorded version-pin decisions improve version-correct codegen on GitChameleon 2.0? Upstream executable-test scoring; never a merge gate. |

## Shared harness
Expand Down
84 changes: 84 additions & 0 deletions sentry/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
# SentryBench

SentryBench evaluates whether AsDecided's deterministic code enforcement
blocks known decision violations without blocking compliant or unrelated code.
It consumes the published `decided` CLI as an external process and never
imports Core.

This is not a retrieval benchmark. It scores enforcement correctness:

- `forbid_pattern`, `require_pattern`, and `forbid_import`
- SQL, Python, Rust, JavaScript/TypeScript, and unsupported-language failure
- full-tree certification and Git diff isolation
- invalid constraint fail-closed behaviour
- decision, rule, path, and line attribution in Sentry JSON
- SARIF source locations
- `decided sentry` / `decided gate --code` parity over their shared projection
- byte-identical JSON on repeated unchanged runs

The frozen set contains 80 contract cases, including 38 seeded violations,
multi-finding and ordering cases, diff-isolation edges, fail-closed behaviour,
and close-neighbour allow cases.

The committed fixture includes an eligible constrained decision, an explicitly
ineligible decision, and an intentionally unclassified decision. Coverage is
asserted but remains distinct from correctness.

## Run

```sh
python3 sentry/run.py
python3 sentry/run.py --json
python3 sentry/run.py --check
```

Set `RAC_BIN` to test a particular native executable:

```sh
RAC_BIN=/path/to/decided python3 sentry/run.py --check
```

## Supported-scale evidence

The scale profile deterministically generates a 5,000-decision corpus, then
checks clean and violating full-tree runs, a violating diff, composed-gate
parity, attribution, coverage accounting, and byte stability:

```sh
python3 sentry/run.py --scale
python3 sentry/run.py --scale --corpus-size 5000
```

The generated corpus is temporary: the repository does not carry 5,000
low-information fixture files. The profile reports elapsed time for each
surface, but correctness does not depend on a wall-clock threshold.

## Performance evidence

Timing is deliberately outside the scored metrics block:

```sh
python3 sentry/run.py --performance --iterations 30
```

This reports median, p95, minimum, and maximum engine time for a clean
full-tree profile and a violating diff profile. It does not gate CI until a
controlled runner profile and stable scale matrix are committed.

## Known boundary

`decided gate --code` does not yet expose Sentry's decision and rule
provenance. Parity therefore compares the public fields shared by both
surfaces: outcome, coverage, code, path, and line. The dedicated Sentry JSON
remains authoritative for decision and rule attribution.

## Gate

Every correctness metric is gated at `1.0` with zero tolerance. Baselines may
only be updated through the explicit, human-reviewed command:

```sh
python3 sentry/run.py --update-baseline
```

See `decisions/` and `requirements/` for the benchmark's governing contract.
55 changes: 55 additions & 0 deletions sentry/baseline.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
{
"overall": {
"conformance": 1.0,
"cases_passed": 80,
"cases_total": 80,
"negative_violations": 0,
"violation_recall": 1.0,
"clean_pass_rate": 1.0,
"attribution_accuracy": 1.0,
"sarif_accuracy": 1.0,
"gate_parity": 1.0,
"byte_determinism": 1.0
},
"by_category": {
"clean": {
"conformance": 1.0
},
"coverage": {
"conformance": 1.0
},
"diff_isolation": {
"conformance": 1.0
},
"fail_closed": {
"conformance": 1.0
},
"forbid_import_javascript": {
"conformance": 1.0
},
"forbid_import_python": {
"conformance": 1.0
},
"forbid_import_rust": {
"conformance": 1.0
},
"forbid_pattern": {
"conformance": 1.0
},
"invalid_constraint": {
"conformance": 1.0
},
"multi_finding": {
"conformance": 1.0
},
"reporting": {
"conformance": 1.0
},
"require_pattern": {
"conformance": 1.0
},
"unsupported_language": {
"conformance": 1.0
}
}
}
Loading
Loading