forgeos 0.1.0-alpha.68 → 0.1.0-alpha.69

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 (57) hide show
  1. package/.agents/skills/forge-agent-fabric/SKILL.md +21 -1
  2. package/.agents/skills/forge-agent-fabric/references/repository-analysis.md +102 -0
  3. package/.agents/skills/forge-agent-fabric/scripts/repository.mjs +44 -0
  4. package/AGENTS.md +1 -1
  5. package/CHANGELOG.md +16 -0
  6. package/README.md +12 -3
  7. package/docs/agent-fabric.md +13 -0
  8. package/docs/architecture/agent-fabric/REPOSITORY_MANIFEST_PLAN.md +272 -0
  9. package/docs/changelog.md +32 -0
  10. package/docs/repository-agent-benchmark.md +179 -0
  11. package/docs/repository-analysis.md +139 -0
  12. package/docs/repository-context-quality.md +179 -0
  13. package/docs/repository-runtime-observation.md +82 -0
  14. package/package.json +14 -2
  15. package/schemas/forge-manifest.schema.json +385 -53
  16. package/src/forge/_generated/releaseManifest.json +1 -1
  17. package/src/forge/_generated/releaseManifest.ts +3 -3
  18. package/src/forge/agent-fabric/managed-run-contract.ts +1 -0
  19. package/src/forge/agent-fabric/managed-run-service.ts +10 -1
  20. package/src/forge/agent-fabric/managed-run-store.ts +20 -0
  21. package/src/forge/agent-fabric/managed-workspace.ts +56 -18
  22. package/src/forge/agent-fabric/repository-context.ts +83 -0
  23. package/src/forge/agent-memory/mcp.ts +38 -1
  24. package/src/forge/cair/index.ts +15 -3
  25. package/src/forge/cair/types.ts +9 -2
  26. package/src/forge/cli/commands.ts +19 -0
  27. package/src/forge/cli/main.ts +15 -0
  28. package/src/forge/cli/parse.ts +70 -16
  29. package/src/forge/cli/repository.ts +151 -0
  30. package/src/forge/compiler/external-manifest/registry.ts +21 -9
  31. package/src/forge/delta/process-identity.ts +22 -16
  32. package/src/forge/repository-analysis/adapters/common.ts +72 -0
  33. package/src/forge/repository-analysis/adapters/docker.ts +185 -0
  34. package/src/forge/repository-analysis/adapters/java.ts +133 -0
  35. package/src/forge/repository-analysis/adapters/typescript.ts +350 -0
  36. package/src/forge/repository-analysis/adapters/vue.ts +71 -0
  37. package/src/forge/repository-analysis/analyze.ts +434 -0
  38. package/src/forge/repository-analysis/benchmark.ts +336 -0
  39. package/src/forge/repository-analysis/cache-gc.ts +154 -0
  40. package/src/forge/repository-analysis/check-selection.ts +123 -0
  41. package/src/forge/repository-analysis/context-node.ts +17 -0
  42. package/src/forge/repository-analysis/context.ts +456 -0
  43. package/src/forge/repository-analysis/http-resolution.ts +135 -0
  44. package/src/forge/repository-analysis/identity.ts +45 -0
  45. package/src/forge/repository-analysis/index.ts +18 -0
  46. package/src/forge/repository-analysis/nuxt-resolution.ts +188 -0
  47. package/src/forge/repository-analysis/quality.ts +60 -0
  48. package/src/forge/repository-analysis/retrieval.ts +309 -0
  49. package/src/forge/repository-analysis/runtime-artifacts.ts +195 -0
  50. package/src/forge/repository-analysis/runtime-observation.ts +316 -0
  51. package/src/forge/repository-analysis/scanner.ts +174 -0
  52. package/src/forge/repository-analysis/storage.ts +193 -0
  53. package/src/forge/repository-analysis/test-associations.ts +59 -0
  54. package/src/forge/repository-analysis/types.ts +99 -0
  55. package/src/forge/repository-manifest/index.ts +178 -0
  56. package/src/forge/repository-manifest/types.ts +63 -0
  57. package/src/forge/version.ts +1 -1
@@ -0,0 +1,179 @@
1
+ # Repository agent benchmark
2
+
3
+ Forge can prepare a reproducible experiment with and without repository maps, then
4
+ evaluate evidence supplied by an external runner. Planning and evaluation are pure:
5
+ they do not invoke Codex, read source files, execute application checks, install dependencies,
6
+ or grant permission to spend credits. A static retrieval fixture passing is useful evidence
7
+ about a packet, but does not demonstrate improved model productivity.
8
+
9
+ ## Prepare a paired plan
10
+
11
+ The CLI validates cache ownership, graph integrity and current source freshness before
12
+ planning. Save its complete JSON output; reporting accepts either that `{plan, ok,
13
+ exitCode}` envelope or the bare API plan. A model config contains only `provider`,
14
+ `name` and scalar `settings`, with no credentials:
15
+
16
+ ```text
17
+ forge repository benchmark-plan --cases tasks.json --model-config model.json --repetitions 2 --json
18
+ forge repository benchmark-report --plan plan.json --observations observations.json --json
19
+ ```
20
+
21
+ The model name is selected explicitly for the experiment, never inferred from the app.
22
+ Planning/reporting are read-only. `--write` is rejected. A valid report with no observations
23
+ has zero comparable pairs and pending results; CLI exit zero confirms valid input/report
24
+ generation only. Planning inputs are capped at 128 KiB, plan files at 128 MiB and observation
25
+ files at 16 MiB. Symlinks and sensitive input paths are refused.
26
+
27
+ Use `createRepositoryAgentBenchmarkPlan(snapshot, reviewedCases, options)` from
28
+ `src/forge/repository-analysis/benchmark.ts`. The caller must first read and validate a
29
+ current snapshot and verify source freshness through the repository context API. The
30
+ planner validates the complete snapshot structure and fingerprint; as a pure function
31
+ it cannot establish that files on disk have not changed since analysis.
32
+
33
+ ```ts
34
+ const plan = createRepositoryAgentBenchmarkPlan(snapshot, reviewedCases, {
35
+ model: {
36
+ provider: "codex",
37
+ name: "the-explicit-model-selected-for-the-experiment",
38
+ settings: { reasoningEffort: "high" },
39
+ },
40
+ repetitions: 2,
41
+ maxChars: 12000,
42
+ });
43
+ ```
44
+
45
+ `reviewedCases` uses the same strict contract as `repository quality`: unique case ID,
46
+ task query, optional repository-relative scope, expected/forbidden files and test names.
47
+ Keep failed retrieval cases in the experiment; removing them after seeing a failure
48
+ biases the comparison. Expected files are context relevance expectations, not a requirement
49
+ to edit those files and not sufficient acceptance criteria for application behavior.
50
+ Use a concrete task query with enough behavior and acceptance detail for independent review.
51
+
52
+ The JSON-serializable plan contains:
53
+
54
+ - `binding`: exact source root, snapshot ID, manifest/scenario hashes, and a digest of
55
+ the analyzed input file hashes and metadata.
56
+ - `model`: explicit provider, model name and scalar settings. Both arms share all settings.
57
+ - `cases`: reviewed context expectations, retained for the evaluator and reviewer.
58
+ - `runs`: two isolated runs per case and repetition. Both share prompt, scope, suggested
59
+ check declarations and model settings. `with-maps` additionally receives the bounded
60
+ `repositoryContext` packet. This is the only difference in `workerInput`.
61
+ - `planId`, `taskDigest`, `executionDigest`, and `runId`: deterministic content bindings.
62
+ Editing a plan invalidates its identity; foreign or altered observations are rejected.
63
+ - `execution: "not-executed"` and `authorization: "external-runner-required"`.
64
+
65
+ Repetitions are bounded to 1–10 and cases to 1–100. Run order alternates by repetition
66
+ to reduce ordering bias. Model settings include no implicit SDK defaults: declare any
67
+ settings that can affect output, and require the runner to use them consistently.
68
+
69
+ ## External runner contract
70
+
71
+ First obtain the normal authorization for model costs, repository changes and actual
72
+ application checks. The presence of a check command in a manifest or plan is a suggestion,
73
+ not authorization to execute it. The planner never starts a runner.
74
+
75
+ For each planned run, the external runner should:
76
+
77
+ 1. Prepare a fresh isolated checkout from the exact analyzed source baseline. Keep
78
+ originals unchanged. Verify input hashes, manifest/scenario, dependency state and
79
+ relevant environment before execution. Bind the observation to the original `binding`;
80
+ isolated checkout paths are runner artifacts, not replacement source bindings.
81
+ 2. Create a fresh worker session. Never reuse sessions between arms, cases or repetitions,
82
+ and prevent shared conversation or generated-artifact leakage between them.
83
+ 3. Pass **only that run's `workerInput`** to the worker. Do not pass the whole plan or
84
+ hidden expected/forbidden context files to the worker. Withhold other map tools from
85
+ the control arm; provide the same ordinary repository tools and permissions to both.
86
+ Ordinary agents may still read source and discover the same relationships themselves.
87
+ 4. Record SDK/provider counters for actual input/output/cached input tokens, wall-clock
88
+ latency, and instrumented source-read events. Use evidence references to durable
89
+ traces or logs. Do not infer tokens from character count, reads from filenames in the
90
+ response, or zero latency/read counts from missing telemetry.
91
+ 5. Preserve the resulting diff/artifact and its SHA-256 digest. Run authorized declared
92
+ application checks in each isolated checkout and record observed outcomes. A map
93
+ query succeeding is not an application check. Missing or skipped checks remain unknown
94
+ or `not-run` and prevent a comparable quality-qualified pair.
95
+ 6. Have a distinct reviewer inspect the concrete task, actual resulting artifact and
96
+ check evidence. Keep the reviewer blind to the arm and metrics where practical.
97
+ The reviewer must not be any worker in this experiment. Record their verdict against
98
+ that artifact digest; a static retrieval pass cannot substitute for this review.
99
+ 7. Supply one observation per completed, failed or cancelled run. Keep missing runs
100
+ absent rather than inventing outcomes. Preserve all original evidence artifacts.
101
+
102
+ The source binding describes the baseline before the worker's edits. Never stamp a
103
+ newer snapshot onto an older result. If the source baseline changes, create a new plan.
104
+ Identical baseline hashes are necessary but insufficient for environment equivalence;
105
+ the runner must record and control dependency versions, network state, tools, limits
106
+ and permissions. The evaluator cannot authenticate those conditions.
107
+
108
+ An observation has this shape (digest placeholders must be replaced by real values):
109
+
110
+ ```json
111
+ {
112
+ "planId": "copy-exact-planId",
113
+ "runId": "copy-exact-runId",
114
+ "binding": { "root": "copy-source-root", "snapshotId": "copy-snapshotId", "inputDigest": "copy-inputDigest", "manifestHash": "copy-manifestHash", "scenarioHash": "copy-scenarioHash" },
115
+ "taskDigest": "copy-exact-taskDigest",
116
+ "executionDigest": "copy-exact-executionDigest",
117
+ "model": { "provider": "codex", "name": "the-actual-explicit-model-used", "settings": { "reasoningEffort": "high" } },
118
+ "workerId": "actual-isolated-session-id",
119
+ "status": "completed",
120
+ "artifactDigest": "sha256:<actual-64-hex-digest>",
121
+ "artifactEvidenceRef": "artifact:actual-diff",
122
+ "metrics": {
123
+ "inputTokens": 1200,
124
+ "outputTokens": 400,
125
+ "latencyMs": 5000,
126
+ "sourceReads": [{ "path": "src/example.ts", "chars": 800, "evidenceRef": "trace:actual-read-event" }],
127
+ "evidenceRefs": ["trace:actual-provider-and-runner-counters"],
128
+ "provenance": "executor-observed"
129
+ },
130
+ "checks": [{ "id": "actual-declared-check-id", "status": "passed", "evidenceRef": "check:actual-exit-and-output" }],
131
+ "review": {
132
+ "reviewerId": "actual-independent-review-session-id",
133
+ "artifactDigest": "sha256:<same-actual-artifact-digest>",
134
+ "outcome": "accepted",
135
+ "evidenceRef": "review:actual-review-report"
136
+ }
137
+ }
138
+ ```
139
+
140
+ All metric fields except `evidenceRefs` and `provenance` are optional. Omit unavailable
141
+ counters. The observation's actual reported model/settings must match the declared model,
142
+ including settings. A substituted model or reasoning setting invalidates the comparison.
143
+ `sourceReads: []` asserts the runner observed zero reads; absence means unknown.
144
+ Repeated read events count separately, while `uniqueSourceFiles` deduplicates paths.
145
+ Read character totals remain unknown unless every observed event includes a character count.
146
+ Token counters are nonnegative safe integers; cached input cannot exceed observed input.
147
+ Check statuses are `passed`, `failed`, `not-run`, or `unknown`; executed statuses require
148
+ evidence. Review outcomes are `accepted`, `changes-requested`, or `inconclusive`.
149
+
150
+ ## Evaluate and interpret
151
+
152
+ ```ts
153
+ const report = evaluateRepositoryAgentBenchmark(plan, observations);
154
+ ```
155
+
156
+ The evaluator rejects mutated plans, foreign source roots/snapshots/input digests,
157
+ different tasks/execution settings, duplicate runs, undeclared checks, unsupported
158
+ fields, invalid counters, artifact review mismatches and reused worker identities.
159
+ Reviewers must be independent of all workers. It does not execute or authenticate
160
+ anything: the report labels its provenance `external-runner-reported` and preserves
161
+ the references supplied with each observation for independent verification.
162
+
163
+ A pair is comparable only when both arms completed, both actual artifacts received
164
+ accepted independent reviews, and all suggested checks declared for that task passed
165
+ with evidence. The report keeps other pairs as `pending`, `execution-incomplete`,
166
+ `review-required`, or `checks-required`. An empty declared check set does not invent
167
+ application coverage: independent task review is still required.
168
+
169
+ For each comparable pair, differences are **with maps minus without maps**. Negative
170
+ token, latency or source-read differences indicate lower observed values for that pair;
171
+ they say nothing about quality unless its review and checks qualified it. Aggregate
172
+ metrics contain an observed-pair count and mean difference. Missing metrics remain
173
+ `null`, including when a quality-qualified pair has no telemetry. Zero is reserved for
174
+ an explicitly observed zero or an actual equal-value difference.
175
+
176
+ Treat the report as a reproducible protocol and evidence ledger. Small fixture samples
177
+ do not establish a general benefit, statistical significance, real user acceptance or
178
+ production readiness. Report failures, review disagreements, omitted telemetry, environment
179
+ limitations and the exact tasks/model/settings alongside any measured improvement.
@@ -0,0 +1,139 @@
1
+ # Forge maps in existing repositories
2
+
3
+ Optional [runtime observation](repository-runtime-observation.md) supplements static maps
4
+ with explicitly executed, source-bound generated artifacts. Review `runtime-plan`, opt in
5
+ with `runtime-observe --execute`, and read current evidence with `runtime-context`.
6
+ Static analysis remains free of implicit project execution.
7
+
8
+ Large snapshot storage uses canonical-order v2 partitions and on-demand graph
9
+ hydration, with eager compatibility for v1. Published analysis performs conservative
10
+ cache maintenance. Use `forge repository cache-gc --json` to preview it, and `--write`
11
+ to apply after retention (24 hours by default). Checks/models remain unexecuted.
12
+ See [context quality and cache contracts](repository-context-quality.md) and
13
+ [paired agent benchmark](repository-agent-benchmark.md) for the detailed guarantees.
14
+
15
+ Forge repository analysis produces static maps and compact agent context without migrating
16
+ the application to Forge's runtime. Vue/Nuxt, Java/Spring, TypeScript/JavaScript and
17
+ Docker/Compose can coexist in one repository manifest. Analysis is available without Git;
18
+ managed Agent Fabric workflows require a Git repository with an initial commit.
19
+
20
+ ## Prepare a manifest with Codex
21
+
22
+ Ask the Codex agent to prepare the project for Forge maps. Discovery returns a draft;
23
+ the agent checks component roots and frameworks against project instructions and source,
24
+ then saves the manifest within the authorized edit scope. Discovery does not overwrite
25
+ an existing service manifest.
26
+
27
+ From the target project, using an absolute shared runtime path:
28
+
29
+ ```text
30
+ node <forge-runtime>/bin/forge.mjs manifest discover --json
31
+ node <forge-runtime>/bin/forge.mjs manifest validate forge.manifest.json --json
32
+ node <forge-runtime>/bin/forge.mjs repository analyze --write --json
33
+ node <forge-runtime>/bin/forge.mjs repository context --query routes --json
34
+ node <forge-runtime>/bin/forge.mjs repository context --query infrastructure --json
35
+ node <forge-runtime>/bin/forge.mjs repository context --query coverage --json
36
+ node <forge-runtime>/bin/forge.mjs repository quality --cases <absolute-reviewed-cases.json> --json
37
+ ```
38
+
39
+ Discovery without `--write` and validation are read-only. Analysis with `--write` explicitly produces local artifacts;
40
+ no application generation, runtime dependency, hook installation, Docker startup or Java
41
+ build is required. The runtime does not need to reside in the target repository. Use
42
+ `--root` for an explicit target, including directories without package.json or Git.
43
+
44
+ Repository manifests use protocol 2.0 and a repository discriminator. Service manifests
45
+ using protocol 1.0 remain separate executable contracts and retain compatibility.
46
+
47
+ ```json
48
+ {
49
+ "forgeProtocol": "2.0",
50
+ "kind": "repository",
51
+ "components": [
52
+ { "id": "web", "root": "frontend", "adapters": ["vue", "typescript"] },
53
+ { "id": "api", "root": "backend", "adapters": ["java", "spring", "maven"] },
54
+ { "id": "infra", "root": ".", "adapters": ["docker"], "files": ["compose.yaml", "backend/Dockerfile"] }
55
+ ],
56
+ "checks": [{ "id": "web-tests", "component": "web", "argv": ["npm", "test"] }]
57
+ }
58
+ ```
59
+
60
+ The manifest describes analysis configuration, not every function. Roots and files are
61
+ relative to the target project. Checks are suggestions and never run during discovery,
62
+ analysis or queries. `.forge/fabric.json` continues to configure managed execution;
63
+ repository manifest checks do not override explicit workflow acceptance obligations.
64
+
65
+ ## Understand evidence and coverage
66
+
67
+ The graph records nodes, relations, locations, source hashes, adapter versions and
68
+ assurance (`declared`, `syntactic`, `resolved`, `inferred`). The coverage report describes
69
+ ignored and unsupported files, diagnostics, unresolved behavior and adapter limitations.
70
+
71
+ Vue maps expose components, script symbols and visible bindings. Java maps expose syntax,
72
+ Spring endpoints and build declarations. Docker maps expose declared builds and Compose
73
+ topology. None of these constitute observed runtime behavior: a port is not a health check,
74
+ `depends_on` is not proof of traffic, and static test association is not executed coverage.
75
+ Dynamic configuration, Java reflection and Vue autoimports can remain unresolved.
76
+ Static Nuxt aliases, local autoimports and supported HTTP clients have additional
77
+ resolution paths. Ambiguous candidates remain visible. Test associations are case-level;
78
+ sharing a test file does not establish that all cases exercise an imported symbol.
79
+ See [repository context quality](repository-context-quality.md) for the declaration
80
+ schema, retrieval rules, cache limits and reviewed task benchmark.
81
+
82
+ Local TypeScript/JavaScript config inheritance, project references, baseUrl and path aliases
83
+ are read statically inside the selected repository. Package-provided executable configuration
84
+ and external inheritance remain unresolved. Vue conditional template branches are included;
85
+ Docker instructions continued across physical lines are joined before extraction.
86
+
87
+ Real `.env` files and credential files are excluded. Unknown environment interpolation
88
+ remains unknown. Analysis does not run scripts, executable config, Gradle/Maven wrappers,
89
+ Docker or arbitrary external adapters. Source snippets are not emitted by default.
90
+
91
+ ## Query current snapshots
92
+
93
+ Queries include overview, locate, symbol, references, routes, dependencies, impact, tests,
94
+ infrastructure and coverage. Use exact node IDs to disambiguate repeated names. Compact
95
+ symbol handles are local to a snapshot and require its snapshotId; they cannot be carried
96
+ to a new snapshot. Sources changed after analysis make the result stale. Reanalyze before
97
+ requesting definitions or applying map evidence to a task.
98
+
99
+ Repository context accepts `--limit` from 1 to 100 and `--max-chars` from 2048 to 50000.
100
+ The same limits apply to MCP context tools. MCP analysis returns bounded coverage samples
101
+ with omitted counts; saved snapshots retain the complete analysis report. Cached graphs are
102
+ validated for structure, identity, containment and source provenance before queries.
103
+
104
+ Artifacts normally reside in `.forge/repository/`, outside generated application code.
105
+ No `.gitignore` is edited automatically. A host-local cache can keep outputs outside the
106
+ project. Omit `--write` when only an ephemeral analysis result is authorized. Parsing
107
+ reuse is based on content hashes; graph identity also includes manifest and scenario.
108
+
109
+ The CAIR repository provider serves read queries. Runtime-specific or mutating CAIR
110
+ actions are unavailable for this provider. An impact map describes potential dependencies
111
+ and does not authorize skipping required tests.
112
+
113
+ ## Use with Agent Fabric
114
+
115
+ Install the personal Forge Agent Fabric skill once. Its `scripts/repository.mjs` helper
116
+ uses the installed shared runtime with an explicit target directory and does not require
117
+ Git. The original `scripts/fabric.mjs` helper retains the Git requirement for execution.
118
+ No per-project runtime dependency, hook or MCP installation is required for maps.
119
+
120
+ When a managed SDK attempt contains a valid repository manifest, Fabric analyzes its
121
+ prepared clone after composing upstream artifacts and preparing dependencies. A bounded
122
+ packet contains scoped nodes and edges, coverage limitations, clone snapshot identity and
123
+ suggested checks with argv/cwd, reasons and requirement status. Task neighbors are
124
+ read-only unless already inside write scope. Static quality counters remain partial;
125
+ `ready` means the packet was prepared. The run status records source project and clone identities separately,
126
+ with phase `prepared-input`; it does not claim the same map describes subsequent worker edits.
127
+ Reviewers receive a fresh snapshot of the combined upstream changes, not the map from the
128
+ original checkout. Matching parse facts can be reused from the source cache while graph
129
+ identity and connections are rebuilt for the clone. Analysis writes no cache into managed clones.
130
+
131
+ A missing manifest leaves existing workflows unchanged. Invalid configuration or
132
+ unavailable analysis is reported as unavailable; the worker must inspect current code
133
+ directly. It never receives a purported fallback graph from another checkout. Maps do not
134
+ alter write scopes, independent review, explicit command verification or publication gates.
135
+ Publication still means applying scoped local changes, not Git push, npm or deployment.
136
+
137
+ MCP queries can use projects registered with Fabric; select the project explicitly.
138
+ Each root and snapshot remain distinct, including separate Windows/WSL copies. Cross-project
139
+ queries do not assert a simultaneous global snapshot or automatically synchronize checkouts.
@@ -0,0 +1,179 @@
1
+ # Repository context quality for Agent Fabric
2
+
3
+ Forge can map an existing repository without converting it into a Forge application. The Codex chat remains the interface; a repository manifesto declares the analysis boundary and optional checks. Analysis reads source and static configuration. It does not evaluate Nuxt/Vite configuration, start Docker, install packages, call remote APIs or execute the checks.
4
+
5
+ ## Implementation plan and boundaries
6
+
7
+ 1. Capture a managed baseline and editable task scope. Carry readonly descriptors/lockfiles with the captured input. Preserve source changes outside that scope.
8
+ 2. Apply upstream artifacts in an isolated clone and prepare its authorized environment. Regenerate repository context from that prepared clone, rather than reusing the source snapshot. Bind the clone identity, source digests, manifest and scenario to the snapshot.
9
+ 3. Resolve static alias and Nuxt declarations inside each component. Give explicit manifesto declarations precedence where automatic static discovery cannot resolve dynamic configuration. Keep unresolved or ambiguous references visible; avoid inventing imports from names alone.
10
+ 4. Link local HTTP client calls to routes only with supporting evidence: known client declaration, literal method/path and compatible API component. Preserve unresolved calls when hosts, path construction or multiple candidates make the connection uncertain.
11
+ 5. Select graph context relevant to the task's files/nodes/components. Preserve snapshot binding, paths, locations, relation evidence and gaps when truncating. The snapshot retains source hashes; the compact packet refers back to it. A compact packet must say what was omitted.
12
+ 6. Select relevant declared checks and explain why. Include their original argv, explicit working directory, cost/category and requirement status. The selector does not authorize or execute them.
13
+ 7. Report preparation, freshness, coverage and relation assurance separately. Verify the final clone packet with fixtures for Nuxt, HTTP clients, partial graphs and check relevance. A paid agent run and a real application test require their own evidence.
14
+
15
+ Changes to the manifesto are optional extensions of protocol `2.0`, kind `repository`. Existing components, checks and the executable service protocol `1.0` retain their previous contracts. Missing extensions do not mean a framework feature is unsupported; they mean no extra declaration was supplied.
16
+
17
+ ## Static analysis declarations
18
+
19
+ ```json
20
+ {
21
+ "forgeProtocol": "2.0",
22
+ "kind": "repository",
23
+ "components": [
24
+ {
25
+ "id": "web",
26
+ "root": "web",
27
+ "adapters": ["vue", "nuxt"],
28
+ "analysis": {
29
+ "aliases": { "@": "src", "~": "src" },
30
+ "nuxt": {
31
+ "rootDir": ".",
32
+ "srcDir": "src",
33
+ "components": ["src/components"],
34
+ "imports": ["src/composables"]
35
+ }
36
+ }
37
+ },
38
+ { "id": "api", "root": "api", "adapters": ["java", "spring"] }
39
+ ],
40
+ "httpClients": [
41
+ {
42
+ "id": "apiClient",
43
+ "component": "web",
44
+ "files": ["src/services/**"],
45
+ "basePath": "/api",
46
+ "apiComponent": "api"
47
+ }
48
+ ],
49
+ "checks": [
50
+ {
51
+ "id": "web-typecheck",
52
+ "component": "web",
53
+ "argv": ["npm", "--prefix", "web", "run", "typecheck"],
54
+ "files": ["src/**"],
55
+ "category": "typecheck",
56
+ "cost": "low",
57
+ "requires": ["node"]
58
+ },
59
+ {
60
+ "id": "api-integration",
61
+ "component": "api",
62
+ "cwd": "api",
63
+ "argv": ["./mvnw", "verify"],
64
+ "category": "integration",
65
+ "cost": "high",
66
+ "requires": ["java", "docker", "network"]
67
+ }
68
+ ]
69
+ }
70
+ ```
71
+
72
+ All `analysis` paths, alias targets and HTTP client `files` are relative to `component.root`. In particular, `srcDir` is relative to the component root, **not** to `rootDir`. Component roots remain repository-relative. These declarations provide a static interpretation; they do not promise complete Nuxt runtime equivalence.
73
+
74
+ Aliases have at most 100 entries. Names are bounded to 128 characters, reject traversal segments and prototype keys, and map to contained relative paths. Nuxt declarations accept only `rootDir`, `srcDir`, `components` and `imports`; each directory list has at most 100 entries. Unknown fields, scripts, absolute paths, Windows streams, backslashes, control characters and `..` segments are rejected. Consumers must preserve physical containment and refuse symlink traversal when reading resolved files.
75
+
76
+ An HTTP client `id` identifies the local variable/function used by the source adapter, such as `apiClient`, `$fetch` or `axios`. IDs are unique within their component and have at most 80 characters. `files` scopes that declaration to component-relative files/globs. `apiComponent` names an existing component and scopes possible route targets; it is an explicit declaration, not proof that a call reaches that service at runtime. `basePath` contains only a literal URL path beginning with `/`, at most 2048 characters. Origins, credentials, query strings, fragments, percent escapes and traversal are rejected. The manifesto never contains headers, environment values, credentials or executable client configuration.
77
+
78
+ The runtime validator also checks component references and duplicate identities. JSON Schema validates structure and bounds; reference/identity checks remain the runtime validator's responsibility. Manifest files retain the existing 256 KiB reading limit.
79
+
80
+ ## Check relevance contract
81
+
82
+ `selectRepositoryChecks(snapshot, task)` is a pure selection API. `task` accepts optional repository-relative `scope`, exact `nodeIds`, component IDs and caller-reported `capabilities`. It returns `checks`, `diagnostics` and `execution: "not-executed"`. The caller should pass a freshly validated snapshot; the pure selector itself does not read files or verify freshness.
83
+
84
+ Checks retain required `id`, `component` and `argv`. Optional fields are:
85
+
86
+ | Field | Meaning |
87
+ | --- | --- |
88
+ | `cwd` | Repository-relative working directory. Omitted means `.`; old argv with `--prefix web` keeps its original interpretation. |
89
+ | `files` | Component-relative files/globs limiting relevance. Empty/omitted means component-wide. This is not permission to edit those files. |
90
+ | `category` | `typecheck`, `test`, `lint`, `build`, `integration`, `security` or `other`. |
91
+ | `cost` | Declared `low`, `medium` or `high`; low-cost declarations sort first. No cost is measured or presumed free. |
92
+ | `requires` | Up to 32 unique symbolic capability names, such as `java`, `docker` or `network`. No values or environment assignments. |
93
+
94
+ A component is relevant when explicitly selected, touched by task scopes/nodes, or directly adjacent to a selected node through a complete declared/resolved edge. Inferred or unresolved edges do not automatically expand check selection. File-limited checks must overlap a relevant file or scope, unless the user explicitly selected the whole component. Directory/glob scopes conservatively include future/unindexed files. This may suggest extra checks; it does not prove those checks cover the task.
95
+
96
+ Every suggestion contains reasons such as `task-component:web`, `task-node-component:web`, `related-node-component:api`, `task-scope-overlaps-component`, `check-files-match-task` or `check-files-overlap-scope`. Unknown node/component references produce diagnostics. Unsafe task scopes or invalid manifests return no suggestions. Empty task selectors return no suggestions.
97
+
98
+ Requirements report `satisfied` when there are no requirements or the caller explicitly reports all of them; `missing` when the caller's capability list omits required entries; and `unknown` when capabilities were not provided. The selector never probes executables, reads environment variables or infers network authorization. Even `satisfied` means only the declaration was satisfied by caller-provided information, not that the command ran successfully.
99
+
100
+ The consumer must show argv as an array, without shell concatenation, and retain `execution: "not-executed"`. A future execution tool must separately bind the checkout, validate physical cwd containment, apply environment/network/cost authorization and record exit status/output against the input digest. A check named `test` is not evidence until it actually executes successfully on the relevant bytes.
101
+
102
+ ## Context quality contract
103
+
104
+ `ready` describes whether a usable packet was prepared. `prepared-input` describes the clone phase from which that packet was generated. Neither describes semantic completeness or successful application verification.
105
+
106
+ A packet should expose these independent dimensions:
107
+
108
+ | Dimension | Required interpretation |
109
+ | --- | --- |
110
+ | Preparation | Absent/invalid manifest, unavailable analyzer, successful packet or bounded failure. Errors must remain visible. |
111
+ | Input phase | Source, composed upstream input or prepared input, with clone identity and snapshot binding. |
112
+ | Freshness | Source/config/manifest inventory matches the analyzed snapshot, or stale/mismatch status. |
113
+ | Coverage | Found/analyzed/ignored/unsupported/error counts and visible limitations. |
114
+ | Relation assurance | Declared, syntactic, resolved or inferred, together with complete/partial/unresolved resolution. |
115
+ | Budget | Packet truncation and omitted context. A small packet is not the entire graph. |
116
+ | Verification | Suggested checks versus independently observed execution results. |
117
+
118
+ Avoid reducing these dimensions to one percentage or a generic “complete” flag. For example, a prepared-input packet can be fresh and usable while Java reflection, Nuxt runtime injection or dynamic HTTP URLs remain unresolved. Explicit manifesto hints improve navigation but remain declared evidence.
119
+
120
+ ## Validation and remaining limits
121
+
122
+ ### Case-level test evidence
123
+
124
+ Test suites and executable cases are separate nodes. Importing a module establishes a `test-file-depends-on` edge between files; it does not associate every case in that file with every imported function. `test-references` means a reference inside that case's callback. `test-exercises` means a statically resolved call, including named import aliases and bounded same-file helper chains (three levels, at most 128 visited nodes). Both carry `observedCoverage: false`. A conventional test filename supplies navigation only. Test queries follow precise associations and exclude unrelated sibling cases.
125
+
126
+ ### Static Nuxt and HTTP resolution
127
+
128
+ Literal Nuxt `rootDir`, `srcDir`, aliases, component directories and import directories are read through the syntax tree. Executable expressions remain unknown. Component and composable candidates come only from scanned local files, and multiple candidates remain ambiguous. External UI packages, module-generated imports, layers and runtime injection can remain unresolved. Manifest analysis paths provide contained, explicit overrides. TypeScript compiler aliases and explicit relative imports keep their precedence.
129
+
130
+ HTTP analysis recognizes immutable local constants, bounded templates, Axios and `$fetch` factories, Nuxt-provided clients and simple returned-call wrappers across imports. A template can additionally retain a separate path pattern when each unknown placeholder occupies a whole segment and comes from a numeric parameter or an encoded scalar parameter. The URL remains dynamic; only a unique compatible endpoint can become a partial candidate link. Dynamic hosts/query strings, embedded or unbounded string expressions and ambiguous routes remain unresolved. Calls belong to the nearest containing function or arrow, including calls initializing local response variables. An absolute external origin needs an explicit API-component declaration before it can become a local service association. Unknown runtime base URLs and document-relative URLs remain unresolved. Manifest client mappings carry declared evidence with `runtimeRoutingVerified: false`; they cannot establish what a deployed reverse proxy or environment actually does.
131
+
132
+ ### Task retrieval and write scope
133
+
134
+ `selectRepositoryContext` uses deterministic ranking for exact symbols, IDs and paths, normalized English/Portuguese task terms and declared write scope. Exact targets suppress expansion through generic instruction verbs. The selector reserves space for actual consumers and precise tests, then follows at most two relevant graph hops, including function-to-HTTP-call-to-endpoint paths. Shared test files and imports are not bridges to unrelated cases. Java call sites are grouped for broad locate queries; expanding a group requires its snapshot binding.
135
+
136
+ Each selected node includes location, assurance, selected metadata, selection reasons and `access: write-scope | read-only`. Neighbor inclusion never changes the scope. Relations and groups retain their endpoints when the packet is truncated. Node/edge counts, character budgets and omitted counts are explicit. Fabric uses a 10,000-character selection budget and a 16,000-character packet budget, includes relevant check argv/cwd as informational data, and records static quality in run metadata. Preparation failures report `unavailable`, including failures after successful analysis.
137
+
138
+ ### Partitioned cache and prepared clones
139
+
140
+ Analyzer version `1.2.1` invalidates incompatible parse facts. Small snapshots retain legacy JSON storage. Large graphs use a bounded index plus content-addressed, hash-checked partitions; source facts are partitioned by file. Snapshot storage v2 partitions preserve canonical ID order, enabling sequential validation and scans. V1 component partitions remain readable through the eager compatibility path. Publication uses the existing analysis lock and an atomic header rename, so an incomplete write does not publish an incomplete graph. Readers reject corrupt, oversized, missing or unsafe partitions.
141
+
142
+ The v2 reader builds compact ID/position and relation indexes, then hydrates nodes/edges on demand through array-compatible read-only collections. A two-partition LRU limits retained decoded partitions within that cache. Full integrity, structure, root ownership and canonical fingerprint validation still reads every current partition before exposing the graph; source freshness is checked separately as before. Streaming canonical JSON hashing avoids building a second complete graph and serialization string. Relation sorting uses compact summaries, and budget-impossible neighbors are rejected before hydration. `repositoryStorageMetrics(snapshot)` reports actual partition reads/bytes and peak **serialized resident payload**, not decoded heap. Candidate lists, broad query results and callers retaining nodes can consume additional memory; this is not a promise of constant memory for arbitrary queries or a database with a full-text index. Returned node objects retain the previous mutable data contract, while partition-backed arrays reject mutations.
143
+
144
+ Successful `repository analyze --write` performs conservative cache maintenance automatically. Identical published headers remain stable apart from the creation time of a new in-memory result; unchanged cache generations keep their original `createdAt`. The first warm run may update reuse statistics. Library callers can disable maintenance with `cacheCleanup: false`. A maintenance failure preserves the successful publication and exposes `REPOSITORY_CACHE_CLEANUP_DEFERRED`; it never reclaims a foreign lock.
145
+
146
+ `repository cache-gc --json` previews cleanup; adding `--write` applies it. The collector preserves all current snapshot/fact references, validates them before mutation, rejects symlinked inventories and journals first-observed orphan identities. Default retention is 24 hours (`--grace-hours 1..720`), with a one-hour minimum. It deletes only chunks continuously observed orphaned through that window. Any header replacement restarts the window conservatively; frequent changing inputs may delay reclamation. Readers that remain alive beyond the configured grace need external coordination or longer retention. Unknown regular files are retained. This command manages generated cache chunks only and never deletes repository source.
147
+
148
+ Managed clones may reuse read-only source parse facts only when path, component, adapter, analyzer version and source digest match. The graph is rebuilt for the actual clone, current manifest and scenario. A changed source file is reparsed. Facts do not supply source-root graph identities or relax the clone freshness check, and preparation writes no analysis cache in the clone. This is an optimization within the host user's trust boundary, not a sandbox against a malicious host user.
149
+
150
+ ### Reviewed task benchmark
151
+
152
+ Create a reviewed JSON array of 1–100 tasks. Names and file paths are bounded and duplicate identities/expectations are rejected. Include required files/tests and explicitly forbidden associations:
153
+
154
+ ```json
155
+ [
156
+ {
157
+ "id": "seo-homologation",
158
+ "query": "Corrigir validação SEO em homologação",
159
+ "scope": ["web/utils/seoEnvironment.ts"],
160
+ "expectedFiles": ["web/utils/seoEnvironment.ts", "web/nuxt.config.ts", "tests/seo.test.ts"],
161
+ "expectedTests": ["unsafe SEO in homologation"],
162
+ "forbiddenTests": ["unrelated checkout price"]
163
+ }
164
+ ]
165
+ ```
166
+
167
+ After explicitly creating the current analysis cache, run from the target repository:
168
+
169
+ ```text
170
+ node <forge-runtime>/bin/forge.mjs repository quality --cases <absolute-reviewed-cases.json> --json
171
+ ```
172
+
173
+ The command reads current snapshots, rejects stale source evidence, and never executes checks or agents. Exit zero means every supplied expectation passed; one means a benchmark/validation failure. Reports show missing/forbidden results, context characters, truncation, recall and precision against the declared file set. That precision is meaningful as total retrieval precision only when the reviewed set is exhaustive; legitimate undeclared neighbors lower it. A passing fixture is not proof that all repository relationships are resolved. Synthetic regression tasks cover SEO, checkout, scheduling, Vue consumers and frontend-to-Java HTTP links.
174
+
175
+ The paired agent experiment is implemented as a planner and evidence evaluator: `repository benchmark-plan --cases tasks.json --model-config model.json --repetitions 2 --json`, followed by `repository benchmark-report --plan plan.json --observations observations.json --json`. The planner binds identical prompts, scopes, models/settings and declared checks to source, manifest, scenario and snapshot identity; only the map packet differs between arms. The report accepts observed token/latency/source-read metrics, artifact-bound independent review and authorized check results. Missing evidence remains unknown and metric differences require comparable completed pairs. Neither command executes a model or an application check, and exit zero on a valid pending report is not an experiment success. See [the runner protocol](repository-agent-benchmark.md) for JSON contracts, counterbalancing and the external authorization boundary. No productivity results are claimed without actual runs.
176
+
177
+ Fixtures cover legacy/new manifesto validation, JSON Schema structure, traversal/unknown fields, declaration bounds, scoped HTTP identities, check selection by files/nodes/components, missing/unknown requirements and unchanged argv/cwd interpretation. Integration must additionally prove that the Fabric packet is rebuilt after upstream composition and environment preparation, and that source/manifest changes invalidate reused context.
178
+
179
+ Static repository analysis is not a Nuxt build, Java compiler, Docker scenario execution, network trace or production test. Same-user clones isolate ordinary edits but are not a security sandbox against an adversarial process with access to the host. Source repository publication and paid Codex workers remain governed by the existing Fabric workflow. EasyGrow validation must run only in a dedicated copy; its original repositories remain read-only.
@@ -0,0 +1,82 @@
1
+ # Repository runtime observation
2
+
3
+ ## Goal and scope
4
+
5
+ Forge can analyze an existing Vue/Nuxt, Java/Spring or Docker repository without converting it into a Forge application. Static maps remain useful before installing dependencies or starting the application. The optional runtime layer supplements those maps with artifacts produced by explicit commands in an independent temporary source copy.
6
+
7
+ The runtime layer answers questions such as which components Nuxt registered after module preparation, which Spring beans and mappings a selected profile exposed, which containers and networks an exported Docker inspection described, and which HTTP paths a recorded execution requested. It does not claim comprehensive execution coverage, production correctness, authentication of external services, or that a generated Nuxt declaration proves a rendered component.
8
+
9
+ ## Implementation plan
10
+
11
+ 1. Extend protocol 2.0 repository manifests with optional `runtime.observations`. Each observation identifies a component, a sequence of executable argv arrays, contained working directories, per-command timeouts and a list of supported artifact formats. Reject unknown fields, duplicate identities, excessive inputs and unsafe paths. Commands are reviewed configuration, never inferred execution authority from static checks.
12
+ 2. Implement pure, bounded collectors for Nuxt declarations, Spring Actuator mappings/beans, Docker inspection, HTTP traces and normalized Forge observations. Collect useful structural fields. Omit environment values, authorization, headers, request/response bodies, credentials, origins and query parameters. Malformed or oversized artifacts must not produce confident evidence.
13
+ 3. Build a read-only plan API. Show exactly which commands and artifacts are requested, the input binding and limits before execution. Planning must not create an owner, start an application, install dependencies, run a model or write a cache.
14
+ 4. Execute only with explicit runtime authorization. Copy eligible current sources into a unique temporary directory, excluding Git metadata, secrets, dependency directories and Forge caches. Execute finite commands with `shell:false`, bounded output and time, a restricted environment and cleanup of the process tree owned by the invocation. Source copy isolation protects the original checkout from ordinary relative writes; it is not an operating-system, network or container sandbox.
15
+ 5. Collect only fresh, contained regular artifacts from the invocation. Bind hashes, command statuses, observation identities, component, source inventory, manifest, scenario, environment label and timestamps into a digest-protected report. A failed command cannot contribute successful facts. Recheck source freshness before publication and fail closed on change.
16
+ 6. Save reports only with explicit `--write`. Read them without executing anything, verify structure, digest, source binding and expiration, and return a bounded context packet. File hashes establish integrity, not the authenticity or semantic correctness of a project-generated observation.
17
+ 7. Expose the same operations through CLI, portable skill and MCP. `runtime-plan` is read-only, `runtime-observe` requires `--execute`/`execute:true`, and `runtime-context` is read-only. Existing static context, quality checks and model benchmarks continue to report their own limited evidence.
18
+ 8. Let Agent Fabric consume compatible saved runtime evidence as an additional packet. Do not start runtime commands automatically while preparing a worker. Do not silently reuse an observation when composed upstream changes, manifest, scenario or full copied-input digest differ. Runtime context does not widen write scope or satisfy review/publication gates.
19
+ 9. Test actual child-process execution, fresh artifacts, failures, timeout/cancellation, process cleanup, secret omission, stale input and report corruption. Test formats against representative generated exports and distinguish fixtures from observations of a deployed system. Run repository tests, typecheck, generator/check, framework verification and package smoke before publication.
20
+
21
+ ## Manifest example
22
+
23
+ ```json
24
+ {
25
+ "forgeProtocol": "2.0",
26
+ "kind": "repository",
27
+ "components": [{ "id": "store", "root": "frontend-store", "adapters": ["typescript", "vue", "nuxt"] }],
28
+ "scenario": { "id": "local-observation", "mode": "development" },
29
+ "runtime": {
30
+ "observations": [{
31
+ "id": "store-generated-registry",
32
+ "component": "store",
33
+ "commands": [
34
+ { "argv": ["npm", "ci", "--ignore-scripts"], "cwd": "frontend-store", "timeoutMs": 120000 },
35
+ { "argv": ["node", "node_modules/nuxt/bin/nuxt.mjs", "prepare"], "cwd": "frontend-store", "timeoutMs": 120000 }
36
+ ],
37
+ "artifacts": [
38
+ { "path": "frontend-store/.nuxt/components.d.ts", "format": "nuxt-components" },
39
+ { "path": "frontend-store/.nuxt/imports.d.ts", "format": "nuxt-imports" }
40
+ ]
41
+ }]
42
+ }
43
+ }
44
+ ```
45
+
46
+ Command `cwd` is repository-relative and defaults to the observation's component root. Artifact paths are always repository-relative. Use the package manager and lockfile actually present in the project. Dependency installation is an explicit command, runs only in the copy and can require network access. Installation scripts are disabled in this example; `nuxt prepare` then runs the reviewed project configuration. On Windows, prefer a native executable or `node` plus the absolute npm CLI JavaScript path when `npm` resolves only to a `.cmd` wrapper: `shell:false` intentionally does not evaluate a command shell. Do not put tokens, passwords or environment values into argv.
47
+
48
+ Collectors do not export Spring/Docker data themselves. Declare a reviewed project script that starts the local test application if needed, exports only the intended artifacts, closes its resources and exits. A Maven/Gradle wrapper can run a project-specific integration/export task; Spring Actuator must be configured by the project for that scenario. For Docker, use a unique Compose project and an export script that tears down only its own resources in `finally`. Forge never shuts down unrelated containers or a developer's existing services.
49
+
50
+ Windows commands run in an owned Job Object. POSIX commands run in an owned process group; a program that deliberately starts another session can escape that group. Exporters must remain finite and close any detached children, servers and container resources they create. This layer does not promise containment of untrusted code.
51
+
52
+ For HTTP, export a HAR or the supported normalized request list from a test execution. Only method, sanitized path and response status enter agent context. Forge does not replay the traffic, inspect authorization headers, or infer the backend process from an unverified hostname.
53
+
54
+ ## Usage from the Codex chat
55
+
56
+ ```sh
57
+ forge repository runtime-plan --root /path/to/repo --environment-id local-test --json
58
+ forge repository runtime-observe --root /path/to/repo --environment-id local-test --execute --write --json
59
+ forge repository analyze --root /path/to/repo --write --json
60
+ forge repository runtime-context --root /path/to/repo --environment-id local-test --query checkout --json
61
+ ```
62
+
63
+ Review the proposed manifesto and execution commands in the chat. Ask Codex to run the observation when the commands, selected scenario and external effects are authorized. No per-repository hook or MCP installation is needed for the CLI/portable skill. A configured shared Forge MCP can expose the same operations for its selected project. Updating a runtime package does not automatically activate hooks or alter global Codex configuration.
64
+
65
+ Run static analysis again after changing the manifest. Runtime context requires a current saved static snapshot and an unexpired report. Runtime commands do not update static caches implicitly. Do not change the original EasyGrow checkout to test this flow: use the dedicated pilot copy or a new independent test copy.
66
+
67
+ ## Evidence and freshness
68
+
69
+ - **Nuxt declaration:** confirms a generated component/import registry for the preparation scenario; it does not prove the application rendered the component.
70
+ - **Nuxt import paths:** relative declarations can omit the source extension. They remain artifact-relative references; bare package imports and virtual aliases such as `vue` and `#app` are omitted.
71
+ - **Spring exported mappings/beans:** describes the exporter result for that invocation and profile; it does not prove every conditional request path executed.
72
+ - **Docker inspection:** describes the exported service/container state; it does not prove application health, correct credentials or production connectivity.
73
+ - **HTTP trace:** records the supplied test execution's request path/status. Origins and queries are omitted, so destination identity and parameter-dependent behavior remain limitations.
74
+ - **Normalized Forge artifact:** describes selected project-exported facts. Extra arbitrary details are excluded; this is not a general telemetry ingestion API.
75
+
76
+ The environment identifier is a human-selected label, not a fingerprint of every installed dependency, database or remote service. Reports expire and input changes invalidate them, but an external service can change sooner; collect again after changing the environment. Maps and reports remain partially complete and are aids for investigation, not a replacement for source inspection or application tests.
77
+
78
+ Reports expire after 15 minutes. The CLI/MCP plan shows a root-neutral digest of the complete eligible source copy, including dependency lockfiles and preparation scripts outside the static component globs. The static snapshot ID alone does not bind every preparation input. Runtime copy limits are 50,000 entries, 16 MiB per file and 256 MiB total; dependency and generated directories are excluded. Artifact input is limited to 2 MiB, reports to 4 MiB and command execution to five minutes total. Update the scenario when changing profiles or topology, and recollect after environment changes.
79
+
80
+ ## Publication checklist
81
+
82
+ Keep alpha.69 unpublished until all validation gates and package-content checks pass. Include this document, schema and runtime modules in the package. Preserve existing alpha.69 changes and regenerate derived artifacts through the compiler. Record the current turn's logs and independent-copy pilot results separately from earlier static-map validation. Do not initiate npm authentication or publish as part of preparation.