jev-layer 0.1.0 → 0.3.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.
Files changed (88) hide show
  1. package/CHANGELOG.md +73 -34
  2. package/CONTRIBUTING.md +146 -146
  3. package/LICENSE +21 -21
  4. package/README.md +125 -126
  5. package/README.ru.md +140 -117
  6. package/README.zh-CN.md +139 -117
  7. package/RELEASE.md +53 -53
  8. package/SECURITY.md +64 -56
  9. package/bin/jev.mjs +215 -213
  10. package/config/codex.mcp.toml +8 -8
  11. package/config/generic-mcp.json +13 -13
  12. package/config/hermes.mcp.yaml +9 -9
  13. package/config/jev.example.json +23 -22
  14. package/config/omp.mcp.json +14 -14
  15. package/config/providers.env.example +13 -13
  16. package/docs/AGENT-IMPLEMENTATION.md +306 -0
  17. package/docs/COMPATIBILITY.md +24 -15
  18. package/docs/HERMES-LOCAL-AGENT-HANDOFF.ru.md +187 -0
  19. package/docs/PROVIDERS.md +109 -0
  20. package/docs/SCHEMA-VERSIONING.md +101 -94
  21. package/docs/architecture.svg +77 -0
  22. package/docs/jev-layer-banner.svg +38 -0
  23. package/examples/capabilities.json +39 -39
  24. package/examples/route-request.json +28 -28
  25. package/integrations/codex/.codex-plugin/plugin.json +19 -19
  26. package/integrations/codex/.mcp.json +11 -11
  27. package/integrations/codex/AGENTS.md +1 -1
  28. package/integrations/codex/run-mcp.mjs +9 -9
  29. package/integrations/codex/skills/jev-route/SKILL.md +17 -17
  30. package/integrations/hermes/__init__.py +156 -51
  31. package/integrations/hermes/plugin.yaml +11 -5
  32. package/integrations/hermes/schemas.py +120 -12
  33. package/integrations/omp/extension.js +106 -105
  34. package/integrations/template/README.md +10 -10
  35. package/integrations/template/adapter.mjs +87 -87
  36. package/package.json +60 -59
  37. package/scripts/benchmark.mjs +35 -35
  38. package/scripts/browser-benchmark.mjs +92 -92
  39. package/scripts/browser-e2e.mjs +117 -117
  40. package/scripts/capability-e2e.mjs +31 -31
  41. package/scripts/clean-install-smoke.mjs +176 -162
  42. package/scripts/codex-mcp-smoke.mjs +119 -119
  43. package/scripts/context-filter-e2e.mjs +45 -45
  44. package/scripts/fail-open-smoke.mjs +120 -120
  45. package/scripts/feature-flags-smoke.mjs +46 -46
  46. package/scripts/mcp-receipt-smoke.mjs +115 -98
  47. package/scripts/model-route-report.mjs +15 -0
  48. package/scripts/openrouter-choice.mjs +59 -59
  49. package/scripts/replay-eval.mjs +124 -124
  50. package/scripts/smoke.mjs +34 -34
  51. package/scripts/supervision-e2e.mjs +138 -109
  52. package/src/browser.mjs +583 -569
  53. package/src/cli.mjs +33 -33
  54. package/src/computer.mjs +196 -0
  55. package/src/config.mjs +86 -75
  56. package/src/context-filter.mjs +56 -56
  57. package/src/contract.mjs +74 -72
  58. package/src/discovery.mjs +65 -65
  59. package/src/hermes-adapter.mjs +134 -0
  60. package/src/images.mjs +98 -0
  61. package/src/mcp-server.mjs +313 -210
  62. package/src/model-route-metrics.mjs +89 -0
  63. package/src/model-routing.mjs +87 -0
  64. package/src/providers/demo.mjs +52 -52
  65. package/src/providers/index.mjs +12 -0
  66. package/src/providers/typesafe.mjs +206 -126
  67. package/src/receipts.mjs +228 -226
  68. package/src/registry.mjs +109 -109
  69. package/src/relevance-filter.mjs +99 -99
  70. package/src/route.mjs +228 -221
  71. package/src/shadow-compaction.mjs +170 -0
  72. package/src/supervision.mjs +268 -244
  73. package/test/browser.test.mjs +222 -199
  74. package/test/capability.test.mjs +54 -54
  75. package/test/computer.test.mjs +195 -0
  76. package/test/context-filter.test.mjs +65 -65
  77. package/test/hermes-adapter.test.mjs +63 -0
  78. package/test/image-fixture.mjs +2 -0
  79. package/test/images.test.mjs +85 -0
  80. package/test/model-route-metrics.test.mjs +61 -0
  81. package/test/model-routing.test.mjs +59 -0
  82. package/test/openrouter-provider.test.mjs +55 -55
  83. package/test/provider-transports.test.mjs +205 -0
  84. package/test/providers.test.mjs +125 -0
  85. package/test/receipts.test.mjs +71 -71
  86. package/test/route.test.mjs +86 -74
  87. package/test/shadow-compaction.test.mjs +67 -0
  88. package/test/supervision.test.mjs +117 -99
package/CHANGELOG.md CHANGED
@@ -1,34 +1,73 @@
1
- # Changelog
2
-
3
- All notable changes to jev-layer are recorded here. Entries describe public behavior and compatibility impact; provider-specific experiments are listed only when they affect a public contract.
4
-
5
- ## [0.1.0]
6
-
7
- First public-release candidate. This version is prepared but has not been pushed, released on GitHub, or published to npm.
8
-
9
- ### Added
10
-
11
- - Portable CLI and stdio MCP routing layer for Hermes, OMP, Codex, and generic MCP-compatible agents.
12
- - Closed-set capability routing through `jev_route` with deterministic host-side policy checks.
13
- - `jev_record_execution` and append-only JSONL routing/execution receipts joined by `correlation_id`.
14
- - Offline replay/evaluation without host execution calls.
15
- - Opt-in supervision judgments with deterministic host policy.
16
- - Opt-in deterministic context filtering (`shadow` and `conservative`).
17
- - Explicit capability discovery for skills, MCP, CLI, DSH, tools, subagents, and models.
18
- - Experimental, opt-in browser fast-path over host-supplied observations.
19
- - MIT license, security policy, schema/version policy, contribution guide, adapter template, CI, and multilingual README documentation.
20
-
21
- ### Compatibility
22
-
23
- - Node.js `>=20`.
24
- - Public request, decision, MCP tool, receipt, replay, and adapter contracts remain schema version 1.
25
- - Release-preparation baseline: OMP `18.2.6`, Hermes `0.21.3` (`b675e6de`), and Codex CLI `0.155.1` observed in the preparation environment. See [docs/COMPATIBILITY.md](docs/COMPATIBILITY.md).
26
- - Browser reliability is validated against the current real-browser fixtures; browser performance optimization remains experimental.
27
-
28
- ### Release constraints
29
-
30
- - Host harnesses retain ownership of permissions, approvals, native execution, retries, recovery, and final results.
31
- - Provider-backed tests require explicit secret-managed environments and are not required for ordinary PR CI.
32
- - No npm publication, GitHub release, or remote push is part of this preparation.
33
-
34
- Proposed repository: https://github.com/typakon4/jev-layer. GitHub release and comparison links become active after repository creation.
1
+ # Changelog
2
+
3
+ All notable changes to jev-layer are recorded here. Entries describe public behavior and compatibility impact; provider-specific experiments are listed only when they affect a public contract.
4
+
5
+ ## [0.3.0] - 2026-10-15
6
+
7
+ ### Added
8
+
9
+ - Direct TypeSafe PNG/JPEG image input with bounded asset validation and the experimental Images/Box opt-in header.
10
+ - OpenRouter vision/Box support via inline Decisions `image_url` parts, with automatic conversion from the layer's shared assets/references format.
11
+ - Opt-in `jev_computer_step` in MCP and Hermes: closed host actions, explicit computer permissions, confirmation, paired visibility/Box grounding and screenshot-bound coordinates.
12
+ - Screenshot input for browser decisions and the host-owned browser fast-path.
13
+
14
+ ### Changed
15
+
16
+ - Pin direct TypeSafe to `jev-1.14.0` and OpenRouter to `typesafe/jev-1.14`; explicit model overrides remain supported. Image-path errors fail open without copying image bytes into receipts.
17
+ - Preserve browser action arguments in MCP/Hermes output. Raise the Hermes process timeout to 10 seconds for multi-call grounding.
18
+ - Exclude screenshot bytes from text projection, durable replay and pending receipt requests; visual replay requires original images.
19
+ - Keep all contracts on schema version 1 and computer use disabled by default.
20
+
21
+ ### Fixed
22
+
23
+ - Generate native Node/entrypoint adapter commands on Windows instead of relying on npm `.cmd` shims.
24
+ - Exercise a real installed package in cross-platform clean-install smoke; correct Windows URL paths and shutdown handling in MCP receipt smoke.
25
+ - Report the installed package version during MCP initialization.
26
+
27
+ ### Distribution
28
+
29
+ - [npm `jev-layer@0.3.0`](https://www.npmjs.com/package/jev-layer/v/0.3.0) · [GitHub `v0.3.0`](https://github.com/typakon4/jev-layer/releases/tag/v0.3.0).
30
+ - Rollback: pin `jev-layer@0.2.0` and restart the MCP process; that version does not provide the new vision/computer-use surface. Report release issues through the repository issue tracker.
31
+
32
+ ## [0.2.0] - 2026-09-25
33
+
34
+ ### Added
35
+
36
+ - Advisory `jev_model_route` recommendations with correlated execution outcomes and a local evidence report. Recommendations do not change the host's provider or model.
37
+ - Report-only `jev_shadow_compaction` candidates for host-supplied context. It does not summarize, mutate, or delete context.
38
+ - Expanded Hermes integration for provider selection, receipts, model-route correlation, supervision, and browser decisions.
39
+ - Evidence-state handling for supervision; contradictory evidence cannot produce a `finish` decision.
40
+
41
+ ### Fixed
42
+
43
+ - Route `typesafe` through the official System One provider in the CLI, stdio MCP server, and adapters. Added offline regression coverage for the reported failure.
44
+ - Apply configured provider environment names consistently across CLI and MCP surfaces, including supervision and browser decisions.
45
+ - Preserve configured provider options in the Hermes integration and send OpenRouter's optional app title.
46
+
47
+ ### Compatibility
48
+
49
+ - Node.js `>=20`.
50
+ - Public request, decision, MCP tool, receipt, replay, and adapter contracts remain schema version 1.
51
+ - Provider-backed tests are not required for ordinary PR CI; normal CI covers provider behavior with offline fixtures.
52
+
53
+ ## [0.1.0] - 2026-09-19
54
+
55
+ Initial public release.
56
+
57
+ ### Added
58
+
59
+ - Portable CLI and stdio MCP routing layer for Hermes, OMP, Codex, and generic MCP-compatible agents.
60
+ - Closed-set capability routing through `jev_route` with deterministic host-side policy checks.
61
+ - `jev_record_execution` and append-only JSONL routing/execution receipts joined by `correlation_id`.
62
+ - Offline replay/evaluation without host execution calls.
63
+ - Opt-in supervision judgments with deterministic host policy.
64
+ - Opt-in deterministic context filtering (`shadow` and `conservative`).
65
+ - Explicit capability discovery for skills, MCP, CLI, DSH, tools, subagents, and models.
66
+ - Experimental, opt-in browser fast-path over host-supplied observations.
67
+ - MIT license, security policy, schema/version policy, contribution guide, adapter template, CI, and multilingual README documentation.
68
+
69
+ ### Compatibility
70
+
71
+ - Node.js `>=20`.
72
+ - Public request, decision, MCP tool, receipt, replay, and adapter contracts remain schema version 1.
73
+ - Browser reliability was validated against real-browser fixtures; browser performance optimization remains experimental.
package/CONTRIBUTING.md CHANGED
@@ -1,146 +1,146 @@
1
- # Contributing to jev-layer
2
-
3
- [English](README.md) | [Русский](README.ru.md) | [简体中文](README.zh-CN.md)
4
-
5
- jev-layer is a portable System-1 decision layer. Contributions must preserve the rule that the host owns execution, permissions, approvals, retries, recovery, and final results. Jev returns bounded decisions; it does not become a security boundary or a second executor.
6
-
7
- ## Before opening a pull request
8
-
9
- 1. Read `SECURITY.md` and `docs/SCHEMA-VERSIONING.md`.
10
- 2. Keep the change narrow. Do not add runtime features while changing an adapter or documentation.
11
- 3. Add deterministic tests and an offline fixture. Provider-backed tests are optional and must not require secrets in ordinary CI.
12
- 4. Do not commit API keys, tokens, private keys, `.env` files, machine-specific paths, home directories, or local installation state.
13
- 5. Preserve existing schema v1 fields and fail-open behavior unless a versioned migration is part of the change.
14
-
15
- ## Adapter contract (version 1)
16
-
17
- A harness adapter is a thin integration. It may use the CLI or stdio MCP, but it must preserve the following sequence:
18
-
19
- | Stage | Required behavior |
20
- | --- | --- |
21
- | Capability discovery/input | Build a closed `capabilities[]` set from the host's known capabilities. Include stable `id`, `kind`, `name`, `description`, `permissions`, `risk`, and availability metadata where known. Do not ask Jev to discover or execute hidden host tools. |
22
- | `jev_route` call | Send `schema_version: 1`, `harness`, `intent`, bounded `context`, `actor_permissions`, `capabilities`, and `policy` to `jev_route`. Preserve the returned `correlation_id` and selected capability id. |
23
- | Host execution | Resolve the selected id through the harness's native registry. The adapter must not shell out to arbitrary ids, grant permissions, or replace native tool execution. |
24
- | `jev_record_execution` receipt | After the host decides what happened, call `jev_record_execution` with the same `correlation_id`, `status` (`completed`, `failed`, or `not_started`), `capability_id`, bounded result/error, and optional exit/timing metadata. |
25
- | Fail-open | If Jev is disabled, unavailable, times out, returns an error, or returns no usable selection, continue through the harness's normal native path. Never guess a capability or treat a Jev failure as permission to execute. |
26
- | Approval semantics | The host remains the approval authority. Consequential actions require the host's normal approval before execution. A denial records `not_started`; Jev cannot approve, elevate, retry, or override the host. |
27
-
28
- `jev_browser_step` follows the same ownership rule: the host supplies a structured observation, the host approves consequential browser actions, and the host executes or hands control back. It is experimental and opt-in.
29
-
30
- ### Minimal adapter pseudocode
31
-
32
- ```text
33
- request = {
34
- schema_version: 1,
35
- harness: "my-harness",
36
- intent: host_goal,
37
- context: bounded_host_context,
38
- actor_permissions: host_permissions,
39
- capabilities: host_capabilities,
40
- policy: host_policy
41
- }
42
-
43
- decision = call_jev_route(request)
44
-
45
- if decision.status != "selected" or decision.selected is null:
46
- return native_host_path(request)
47
-
48
- if consequential(decision.selected) and not host_approval(decision.selected):
49
- call_jev_record_execution({
50
- correlation_id: decision.correlation_id,
51
- capability_id: decision.selected,
52
- status: "not_started",
53
- error: "host approval denied"
54
- })
55
- return native_host_path(request)
56
-
57
- try:
58
- host_result = execute_native(decision.selected)
59
- status = "completed"
60
- except error:
61
- host_result = null
62
- status = "failed"
63
-
64
- receipt = call_jev_record_execution({
65
- correlation_id: decision.correlation_id,
66
- capability_id: decision.selected,
67
- status,
68
- result: bounded(host_result),
69
- error: bounded(error),
70
- duration_ms: measured_duration
71
- })
72
- return { decision, host_result, receipt }
73
- ```
74
-
75
- Copy `integrations/template/adapter.mjs` for a small JavaScript starting point with the same injected boundaries.
76
-
77
- ## Adding a new harness
78
-
79
- The shortest supported PR path is:
80
-
81
- 1. Add `integrations/<harness>/` with a thin adapter that calls the existing CLI or MCP contract.
82
- 2. Add a secret-free config/example snippet under `config/` or the integration directory.
83
- 3. Add an offline smoke fixture proving route, fail-open, approval denial, host execution, and execution receipt behavior.
84
- 4. Register compatibility in `README.md`, the translated READMEs, `docs/SCHEMA-VERSIONING.md`, and `RELEASE.md` when the harness is supported.
85
- 5. Run the required CI commands and submit the PR.
86
-
87
- Do not add a harness-specific routing implementation. Keep configuration user-owned; never overwrite global harness settings.
88
-
89
- ## Adding a provider
90
-
91
- Providers implement the existing provider surface in `src/providers/`: a `name` and an async `decide({ state, candidates })` method. Supervision-capable providers may also implement `evaluate({ state, questions })`. Return the normalized provider response expected by `src/route.mjs`; do not execute capabilities in the provider.
92
-
93
- - Add the provider to explicit configuration/selection only when it is usable offline or clearly fails open.
94
- - Add deterministic unit tests using injected responses or the `demo` provider.
95
- - Keep API keys and endpoints in environment variables or user-owned configuration.
96
- - Provider-backed tests belong in secret-managed CI, not ordinary pull-request CI.
97
-
98
- ## Adding a discovery source
99
-
100
- Use `discoverCapabilities()` and the normalized capability shape in `src/discovery.mjs`. A new source must:
101
-
102
- - produce stable, namespaced ids;
103
- - preserve `kind`, `name`, `description`, `source`, `verified`, and availability metadata;
104
- - deduplicate by id deterministically;
105
- - read only explicit input or an explicitly supplied manifest path;
106
- - never scan undocumented global locations or execute discovered entries.
107
-
108
- Add a fixture covering empty input, malformed entries, duplicate ids, unavailable entries, and the new source's normalized output.
109
-
110
- ## Adding a browser executor
111
-
112
- Browser executors are host-owned and optional. Implement `observe()` plus `execute(action)`, and implement `select(action)` when the host has a native select mechanism. The observation must be bounded and structured; the executor must validate target ids, preserve host approval, return the next observation, and report failures without retrying implicitly. Do not add screenshots, text entry, browser workers, or permission logic to jev-layer as part of an executor contribution.
113
-
114
- ## Adding an eval or replay fixture
115
-
116
- Add a small JSONL or JSON fixture under `examples/` or a test fixture directory. Include a stable `schema_version`, `harness`, bounded capabilities, and deterministic expected selection/fallback behavior. For receipts, use one `correlation_id` for the routing case and execution receipt. Exercise it with:
117
-
118
- ```sh
119
- npm run replay:evaluate -- --provider demo --limit 20
120
- npm test
121
- ```
122
-
123
- A fixture must not call a real provider, host command, network service, or browser. If a real-provider scenario is useful, document it separately and gate it on an explicitly supplied secret.
124
-
125
- ## Required checks
126
-
127
- From a clean checkout:
128
-
129
- ```sh
130
- npm install
131
- npm test
132
- npm run smoke
133
- npm run fail-open-smoke
134
- npm run clean-install-smoke
135
- npm pack --dry-run
136
- ```
137
-
138
- Changes touching browser, supervision, context filtering, discovery, or MCP should also run the matching existing E2E/smoke script. CI does not require provider credentials.
139
-
140
- ## Backward compatibility
141
-
142
- - Keep schema v1 request, decision, receipt, and replay fields readable.
143
- - Prefer additive optional fields. Do not rename or remove existing fields in a patch release.
144
- - Preserve `correlation_id` across route and execution records.
145
- - Preserve fail-open behavior and host approval ownership.
146
- - If a breaking contract is unavoidable, document a new schema/adapter version and migration before changing the implementation.
1
+ # Contributing to jev-layer
2
+
3
+ [English](README.md) | [Русский](README.ru.md) | [简体中文](README.zh-CN.md)
4
+
5
+ jev-layer is a portable System-1 decision layer. Contributions must preserve the rule that the host owns execution, permissions, approvals, retries, recovery, and final results. Jev returns bounded decisions; it does not become a security boundary or a second executor.
6
+
7
+ ## Before opening a pull request
8
+
9
+ 1. Read `SECURITY.md` and `docs/SCHEMA-VERSIONING.md`.
10
+ 2. Keep the change narrow. Do not add runtime features while changing an adapter or documentation.
11
+ 3. Add deterministic tests and an offline fixture. Provider-backed tests are optional and must not require secrets in ordinary CI.
12
+ 4. Do not commit API keys, tokens, private keys, `.env` files, machine-specific paths, home directories, or local installation state.
13
+ 5. Preserve existing schema v1 fields and fail-open behavior unless a versioned migration is part of the change.
14
+
15
+ ## Adapter contract (version 1)
16
+
17
+ A harness adapter is a thin integration. It may use the CLI or stdio MCP, but it must preserve the following sequence:
18
+
19
+ | Stage | Required behavior |
20
+ | --- | --- |
21
+ | Capability discovery/input | Build a closed `capabilities[]` set from the host's known capabilities. Include stable `id`, `kind`, `name`, `description`, `permissions`, `risk`, and availability metadata where known. Do not ask Jev to discover or execute hidden host tools. |
22
+ | `jev_route` call | Send `schema_version: 1`, `harness`, `intent`, bounded `context`, `actor_permissions`, `capabilities`, and `policy` to `jev_route`. Preserve the returned `correlation_id` and selected capability id. |
23
+ | Host execution | Resolve the selected id through the harness's native registry. The adapter must not shell out to arbitrary ids, grant permissions, or replace native tool execution. |
24
+ | `jev_record_execution` receipt | After the host decides what happened, call `jev_record_execution` with the same `correlation_id`, `status` (`completed`, `failed`, or `not_started`), `capability_id`, bounded result/error, and optional exit/timing metadata. |
25
+ | Fail-open | If Jev is disabled, unavailable, times out, returns an error, or returns no usable selection, continue through the harness's normal native path. Never guess a capability or treat a Jev failure as permission to execute. |
26
+ | Approval semantics | The host remains the approval authority. Consequential actions require the host's normal approval before execution. A denial records `not_started`; Jev cannot approve, elevate, retry, or override the host. |
27
+
28
+ `jev_browser_step` follows the same ownership rule: the host supplies a structured observation, the host approves consequential browser actions, and the host executes or hands control back. It is experimental and opt-in.
29
+
30
+ ### Minimal adapter pseudocode
31
+
32
+ ```text
33
+ request = {
34
+ schema_version: 1,
35
+ harness: "my-harness",
36
+ intent: host_goal,
37
+ context: bounded_host_context,
38
+ actor_permissions: host_permissions,
39
+ capabilities: host_capabilities,
40
+ policy: host_policy
41
+ }
42
+
43
+ decision = call_jev_route(request)
44
+
45
+ if decision.status != "selected" or decision.selected is null:
46
+ return native_host_path(request)
47
+
48
+ if consequential(decision.selected) and not host_approval(decision.selected):
49
+ call_jev_record_execution({
50
+ correlation_id: decision.correlation_id,
51
+ capability_id: decision.selected,
52
+ status: "not_started",
53
+ error: "host approval denied"
54
+ })
55
+ return native_host_path(request)
56
+
57
+ try:
58
+ host_result = execute_native(decision.selected)
59
+ status = "completed"
60
+ except error:
61
+ host_result = null
62
+ status = "failed"
63
+
64
+ receipt = call_jev_record_execution({
65
+ correlation_id: decision.correlation_id,
66
+ capability_id: decision.selected,
67
+ status,
68
+ result: bounded(host_result),
69
+ error: bounded(error),
70
+ duration_ms: measured_duration
71
+ })
72
+ return { decision, host_result, receipt }
73
+ ```
74
+
75
+ Copy `integrations/template/adapter.mjs` for a small JavaScript starting point with the same injected boundaries.
76
+
77
+ ## Adding a new harness
78
+
79
+ The shortest supported PR path is:
80
+
81
+ 1. Add `integrations/<harness>/` with a thin adapter that calls the existing CLI or MCP contract.
82
+ 2. Add a secret-free config/example snippet under `config/` or the integration directory.
83
+ 3. Add an offline smoke fixture proving route, fail-open, approval denial, host execution, and execution receipt behavior.
84
+ 4. Register compatibility in `README.md`, the translated READMEs, `docs/SCHEMA-VERSIONING.md`, and `RELEASE.md` when the harness is supported.
85
+ 5. Run the required CI commands and submit the PR.
86
+
87
+ Do not add a harness-specific routing implementation. Keep configuration user-owned; never overwrite global harness settings.
88
+
89
+ ## Adding a provider
90
+
91
+ Providers implement the existing provider surface in `src/providers/`: a `name` and an async `decide({ state, candidates })` method. Supervision-capable providers may also implement `evaluate({ state, questions })`. Return the normalized provider response expected by `src/route.mjs`; do not execute capabilities in the provider.
92
+
93
+ - Add the provider to explicit configuration/selection only when it is usable offline or clearly fails open.
94
+ - Add deterministic unit tests using injected responses or the `demo` provider.
95
+ - Keep API keys and endpoints in environment variables or user-owned configuration.
96
+ - Provider-backed tests belong in secret-managed CI, not ordinary pull-request CI.
97
+
98
+ ## Adding a discovery source
99
+
100
+ Use `discoverCapabilities()` and the normalized capability shape in `src/discovery.mjs`. A new source must:
101
+
102
+ - produce stable, namespaced ids;
103
+ - preserve `kind`, `name`, `description`, `source`, `verified`, and availability metadata;
104
+ - deduplicate by id deterministically;
105
+ - read only explicit input or an explicitly supplied manifest path;
106
+ - never scan undocumented global locations or execute discovered entries.
107
+
108
+ Add a fixture covering empty input, malformed entries, duplicate ids, unavailable entries, and the new source's normalized output.
109
+
110
+ ## Adding a browser executor
111
+
112
+ Browser executors are host-owned and optional. Implement `observe()` plus `execute(action)`, and implement `select(action)` when the host has a native select mechanism. The observation must be bounded and structured; the executor must validate target ids, preserve host approval, return the next observation, and report failures without retrying implicitly. The host may supply a prepared PNG/JPEG screenshot through the existing advisory image contract. Do not add screenshot capture, text generation, browser workers, or permission logic to jev-layer as part of an executor contribution.
113
+
114
+ ## Adding an eval or replay fixture
115
+
116
+ Add a small JSONL or JSON fixture under `examples/` or a test fixture directory. Include a stable `schema_version`, `harness`, bounded capabilities, and deterministic expected selection/fallback behavior. For receipts, use one `correlation_id` for the routing case and execution receipt. Exercise it with:
117
+
118
+ ```sh
119
+ npm run replay:evaluate -- --provider demo --limit 20
120
+ npm test
121
+ ```
122
+
123
+ A fixture must not call a real provider, host command, network service, or browser. If a real-provider scenario is useful, document it separately and gate it on an explicitly supplied secret.
124
+
125
+ ## Required checks
126
+
127
+ From a clean checkout:
128
+
129
+ ```sh
130
+ npm install
131
+ npm test
132
+ npm run smoke
133
+ npm run fail-open-smoke
134
+ npm run clean-install-smoke
135
+ npm pack --dry-run
136
+ ```
137
+
138
+ Changes touching browser, supervision, context filtering, discovery, or MCP should also run the matching existing E2E/smoke script. CI does not require provider credentials.
139
+
140
+ ## Backward compatibility
141
+
142
+ - Keep schema v1 request, decision, receipt, and replay fields readable.
143
+ - Prefer additive optional fields. Do not rename or remove existing fields in a patch release.
144
+ - Preserve `correlation_id` across route and execution records.
145
+ - Preserve fail-open behavior and host approval ownership.
146
+ - If a breaking contract is unavoidable, document a new schema/adapter version and migration before changing the implementation.
package/LICENSE CHANGED
@@ -1,21 +1,21 @@
1
- MIT License
2
-
3
- Copyright (c) 2026 jev-layer contributors
4
-
5
- Permission is hereby granted, free of charge, to any person obtaining a copy
6
- of this software and associated documentation files (the "Software"), to deal
7
- in the Software without restriction, including without limitation the rights
8
- to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
- copies of the Software, and to permit persons to whom the Software is
10
- furnished to do so, subject to the following conditions:
11
-
12
- The above copyright notice and this permission notice shall be included in all
13
- copies or substantial portions of the Software.
14
-
15
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
- SOFTWARE.
1
+ MIT License
2
+
3
+ Copyright (c) 2026 jev-layer contributors
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.