@wrongstack/plugins 0.292.1 → 0.295.0
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/README.md +7 -71
- package/dist/accessibility-auditor/index.d.ts +1 -1
- package/dist/accessibility-auditor/index.d.ts.map +1 -1
- package/dist/accessibility-auditor.js +31 -31
- package/dist/agent-handoff/index.d.ts +1 -1
- package/dist/agent-handoff/index.d.ts.map +1 -1
- package/dist/api-compatibility-gate/index.d.ts +1 -1
- package/dist/api-compatibility-gate/index.d.ts.map +1 -1
- package/dist/api-compatibility-gate.js +21 -16
- package/dist/audit/index.d.ts +386 -0
- package/dist/audit/index.d.ts.map +1 -0
- package/dist/audit.d.ts +1 -0
- package/dist/audit.js +454 -0
- package/dist/auto-doc/index.d.ts +1 -1
- package/dist/auto-doc/index.d.ts.map +1 -1
- package/dist/auto-escalate/index.d.ts +1 -1
- package/dist/auto-escalate/index.d.ts.map +1 -1
- package/dist/auto-i18n-extractor/index.d.ts +1 -1
- package/dist/auto-i18n-extractor/index.d.ts.map +1 -1
- package/dist/auto-i18n-extractor.js +2 -1
- package/dist/branch-guard/index.d.ts +1 -1
- package/dist/branch-guard/index.d.ts.map +1 -1
- package/dist/branch-guard.js +9 -1
- package/dist/catalog.d.ts +5 -30
- package/dist/catalog.d.ts.map +1 -1
- package/dist/changelog-writer/index.d.ts +1 -1
- package/dist/changelog-writer/index.d.ts.map +1 -1
- package/dist/checkpoint/index.d.ts +1 -1
- package/dist/checkpoint/index.d.ts.map +1 -1
- package/dist/checkpoint.js +7 -8
- package/dist/code-metrics/index.d.ts +1 -1
- package/dist/code-metrics/index.d.ts.map +1 -1
- package/dist/code-metrics.js +29 -29
- package/dist/commit-validator/index.d.ts +1 -1
- package/dist/commit-validator/index.d.ts.map +1 -1
- package/dist/config-validator/index.d.ts +1 -1
- package/dist/config-validator/index.d.ts.map +1 -1
- package/dist/context-pins/index.d.ts +1 -1
- package/dist/context-pins/index.d.ts.map +1 -1
- package/dist/cost-tracker/index.d.ts +1 -1
- package/dist/cost-tracker/index.d.ts.map +1 -1
- package/dist/cost-tracker.js +9 -2
- package/dist/cron/index.d.ts +1 -1
- package/dist/cron/index.d.ts.map +1 -1
- package/dist/dead-code-detector/index.d.ts +1 -1
- package/dist/dead-code-detector/index.d.ts.map +1 -1
- package/dist/dead-code-detector.js +26 -18
- package/dist/dep-guard/index.d.ts +1 -1
- package/dist/dep-guard/index.d.ts.map +1 -1
- package/dist/dependency-vulnerability-gate/index.d.ts +1 -1
- package/dist/dependency-vulnerability-gate/index.d.ts.map +1 -1
- package/dist/dependency-vulnerability-gate.js +34 -22
- package/dist/diff-summary/index.d.ts +1 -1
- package/dist/diff-summary/index.d.ts.map +1 -1
- package/dist/diff-summary.js +28 -29
- package/dist/doc-sync-guard/index.d.ts +1 -1
- package/dist/doc-sync-guard/index.d.ts.map +1 -1
- package/dist/doc-sync-guard.js +2 -1
- package/dist/duplicate-code-detector/index.d.ts +26 -1
- package/dist/duplicate-code-detector/index.d.ts.map +1 -1
- package/dist/duplicate-code-detector.js +178 -67
- package/dist/error-lens/index.d.ts +1 -1
- package/dist/error-lens/index.d.ts.map +1 -1
- package/dist/factories/index.d.ts +4 -0
- package/dist/factories/index.d.ts.map +1 -0
- package/dist/factories.d.ts +1 -0
- package/dist/factories.js +74 -0
- package/dist/feature-flag-tracker/index.d.ts +1 -1
- package/dist/feature-flag-tracker/index.d.ts.map +1 -1
- package/dist/feature-flag-tracker.js +29 -29
- package/dist/file-watcher/index.d.ts +1 -1
- package/dist/file-watcher/index.d.ts.map +1 -1
- package/dist/format-on-save/index.d.ts +1 -1
- package/dist/format-on-save/index.d.ts.map +1 -1
- package/dist/format-on-save.js +2 -1
- package/dist/generated-plugin-exports.d.ts +65 -0
- package/dist/generated-plugin-exports.d.ts.map +1 -0
- package/dist/git-autocommit/index.d.ts +1 -1
- package/dist/git-autocommit/index.d.ts.map +1 -1
- package/dist/import-organizer/index.d.ts +1 -1
- package/dist/import-organizer/index.d.ts.map +1 -1
- package/dist/import-organizer.js +2 -1
- package/dist/index.d.ts +4 -183
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +17675 -17377
- package/dist/injection-shield/index.d.ts +1 -1
- package/dist/injection-shield/index.d.ts.map +1 -1
- package/dist/interface-contract-guard/index.d.ts +1 -1
- package/dist/interface-contract-guard/index.d.ts.map +1 -1
- package/dist/interface-contract-guard.js +29 -29
- package/dist/knowledge-graph/index.d.ts +1 -1
- package/dist/knowledge-graph/index.d.ts.map +1 -1
- package/dist/license-audit-gate/index.d.ts +1 -1
- package/dist/license-audit-gate/index.d.ts.map +1 -1
- package/dist/lint-gate/index.d.ts +1 -1
- package/dist/lint-gate/index.d.ts.map +1 -1
- package/dist/lint-gate.js +10 -1
- package/dist/llm-cache/index.d.ts +5 -1
- package/dist/llm-cache/index.d.ts.map +1 -1
- package/dist/llm-cache.js +16 -8
- package/dist/loop-breaker/index.d.ts +1 -1
- package/dist/loop-breaker/index.d.ts.map +1 -1
- package/dist/loop-breaker.js +10 -4
- package/dist/manifest/index.d.ts +16 -0
- package/dist/manifest/index.d.ts.map +1 -0
- package/dist/manifest.d.ts +1 -0
- package/dist/manifest.js +152 -0
- package/dist/migration-planner/index.d.ts +1 -1
- package/dist/migration-planner/index.d.ts.map +1 -1
- package/dist/migration-planner.js +2 -1
- package/dist/model-router/index.d.ts +1 -1
- package/dist/model-router/index.d.ts.map +1 -1
- package/dist/notify-hub/index.d.ts +1 -1
- package/dist/notify-hub/index.d.ts.map +1 -1
- package/dist/notify-hub/webhook-channel.d.ts +1 -1
- package/dist/notify-hub/webhook-channel.d.ts.map +1 -1
- package/dist/path-guard/index.d.ts +1 -1
- package/dist/path-guard/index.d.ts.map +1 -1
- package/dist/performance-regression-gate/index.d.ts +1 -1
- package/dist/performance-regression-gate/index.d.ts.map +1 -1
- package/dist/plugin-stack-observer/index.d.ts +1 -1
- package/dist/plugin-stack-observer/index.d.ts.map +1 -1
- package/dist/pr-drafter/index.d.ts +1 -1
- package/dist/pr-drafter/index.d.ts.map +1 -1
- package/dist/pr-drafter.js +28 -29
- package/dist/process-guard/index.d.ts +1 -1
- package/dist/process-guard/index.d.ts.map +1 -1
- package/dist/prompt-firewall/index.d.ts +1 -1
- package/dist/prompt-firewall/index.d.ts.map +1 -1
- package/dist/refactor-suggester/index.d.ts +1 -1
- package/dist/refactor-suggester/index.d.ts.map +1 -1
- package/dist/refactor-suggester.js +29 -29
- package/dist/release-notes-generator/index.d.ts +1 -1
- package/dist/release-notes-generator/index.d.ts.map +1 -1
- package/dist/release-notes-generator.js +29 -22
- package/dist/runtime/index.d.ts +15 -0
- package/dist/runtime/index.d.ts.map +1 -1
- package/dist/runtime/llm.d.ts +1 -1
- package/dist/runtime/llm.d.ts.map +1 -1
- package/dist/runtime.js +43 -2
- package/dist/schema-evolution-guard/index.d.ts +1 -1
- package/dist/schema-evolution-guard/index.d.ts.map +1 -1
- package/dist/schema-evolution-guard.js +2 -1
- package/dist/secret-scanner/index.d.ts +1 -1
- package/dist/secret-scanner/index.d.ts.map +1 -1
- package/dist/secret-scanner.js +7 -1
- package/dist/security-hotspot-scanner/index.d.ts +1 -1
- package/dist/security-hotspot-scanner/index.d.ts.map +1 -1
- package/dist/security-hotspot-scanner.js +26 -19
- package/dist/semantic-search-indexer/index.d.ts +1 -1
- package/dist/semantic-search-indexer/index.d.ts.map +1 -1
- package/dist/semver-bump/index.d.ts +1 -1
- package/dist/semver-bump/index.d.ts.map +1 -1
- package/dist/semver-bump.js +78 -43
- package/dist/session-recap/index.d.ts +1 -1
- package/dist/session-recap/index.d.ts.map +1 -1
- package/dist/shell-check/index.d.ts +1 -1
- package/dist/shell-check/index.d.ts.map +1 -1
- package/dist/smart-rename/index.d.ts +1 -1
- package/dist/smart-rename/index.d.ts.map +1 -1
- package/dist/spec-linker/index.d.ts +1 -1
- package/dist/spec-linker/index.d.ts.map +1 -1
- package/dist/spec-linker.js +222 -20772
- package/dist/template-engine/index.d.ts +1 -1
- package/dist/template-engine/index.d.ts.map +1 -1
- package/dist/template-engine.js +4 -6
- package/dist/test-coverage-gate/index.d.ts +1 -1
- package/dist/test-coverage-gate/index.d.ts.map +1 -1
- package/dist/test-coverage-gate.js +29 -14
- package/dist/test-flake-detector/index.d.ts +1 -1
- package/dist/test-flake-detector/index.d.ts.map +1 -1
- package/dist/test-flake-detector.js +31 -20
- package/dist/test-generator/index.d.ts +1 -1
- package/dist/test-generator/index.d.ts.map +1 -1
- package/dist/test-runner-gate/index.d.ts +1 -1
- package/dist/test-runner-gate/index.d.ts.map +1 -1
- package/dist/test-runner-gate.js +2 -1
- package/dist/todo-listener/index.d.ts +1 -32
- package/dist/todo-listener/index.d.ts.map +1 -1
- package/dist/todo-tracker/index.d.ts +1 -1
- package/dist/todo-tracker/index.d.ts.map +1 -1
- package/dist/token-budget/index.d.ts +1 -1
- package/dist/token-budget/index.d.ts.map +1 -1
- package/dist/token-throttle/index.d.ts +1 -1
- package/dist/token-throttle/index.d.ts.map +1 -1
- package/dist/type-gate/index.d.ts +1 -1
- package/dist/type-gate/index.d.ts.map +1 -1
- package/dist/type-gate.js +11 -4
- package/package.json +80 -68
package/README.md
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
# @wrongstack/plugins
|
|
2
2
|
|
|
3
3
|
First-party plugin collection for [WrongStack](https://github.com/WrongStack/WrongStack).
|
|
4
|
-
Sixty-
|
|
4
|
+
Sixty-four focused, single-purpose plugins ship in this package. Passive,
|
|
5
5
|
broadly applicable diagnostics and bounded safety checks load automatically;
|
|
6
6
|
plugins with automatic mutation, policy enforcement, network egress, background
|
|
7
7
|
work, or provider-call semantic changes are opt-in.
|
|
@@ -15,79 +15,15 @@ exports a default `Plugin` object. The host's plugin loader
|
|
|
15
15
|
`ToolRegistry` and may also register **hooks** (e.g.
|
|
16
16
|
`secret-scanner` registers `PreToolUse` + `PostToolUse` hooks).
|
|
17
17
|
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
18
|
+
Official plugins are loaded lazily through factories generated from the typed
|
|
19
|
+
manifest. The canonical default is each manifest entry's `audit.defaultState`:
|
|
20
|
+
list an inactive plugin with
|
|
21
21
|
`{ name: '<plugin>', enabled: true }` to opt in, or list an active plugin with
|
|
22
22
|
`enabled: false` to opt out.
|
|
23
23
|
|
|
24
24
|
## Plugin catalog
|
|
25
25
|
|
|
26
|
-
|
|
27
|
-
|---|---|---|---|---|
|
|
28
|
-
| 1 | [`auto-doc`](./src/auto-doc) | `auto_doc` | — | JSDoc/TSDoc generation with `dry_run` preview |
|
|
29
|
-
| 2 | [`git-autocommit`](./src/git-autocommit) | `git_autocommit` | — | AI-written conventional commits; warns on simultaneous worktrees |
|
|
30
|
-
| 3 | [`shell-check`](./src/shell-check) | `shellcheck` | — | Runs `shellcheck` on files or directories |
|
|
31
|
-
| 4 | [`cost-tracker`](./src/cost-tracker) | `cost_summary`, `cost_reset`, `cost_export` | — | Tracks per-model token usage and estimated USD cost |
|
|
32
|
-
| 5 | [`file-watcher`](./src/file-watcher) | `watch_start`, `watch_stop`, `watch_list` | — | Watches project files and emits debounced change events |
|
|
33
|
-
| 6 | [`cron`](./src/cron) | `cron_schedule`, `cron_list`, `cron_cancel` | — | Schedules recurring in-session actions |
|
|
34
|
-
| 7 | [`template-engine`](./src/template-engine) | `template_expand`, `template_render`, `template_create`, `template_list` | — | Expands templates with variables, conditionals, and loops |
|
|
35
|
-
| 8 | [`semver-bump`](./src/semver-bump) | `semver_bump`, `semver_current`, `semver_changelog` | — | Infers version bumps and changelogs from conventional commits |
|
|
36
|
-
| 9 | [`secret-scanner`](./src/secret-scanner) | `secret_scanner_status`, `secret_scanner_test` | `PreToolUse` + `PostToolUse` | Blocks/redacts input secrets and warns on output leaks |
|
|
37
|
-
| 10 | [`todo-tracker`](./src/todo-tracker) | `todo_tracker_*` | — | Persistent project-scoped backlog that survives sessions |
|
|
38
|
-
| 11 | [`token-budget`](./src/token-budget) | `token_budget_status` | `Stop` + `PostToolUse` | Tracks token use and can warn/stop at configured limits |
|
|
39
|
-
| 12 | [`lint-gate`](./src/lint-gate) | `lint_gate_status` | `PreToolUse` | Lints would-be write/edit content before mutation |
|
|
40
|
-
| 13 | [`branch-guard`](./src/branch-guard) | `branch_guard_status` | `PreToolUse` | Opt-in protected-branch policy for commits, pushes, and merges |
|
|
41
|
-
| 14 | [`diff-summary`](./src/diff-summary) | `diff_summary_status` | `PostToolUse` | Injects compact git diff context after write/edit |
|
|
42
|
-
| 15 | [`commit-validator`](./src/commit-validator) | `commit_validator_status` | `PreToolUse` | Opt-in conventional-commit policy |
|
|
43
|
-
| 16 | [`format-on-save`](./src/format-on-save) | `format_on_save_status` | `PostToolUse` | Runs formatter after write/edit |
|
|
44
|
-
| 17 | [`test-runner-gate`](./src/test-runner-gate) | `test_gate_status` | `PostToolUse` | Runs relevant tests after source edits |
|
|
45
|
-
| 18 | [`import-organizer`](./src/import-organizer) | `import_organizer_status` | `PostToolUse` | Organizes imports and applies safe fixes after write/edit |
|
|
46
|
-
| 19 | [`todo-listener`](./src/todo-listener) | `todo_listener_status` | `PostToolUse` | Broadcasts todo status changes to the project mailbox |
|
|
47
|
-
| 20 | [`session-recap`](./src/session-recap) | `session_recap_status` | `Stop` | Posts a compact session recap to the project mailbox |
|
|
48
|
-
| 21 | [`spec-linker`](./src/spec-linker) | `spec_linker_status` | `PreToolUse` + `PostToolUse` | Detects unlinked plugin references in markdown docs |
|
|
49
|
-
| 22 | [`loop-breaker`](./src/loop-breaker) | `loop_breaker_status` | `PreToolUse` | Detects repeated tool-call loops and oscillations |
|
|
50
|
-
| 23 | [`path-guard`](./src/path-guard) | `path_guard_status` | `PreToolUse` | Opt-in protected-path policy for writes and destructive commands |
|
|
51
|
-
| 24 | [`context-pins`](./src/context-pins) | `pin_add`, `pin_remove`, `pin_list` | System prompt contributor | Persists short pinned facts across compaction/session boundaries |
|
|
52
|
-
| 25 | [`checkpoint`](./src/checkpoint) | `checkpoint_create`, `checkpoint_list`, `checkpoint_restore` | `PreToolUse` | Opt-in in-memory snapshots of pre-edit file contents |
|
|
53
|
-
| 26 | [`error-lens`](./src/error-lens) | `error_lens_history` | `PostToolUse` | Summarizes failed tool output and repeated failure patterns |
|
|
54
|
-
| 27 | [`dep-guard`](./src/dep-guard) | `dep_guard_status` | `PreToolUse` | Supervises dependency installs for deny-list and supply-chain warnings |
|
|
55
|
-
| 28 | [`config-validator`](./src/config-validator) | `config_validator_status` | `PostToolUse` | Validates edited JSON/JSONC/YAML/TOML config files |
|
|
56
|
-
| 29 | [`notify-hub`](./src/notify-hub) | `notify_send`, `notify_hub_status` | `Stop` + event subscriptions | Sends session/tool notifications to a configured webhook |
|
|
57
|
-
| 30 | [`changelog-writer`](./src/changelog-writer) | `changelog_add`, `changelog_preview`, `changelog_write` | — | Collects and writes Keep-a-Changelog entries |
|
|
58
|
-
| 31 | [`injection-shield`](./src/injection-shield) | `injection_shield_status` | `PostToolUse` | Warns when tool output contains prompt-injection patterns |
|
|
59
|
-
| 32 | [`llm-cache`](./src/llm-cache) | `llm_cache_status`, `llm_cache_clear` | Provider runner wrapper | Opt-in cache for deterministic provider requests |
|
|
60
|
-
| 33 | [`model-router`](./src/model-router) | `model_router_status` | Provider runner wrapper | Opt-in routing of provider calls by declarative rules |
|
|
61
|
-
| 34 | [`prompt-firewall`](./src/prompt-firewall) | `prompt_firewall_status` | Provider runner wrapper | Opt-in provider-wire prompt/secret scanning and redaction/blocking |
|
|
62
|
-
| 35 | [`auto-escalate`](./src/auto-escalate) | `auto_escalate_status` | `onError` extension | Opt-in retry/escalation ladder for transient provider errors |
|
|
63
|
-
| 36 | [`token-throttle`](./src/token-throttle) | `token_throttle_status` | Provider runner wrapper | Opt-in rolling-window token throttling for provider calls |
|
|
64
|
-
| 37 | [`type-gate`](./src/type-gate) | `type_gate_status` | `PostToolUse` | Runs `tsc --noEmit` after `write`/`edit` to catch type regressions |
|
|
65
|
-
| 38 | [`test-coverage-gate`](./src/test-coverage-gate) | `coverage_gate_status` | `PostToolUse` | Detects test-coverage regressions after source-file edits |
|
|
66
|
-
| 39 | [`pr-drafter`](./src/pr-drafter) | `pr_draft` | `Stop` + event subscriptions | Drafts a pull-request description from session commits/files/diff |
|
|
67
|
-
| 40 | [`agent-handoff`](./src/agent-handoff) | `handoff_note`, `handoff_status` | `subagent.done` event listener | Opt-in mailbox publication of subagent results |
|
|
68
|
-
| 41 | [`knowledge-graph`](./src/knowledge-graph) | `kg_add_fact`, `kg_query`, `kg_remove_fact`, `kg_status` | System prompt contributor | Persistent structured (subject, relation, object) project facts |
|
|
69
|
-
| 42 | [`dead-code-detector`](./src/dead-code-detector) | `dead_code_scan` | `PostToolUse` | Regex-based scan for exported identifiers that appear unused |
|
|
70
|
-
| 43 | [`dependency-vulnerability-gate`](./src/dependency-vulnerability-gate) | `dependency_audit_status` | `PostToolUse` | Opt-in blocking `npm/pnpm audit` after installs |
|
|
71
|
-
| 44 | [`migration-planner`](./src/migration-planner) | `migration_plan`, `migration_status` | `PostToolUse` | Evidence-backed checklists + optional `api.llm` risk/verification analysis |
|
|
72
|
-
| 45 | [`semantic-search-indexer`](./src/semantic-search-indexer) | `semantic_search`, `semantic_index_status` | — | Lightweight keyword index over project source files |
|
|
73
|
-
| 46 | [`auto-i18n-extractor`](./src/auto-i18n-extractor) | `i18n_extract`, `i18n_status` | `PostToolUse` | Detects hardcoded user-facing strings and suggests i18n keys |
|
|
74
|
-
| 47 | [`doc-sync-guard`](./src/doc-sync-guard) | `doc_sync_status` | `PostToolUse` | Warns when README/docs edits omit recently changed source files |
|
|
75
|
-
| 48 | [`api-compatibility-gate`](./src/api-compatibility-gate) | `api_compat_status` | `PostToolUse` | Detects removed exports in entry-point files as breaking changes |
|
|
76
|
-
| 49 | [`performance-regression-gate`](./src/performance-regression-gate) | `perf_regression_status` | — | Compares benchmark results and reports regressions |
|
|
77
|
-
| 50 | [`test-flake-detector`](./src/test-flake-detector) | `flake_detect`, `flake_status` | — | Runs a test command N times to identify flaky tests |
|
|
78
|
-
| 51 | [`schema-evolution-guard`](./src/schema-evolution-guard) | `schema_evolution_status` | `PostToolUse` | Detects destructive patterns in DB/API schema files |
|
|
79
|
-
| 52 | [`license-audit-gate`](./src/license-audit-gate) | `license_audit_status` | `PostToolUse` | Audits newly added dependency licenses against an allowlist |
|
|
80
|
-
| 53 | [`accessibility-auditor`](./src/accessibility-auditor) | `a11y_audit`, `a11y_status` | `PostToolUse` | Audits UI files for missing alt, labels, button text, duplicate ids |
|
|
81
|
-
| 54 | [`security-hotspot-scanner`](./src/security-hotspot-scanner) | `security_hotspot_scan`, `security_hotspot_status` | `PostToolUse` | Scans source for security anti-patterns after writes/edits |
|
|
82
|
-
| 55 | [`duplicate-code-detector`](./src/duplicate-code-detector) | `detect_duplicate_code`, `duplicate_code_status` | `PostToolUse` | Detects duplicate/similar code blocks using normalized-line fingerprints |
|
|
83
|
-
| 56 | [`code-metrics`](./src/code-metrics) | `measure_code_metrics`, `metrics_status` | `PostToolUse` | Computes LOC, comment ratio, function count, and approximate cyclomatic complexity |
|
|
84
|
-
| 57 | [`refactor-suggester`](./src/refactor-suggester) | `suggest_refactors`, `refactor_status` | `PostToolUse` | Flags long functions, deep nesting, many parameters, magic numbers, console.log |
|
|
85
|
-
| 58 | [`test-generator`](./src/test-generator) | `generate_unit_tests` | — | Framework-correct skeletons + optional behavior-focused `api.llm` tests |
|
|
86
|
-
| 59 | [`release-notes-generator`](./src/release-notes-generator) | `generate_release_notes` | — | Traceable notes + optional hash-preserving `api.llm` polish |
|
|
87
|
-
| 60 | [`smart-rename`](./src/smart-rename) | `smart_rename` | — | Whole-word symbol rename with preview and optional apply |
|
|
88
|
-
| 61 | [`feature-flag-tracker`](./src/feature-flag-tracker) | `scan_feature_flags`, `feature_flag_status` | `PostToolUse` | Scans source files for feature-flag usage and reports flag inventory |
|
|
89
|
-
| 62 | [`interface-contract-guard`](./src/interface-contract-guard) | `check_interface_contracts`, `interface_contract_status` | `PostToolUse` | Warns when TypeScript interfaces change or lack implementers |
|
|
90
|
-
| 63 | [`plugin-stack-observer`](./src/plugin-stack-observer) | `plugin_stack_status` | Event listener + optional system prompt contributor | Reports active provider-runner wrappers in registration order |
|
|
26
|
+
Plugin identity, import paths, versions, API ranges, and descriptions are generated from the typed manifest in [`PLUGIN_CATALOG.md`](./PLUGIN_CATALOG.md). Run `pnpm plugins:manifest:write` after changing the manifest.
|
|
91
27
|
|
|
92
28
|
### Removed plugins (use built-in tools instead)
|
|
93
29
|
|
|
@@ -702,7 +638,7 @@ context. Increase `includeTranscriptTail` for more history.
|
|
|
702
638
|
Two hooks working together:
|
|
703
639
|
|
|
704
640
|
**PostToolUse** (always active when the plugin is enabled):
|
|
705
|
-
scans markdown files for *unlinked* references to one of the
|
|
641
|
+
scans markdown files for *unlinked* references to one of the manifest-listed
|
|
706
642
|
known plugins and surfaces them to the LLM via
|
|
707
643
|
`additionalContext`. The plugin does NOT modify the file — it
|
|
708
644
|
only injects a low-noise context block listing the unlinked
|
|
@@ -726,7 +662,7 @@ the PostToolUse context tells the LLM what to fix.
|
|
|
726
662
|
|
|
727
663
|
**Detection rules** (both hooks):
|
|
728
664
|
- Source matches `config.fileGlobs` (default: `**/*.md`, `**/*.mdx`)
|
|
729
|
-
- The reference matches one of the
|
|
665
|
+
- The reference matches one of the manifest-listed plugin names
|
|
730
666
|
(case-insensitive)
|
|
731
667
|
- It is NOT already wrapped in a markdown link `[name](...)` or
|
|
732
668
|
inline code `` `name` ``
|
|
@@ -24,7 +24,7 @@
|
|
|
24
24
|
*
|
|
25
25
|
* @public
|
|
26
26
|
*/
|
|
27
|
-
import type { Plugin } from '@wrongstack/core';
|
|
27
|
+
import type { Plugin } from '@wrongstack/core/types';
|
|
28
28
|
export type A11yRule = 'missing-alt' | 'missing-input-label' | 'low-contrast-placeholder' | 'missing-button-text' | 'duplicate-id';
|
|
29
29
|
export interface A11yFinding {
|
|
30
30
|
file: string;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/accessibility-auditor/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;GAyBG;AAIH,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/accessibility-auditor/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;GAyBG;AAIH,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,wBAAwB,CAAC;AASrD,MAAM,MAAM,QAAQ,GAChB,aAAa,GACb,qBAAqB,GACrB,0BAA0B,GAC1B,qBAAqB,GACrB,cAAc,CAAC;AAEnB,MAAM,WAAW,WAAW;IAC1B,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,QAAQ,CAAC;IACf,QAAQ,EAAE,OAAO,GAAG,SAAS,CAAC;IAC9B,OAAO,EAAE,MAAM,CAAC;CACjB;AAuPD,QAAA,MAAM,MAAM,EAAE,MA0Nb,CAAC;eAEa,MAAM"}
|
|
@@ -1,9 +1,8 @@
|
|
|
1
1
|
// src/accessibility-auditor/index.ts
|
|
2
|
-
import {
|
|
2
|
+
import { readFile } from "node:fs/promises";
|
|
3
3
|
import { isAbsolute as isAbsolute2, relative as relative2, resolve as resolve2 } from "node:path";
|
|
4
4
|
|
|
5
5
|
// src/runtime/index.ts
|
|
6
|
-
import { existsSync, readdirSync, statSync } from "node:fs";
|
|
7
6
|
import { basename, extname, isAbsolute, relative, resolve } from "node:path";
|
|
8
7
|
var MAX_BUFFER_BYTES = 16 * 1024 * 1024;
|
|
9
8
|
function hasLeadingDash(arg) {
|
|
@@ -17,44 +16,45 @@ function withinProjectPath(projectRoot, candidate) {
|
|
|
17
16
|
return rel === "" || !rel.startsWith("..") && !isAbsolute(rel);
|
|
18
17
|
}
|
|
19
18
|
function withinProject(p) {
|
|
20
|
-
|
|
19
|
+
const cwd = process.cwd();
|
|
20
|
+
return withinProjectPath(cwd, p) || relative(cwd, p) === ".";
|
|
21
21
|
}
|
|
22
22
|
var DEFAULT_EXCLUDE_DIRS = ["node_modules", "dist", ".git", "coverage"];
|
|
23
|
-
function
|
|
23
|
+
async function collectSourceFilesAsync(root, opts) {
|
|
24
|
+
const { readdir, stat } = await import("node:fs/promises");
|
|
24
25
|
const files = [];
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
26
|
+
try {
|
|
27
|
+
const s = await stat(root);
|
|
28
|
+
if (s.isFile()) {
|
|
29
|
+
if (matchesExtension(root, opts.extensions)) files.push(root);
|
|
30
|
+
return files;
|
|
31
|
+
}
|
|
32
|
+
if (!s.isDirectory()) return files;
|
|
33
|
+
} catch {
|
|
29
34
|
return files;
|
|
30
35
|
}
|
|
31
|
-
if (!s.isDirectory()) return files;
|
|
32
36
|
const exclude = opts.excludeDirs ?? DEFAULT_EXCLUDE_DIRS;
|
|
33
|
-
|
|
37
|
+
const excludeSet = new Set(exclude);
|
|
38
|
+
async function walk(dir, depth) {
|
|
34
39
|
if (opts.maxDepth !== void 0 && depth > opts.maxDepth) return;
|
|
35
40
|
let entries;
|
|
36
41
|
try {
|
|
37
|
-
entries =
|
|
42
|
+
entries = await readdir(dir, { withFileTypes: true });
|
|
38
43
|
} catch {
|
|
39
44
|
return;
|
|
40
45
|
}
|
|
46
|
+
entries.sort((a, b) => a.name.localeCompare(b.name));
|
|
41
47
|
for (const entry of entries) {
|
|
42
|
-
if (
|
|
43
|
-
const full = resolve(dir, entry);
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
} catch {
|
|
48
|
-
continue;
|
|
49
|
-
}
|
|
50
|
-
if (st.isDirectory()) {
|
|
51
|
-
walk(full, depth + 1);
|
|
52
|
-
} else if (st.isFile() && matchesExtension(full, opts.extensions)) {
|
|
48
|
+
if (excludeSet.has(entry.name)) continue;
|
|
49
|
+
const full = resolve(dir, entry.name);
|
|
50
|
+
if (entry.isDirectory()) {
|
|
51
|
+
await walk(full, depth + 1);
|
|
52
|
+
} else if (entry.isFile() && matchesExtension(full, opts.extensions)) {
|
|
53
53
|
files.push(full);
|
|
54
54
|
}
|
|
55
55
|
}
|
|
56
56
|
}
|
|
57
|
-
walk(root, 0);
|
|
57
|
+
await walk(root, 0);
|
|
58
58
|
return files;
|
|
59
59
|
}
|
|
60
60
|
function matchesExtension(p, exts) {
|
|
@@ -109,10 +109,10 @@ function hasMeaningfulAlt(tag) {
|
|
|
109
109
|
const valMatch = tag.match(/\balt\s*=\s*["']?([^"'\s>]*)["']?/i);
|
|
110
110
|
return valMatch ? valMatch[1].trim().length > 0 : false;
|
|
111
111
|
}
|
|
112
|
-
function auditFile(filePath, projectRoot) {
|
|
112
|
+
async function auditFile(filePath, projectRoot) {
|
|
113
113
|
let content;
|
|
114
114
|
try {
|
|
115
|
-
content =
|
|
115
|
+
content = await readFile(filePath, "utf-8");
|
|
116
116
|
} catch {
|
|
117
117
|
return [];
|
|
118
118
|
}
|
|
@@ -198,14 +198,14 @@ function auditFile(filePath, projectRoot) {
|
|
|
198
198
|
}
|
|
199
199
|
return findings;
|
|
200
200
|
}
|
|
201
|
-
function auditPath(rawPath, cfg) {
|
|
201
|
+
async function auditPath(rawPath, cfg) {
|
|
202
202
|
const root = process.cwd();
|
|
203
203
|
const resolved = isAbsolute2(rawPath) ? resolve2(rawPath) : resolve2(root, rawPath);
|
|
204
204
|
const exts = normalizeExtensions(cfg.includeExtensions);
|
|
205
|
-
const files =
|
|
205
|
+
const files = await collectSourceFilesAsync(resolved, { extensions: exts });
|
|
206
206
|
const findings = [];
|
|
207
207
|
for (const file of files) {
|
|
208
|
-
const fileFindings = auditFile(file, root);
|
|
208
|
+
const fileFindings = await auditFile(file, root);
|
|
209
209
|
findings.push(...fileFindings);
|
|
210
210
|
if (findings.length >= cfg.maxFindings) break;
|
|
211
211
|
}
|
|
@@ -274,7 +274,7 @@ var plugin = {
|
|
|
274
274
|
state.lastResult = null;
|
|
275
275
|
state.hookUnregister = null;
|
|
276
276
|
const cfg = readConfig(api.config.extensions?.["accessibility-auditor"]);
|
|
277
|
-
const hook = (input) => {
|
|
277
|
+
const hook = async (input) => {
|
|
278
278
|
if (!cfg.enabled || !cfg.onWriteEdit) return;
|
|
279
279
|
if (input.toolResult?.isError) return;
|
|
280
280
|
const inp = input.toolInput ?? {};
|
|
@@ -284,7 +284,7 @@ var plugin = {
|
|
|
284
284
|
const exts = normalizeExtensions(cfg.includeExtensions);
|
|
285
285
|
if (!matchesExtension(sourcePath, exts)) return;
|
|
286
286
|
state.hookInvocationCount += 1;
|
|
287
|
-
const result = auditPath(sourcePath, cfg);
|
|
287
|
+
const result = await auditPath(sourcePath, cfg);
|
|
288
288
|
state.auditCount += 1;
|
|
289
289
|
state.fileCount += result.fileCount;
|
|
290
290
|
state.findingCount += result.findings.length;
|
|
@@ -328,7 +328,7 @@ var plugin = {
|
|
|
328
328
|
return { ok: false, error: "path must be inside the project" };
|
|
329
329
|
}
|
|
330
330
|
state.auditCount += 1;
|
|
331
|
-
const result = auditPath(rawPath, cfg);
|
|
331
|
+
const result = await auditPath(rawPath, cfg);
|
|
332
332
|
state.fileCount += result.fileCount;
|
|
333
333
|
state.findingCount += result.findings.length;
|
|
334
334
|
state.lastResult = {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/agent-handoff/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA8BG;
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/agent-handoff/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA8BG;AAGH,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,wBAAwB,CAAC;AAwKrD,QAAA,MAAM,MAAM,EAAE,MAsNb,CAAC;eAEa,MAAM"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/api-compatibility-gate/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA+BG;
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/api-compatibility-gate/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA+BG;AAMH,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,wBAAwB,CAAC;AAsRrD,QAAA,MAAM,MAAM,EAAE,MA6Mb,CAAC;eAEa,MAAM"}
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
// src/api-compatibility-gate/index.ts
|
|
2
|
-
import {
|
|
2
|
+
import { execFile } from "node:child_process";
|
|
3
3
|
import { existsSync, readFileSync } from "node:fs";
|
|
4
|
+
import { readFile } from "node:fs/promises";
|
|
4
5
|
import { basename, dirname, extname, isAbsolute, relative, resolve } from "node:path";
|
|
5
6
|
var API_VERSION = "^0.1.10";
|
|
6
7
|
var state = {
|
|
@@ -155,21 +156,25 @@ function extractExports(source) {
|
|
|
155
156
|
function readGitVersion(filePath) {
|
|
156
157
|
const resolved = resolveToProjectRoot(filePath);
|
|
157
158
|
const relPath = normalizePath(relative(process.cwd(), resolved));
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
159
|
+
return new Promise((resolveVersion) => {
|
|
160
|
+
execFile(
|
|
161
|
+
"git",
|
|
162
|
+
["show", `HEAD:${relPath}`],
|
|
163
|
+
{
|
|
164
|
+
encoding: "utf8",
|
|
165
|
+
cwd: process.cwd(),
|
|
166
|
+
windowsHide: true,
|
|
167
|
+
timeout: 5e3,
|
|
168
|
+
maxBuffer: 5 * 1024 * 1024
|
|
169
|
+
},
|
|
170
|
+
(error, stdout) => resolveVersion(error ? null : stdout)
|
|
171
|
+
);
|
|
172
|
+
});
|
|
168
173
|
}
|
|
169
|
-
function readCurrentFile(filePath) {
|
|
174
|
+
async function readCurrentFile(filePath) {
|
|
170
175
|
try {
|
|
171
176
|
const resolved = resolveToProjectRoot(filePath);
|
|
172
|
-
return
|
|
177
|
+
return await readFile(resolved, "utf8");
|
|
173
178
|
} catch {
|
|
174
179
|
return null;
|
|
175
180
|
}
|
|
@@ -227,7 +232,7 @@ var plugin = {
|
|
|
227
232
|
state.hookUnregister = null;
|
|
228
233
|
}
|
|
229
234
|
const cfg = readConfig(api.config.extensions?.["api-compatibility-gate"]);
|
|
230
|
-
const hook = (input) => {
|
|
235
|
+
const hook = async (input) => {
|
|
231
236
|
if (!cfg.enabled) return;
|
|
232
237
|
if (input.toolResult?.isError) return;
|
|
233
238
|
const inp = input.toolInput ?? {};
|
|
@@ -242,12 +247,12 @@ var plugin = {
|
|
|
242
247
|
state.skippedCount += 1;
|
|
243
248
|
return;
|
|
244
249
|
}
|
|
245
|
-
const before = readGitVersion(filePath);
|
|
250
|
+
const before = await readGitVersion(filePath);
|
|
246
251
|
if (before === null) {
|
|
247
252
|
state.skippedCount += 1;
|
|
248
253
|
return;
|
|
249
254
|
}
|
|
250
|
-
const after = readCurrentFile(filePath);
|
|
255
|
+
const after = await readCurrentFile(filePath);
|
|
251
256
|
if (after === null) {
|
|
252
257
|
state.errorCount += 1;
|
|
253
258
|
return;
|