crewforth 3.1.0 → 3.2.0-rc.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +151 -0
- package/README.md +4 -3
- package/VERSION +1 -1
- package/adopt.sh +91 -11
- package/kit/AGENT_TEMPLATE.md +2 -1
- package/kit/CLAUDE.md +9 -8
- package/kit/agents/crew-commit-agent.md +7 -2
- package/kit/agents/crew-docs-agent.md +71 -0
- package/kit/agents/crew-planner.md +2 -0
- package/kit/agents/crew-refuter.md +77 -0
- package/kit/agents/crew-security-expert.md +3 -1
- package/kit/agents/crew-session-manager.md +11 -9
- package/kit/eval/doctor.sh +91 -3
- package/kit/eval/golden-routing.txt +9 -0
- package/kit/eval/lib/crew-map/crew-map.sh +26 -0
- package/kit/eval/lib/crew-map/detect.mjs +238 -0
- package/kit/eval/lib/crew-map/narrative.mjs +98 -0
- package/kit/eval/lib/crew-map/parse.mjs +305 -0
- package/kit/eval/lib/crew-map/project.mjs +163 -0
- package/kit/eval/lib/crew-map/rules/names.json +38 -0
- package/kit/eval/lib/crew-map/rules/packages.json +142 -0
- package/kit/eval/lib/crew-map/rules/python-stdlib.json +197 -0
- package/kit/eval/lib/crew-map/scan.mjs +214 -0
- package/kit/eval/lib/crew-map/stacks.mjs +441 -0
- package/kit/eval/lib/crew-map/surface.mjs +457 -0
- package/kit/eval/lib/findings/findings.mjs +410 -0
- package/kit/eval/lib/findings/findings.schema.json +122 -0
- package/kit/eval/lib/findings/findings.sh +29 -0
- package/kit/eval/lib/settings-json.awk +5 -0
- package/kit/eval/lib/star.sh +23 -7
- package/kit/eval/lib/statusline.settings.json +6 -0
- package/kit/eval/lib/statusline.sh +115 -0
- package/kit/eval/smoke-test.sh +465 -38
- package/kit/hooks/agent-outcome.sh +6 -3
- package/kit/hooks/guard-agent-model.sh +15 -5
- package/kit/hooks/guard-bash.sh +240 -182
- package/kit/hooks/guard-question.sh +73 -0
- package/kit/hooks/guard-write.sh +21 -0
- package/kit/hooks/prompt-approval.sh +320 -103
- package/kit/hooks/refuter-ledger.sh +80 -0
- package/kit/owned-blobs.tsv +4 -1
- package/kit/settings.json +33 -0
- package/kit/skills/crew-approve/SKILL.md +7 -0
- package/kit/skills/crew-doctor/SKILL.md +5 -1
- package/kit/skills/crew-handoff/SKILL.md +3 -2
- package/kit/skills/crew-map/SKILL.md +44 -0
- package/kit/skills/crew-review/SKILL.md +2 -0
- package/kit/skills/crew-update/SKILL.md +1 -1
- package/kit/skills/incident-runbook/SKILL.md +2 -2
- package/kit/skills/security-scan/references/verify.md +6 -3
- package/kit/studio/README.md +12 -0
- package/kit/studio/server/index.js +114 -11
- package/kit/studio/server/lib/crew-map.js +113 -0
- package/kit/studio/server/lib/model-outcomes.js +130 -15
- package/kit/studio/server/lib/pricing.js +3 -0
- package/kit/studio/server/lib/remote.js +99 -0
- package/kit/studio/server/lib/usage.js +74 -14
- package/kit/studio/web/app.js +214 -12
- package/kit/studio/web/canvas.js +44 -120
- package/kit/studio/web/graph-plan.js +10 -4
- package/kit/studio/web/index.html +10 -5
- package/kit/studio/web/map-plan.js +341 -0
- package/kit/studio/web/map.js +503 -0
- package/kit/studio/web/models-plan.js +61 -7
- package/kit/studio/web/models.js +19 -3
- package/kit/studio/web/style.css +125 -0
- package/kit/studio/web/usage.js +12 -0
- package/kit/studio/web/viewport.js +160 -0
- package/package.json +6 -5
- package/start.sh +10 -0
|
@@ -19,7 +19,8 @@
|
|
|
19
19
|
# -> blocked: not run, nothing concluded.
|
|
20
20
|
# not finished in CREW_VERIFY_TIMEOUT seconds (540)
|
|
21
21
|
# -> timeout: stopped, nothing concluded.
|
|
22
|
-
# Then one line is added to .claude/state/model-outcomes.tsv,
|
|
22
|
+
# Then one line is added to .claude/state/model-outcomes.tsv, its last column the gate's reason
|
|
23
|
+
# when the work is critical (risk_why, "-" when it is not), and the class is looked at:
|
|
23
24
|
# where the first try failed too often, its floor goes one model up (crew-model-floors.auto).
|
|
24
25
|
# Only ever up: lowering a floor is the user's decision and nothing here does it.
|
|
25
26
|
# PostToolUse (Agent) a foreground call has come back. If its verify failed, or its report closed with
|
|
@@ -280,6 +281,8 @@ case "$EV" in
|
|
|
280
281
|
_am_rec_get "$REC" verify; VCMD="$_AMV"
|
|
281
282
|
_am_rec_get "$REC" agent; AG="$_AMV"; _am_rec_get "$REC" change; CH="$_AMV"; _am_rec_get "$REC" risk; RK="$_AMV"
|
|
282
283
|
_am_rec_get "$REC" card; CID="$_AMV"; _am_rec_get "$REC" esc; ESC="${_AMV:--}"
|
|
284
|
+
# A record written before the gate kept its reason has none: that is "-", not a reason made up here.
|
|
285
|
+
_am_rec_get "$REC" why; RW="${_AMV:--}"; RW="${RW//$'\t'/ }"
|
|
283
286
|
_am_rec_get "$REC" asked || _am_rec_get "$REC" tier; ASK="$_AMV"
|
|
284
287
|
mkdir -p "$_AMD/results" "$_AMD/tries" "$_AMD/fails" 2>/dev/null || exit 0
|
|
285
288
|
TRIES=0; [ -f "$_AMD/tries/$AID" ] && IFS= read -r TRIES < "$_AMD/tries/$AID"; case "$TRIES" in ''|*[!0-9]*) TRIES=0 ;; esac
|
|
@@ -359,10 +362,10 @@ case "$EV" in
|
|
|
359
362
|
printf 'verify=%s\nfixes=%s\nconfidence=%s\ntier=%s\nesc=%s\nescalate=%s\nwhynot=%s\ncmd=%s\n' "$RES" "$TRIES" "$CONF" "$ASK" "$ESC" "$ESCL" "$WHYNOT" "$VCMD" > "$_AMD/results/$AID" 2>/dev/null
|
|
360
363
|
case "$REC" in "$_AMD/pending/"*) rm -f "$REC" 2>/dev/null ;; *) : > "$REC.used" 2>/dev/null ;; esac
|
|
361
364
|
TSV="$_AMS/model-outcomes.tsv"
|
|
362
|
-
[ -s "$TSV" ] || printf 'ts\tagent_id\tagent\tchange\trisk\tcard\tmodel\tverify\tfixes\tescalated_from\tran_on\tconfidence\n' > "$TSV" 2>/dev/null
|
|
365
|
+
[ -s "$TSV" ] || printf 'ts\tagent_id\tagent\tchange\trisk\tcard\tmodel\tverify\tfixes\tescalated_from\tran_on\tconfidence\trisk_why\n' > "$TSV" 2>/dev/null
|
|
363
366
|
_ao_now
|
|
364
367
|
_ao_lock
|
|
365
|
-
printf '%s\t%s\t%s\t%s\t%s\t%s\t%s\t%s\t%s\t%s\t%s\t%s\n' "$_AON" "$AID" "$AG" "$CH" "$RK" "$CID" "$ASK" "$RES" "$TRIES" "$ESC" "$RAN" "$CONF" >> "$TSV" 2>/dev/null
|
|
368
|
+
printf '%s\t%s\t%s\t%s\t%s\t%s\t%s\t%s\t%s\t%s\t%s\t%s\t%s\n' "$_AON" "$AID" "$AG" "$CH" "$RK" "$CID" "$ASK" "$RES" "$TRIES" "$ESC" "$RAN" "$CONF" "$RW" >> "$TSV" 2>/dev/null
|
|
366
369
|
_ao_unlock
|
|
367
370
|
case "$RES" in pass|fail) _ao_calibrate "$AG" "$CH" "$RK" ;; esac
|
|
368
371
|
exit 0 ;;
|
|
@@ -357,9 +357,13 @@ _am_tier(){ # $1 = a model as a call or a transcript names it -> _AMT haiku|son
|
|
|
357
357
|
# a .sql file, schema.prisma. The path is read from the project's root down, so the name of the folder the project
|
|
358
358
|
# sits in decides nothing. .claude/crew-model-rules, which only the user writes, adds (`+ glob`) and removes
|
|
359
359
|
# (`- glob`); the last line that matches wins.
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
360
|
+
# Legal and personal-data texts are critical too (crew-docs-agent's work): legal, privacy, consent in every form, and
|
|
361
|
+
# terms only in lower case — `terms/`, `terms-of-service.md` — because the camelCase `searchTerms` is a search box.
|
|
362
|
+
# Store listings are critical by place and only as text: under store/, store-listing/, fastlane/metadata/ or
|
|
363
|
+
# metadata/android|ios/, a .txt .md .xml .yml .yaml is; code there (a Redux `store/index.ts`) and images are not.
|
|
364
|
+
_AM_W_L='auth|authn|authz|authentication|authorization|oauth|payments?|billing|migrations?|security|crypto|secrets?|legal|privacy|terms|consent'
|
|
365
|
+
_AM_W_C='Auth|Authn|Authz|Authentication|Authorization|OAuth|Payments?|Billing|Migrations?|Security|Crypto|Secrets?|Legal|Privacy|Consent'
|
|
366
|
+
_AM_W_U='AUTH|AUTHN|AUTHZ|OAUTH|PAYMENTS?|BILLING|MIGRATIONS?|SECURITY|CRYPTO|SECRETS?|LEGAL|PRIVACY|TERMS|CONSENT'
|
|
363
367
|
_AM_RE_L="(^|[^A-Za-z])($_AM_W_L)([^a-z]|\$)"
|
|
364
368
|
_AM_RE_C="(^|[^A-Z])($_AM_W_C)([^a-z]|\$)"
|
|
365
369
|
_AM_RE_U="(^|[^A-Za-z])($_AM_W_U)([^A-Za-z]|\$)"
|
|
@@ -394,7 +398,10 @@ _am_crit_path(){ # $1 = a path or a glob -> 0 critical (_AMW says by what), 1 n
|
|
|
394
398
|
local p r k g hit=1
|
|
395
399
|
_am_rel "$1"; p="$_AMRP"; _AMW=""
|
|
396
400
|
if [[ "$p" =~ $_AM_RE_L ]] || [[ "$p" =~ $_AM_RE_C ]] || [[ "$p" =~ $_AM_RE_U ]]; then hit=0; _AMW="${BASH_REMATCH[2]}"
|
|
397
|
-
else case "$p" in *.sql|*.SQL) hit=0; _AMW="a .sql file" ;; schema.prisma|*/schema.prisma) hit=0; _AMW="schema.prisma" ;;
|
|
401
|
+
else case "$p" in *.sql|*.SQL) hit=0; _AMW="a .sql file" ;; schema.prisma|*/schema.prisma) hit=0; _AMW="schema.prisma" ;;
|
|
402
|
+
store/*|*/store/*|store-listing/*|*/store-listing/*|fastlane/metadata/*|*/fastlane/metadata/*|metadata/android/*|*/metadata/android/*|metadata/ios/*|*/metadata/ios/*)
|
|
403
|
+
case "$p" in *.txt|*.md|*.xml|*.yml|*.yaml) hit=0; _AMW="a store listing text" ;; esac ;;
|
|
404
|
+
esac; fi
|
|
398
405
|
_am_rules
|
|
399
406
|
for r in ${_AM_RULES[@]+"${_AM_RULES[@]}"}; do
|
|
400
407
|
k="${r%%$'\t'*}"; g="${r#*$'\t'}"
|
|
@@ -818,7 +825,10 @@ fi
|
|
|
818
825
|
_json_slice "$INPUT" tool_use_id >/dev/null; tid="$_JS"; case "$tid" in ''|*[!A-Za-z0-9._-]*) tid="x$RANDOM" ;; esac
|
|
819
826
|
if mkdir -p "$_AMD/pending" 2>/dev/null; then
|
|
820
827
|
if [ "${BASH_VERSINFO[0]}" -ge 5 ] || { [ "${BASH_VERSINFO[0]}" -eq 4 ] && [ "${BASH_VERSINFO[1]}" -ge 2 ]; }; then printf -v t '%(%s)T' -1; else t="$(date +%s)"; fi
|
|
821
|
-
|
|
828
|
+
# Why the work counts as critical, as the gate decided it, so a reader shows the reason and does not work it out
|
|
829
|
+
# again: one line, no tab (it ends up in a column of model-outcomes.tsv).
|
|
830
|
+
rw="${CARD_RISKWHY:--}"; rw="${rw//$'\t'/ }"; rw="${rw//$'\r'/ }"; rw="${rw//$'\n'/ }"
|
|
831
|
+
{ printf 'agent=%s\ntier=%s\nchange=%s\nrisk=%s\ncard=%s\nbg=%s\nesc=%s\nverify=%s\nfiles=%s\nwhy=%s\n' "$st" "$m" "$CARD_CHANGE" "$CARD_RISK" "$CARD_ID" "$bg" "${p:--}" "$CARD_VERIFY" "$CARD_FILES" "$rw" > "$_AMD/pending/$t-$tid"; } 2>/dev/null || true
|
|
822
832
|
fi
|
|
823
833
|
exit 0
|
|
824
834
|
}
|