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.
- package/.agents/skills/forge-agent-fabric/SKILL.md +21 -1
- package/.agents/skills/forge-agent-fabric/references/repository-analysis.md +102 -0
- package/.agents/skills/forge-agent-fabric/scripts/repository.mjs +44 -0
- package/AGENTS.md +1 -1
- package/CHANGELOG.md +16 -0
- package/README.md +12 -3
- package/docs/agent-fabric.md +13 -0
- package/docs/architecture/agent-fabric/REPOSITORY_MANIFEST_PLAN.md +272 -0
- package/docs/changelog.md +32 -0
- package/docs/repository-agent-benchmark.md +179 -0
- package/docs/repository-analysis.md +139 -0
- package/docs/repository-context-quality.md +179 -0
- package/docs/repository-runtime-observation.md +82 -0
- package/package.json +14 -2
- package/schemas/forge-manifest.schema.json +385 -53
- package/src/forge/_generated/releaseManifest.json +1 -1
- package/src/forge/_generated/releaseManifest.ts +3 -3
- package/src/forge/agent-fabric/managed-run-contract.ts +1 -0
- package/src/forge/agent-fabric/managed-run-service.ts +10 -1
- package/src/forge/agent-fabric/managed-run-store.ts +20 -0
- package/src/forge/agent-fabric/managed-workspace.ts +56 -18
- package/src/forge/agent-fabric/repository-context.ts +83 -0
- package/src/forge/agent-memory/mcp.ts +38 -1
- package/src/forge/cair/index.ts +15 -3
- package/src/forge/cair/types.ts +9 -2
- package/src/forge/cli/commands.ts +19 -0
- package/src/forge/cli/main.ts +15 -0
- package/src/forge/cli/parse.ts +70 -16
- package/src/forge/cli/repository.ts +151 -0
- package/src/forge/compiler/external-manifest/registry.ts +21 -9
- package/src/forge/delta/process-identity.ts +22 -16
- package/src/forge/repository-analysis/adapters/common.ts +72 -0
- package/src/forge/repository-analysis/adapters/docker.ts +185 -0
- package/src/forge/repository-analysis/adapters/java.ts +133 -0
- package/src/forge/repository-analysis/adapters/typescript.ts +350 -0
- package/src/forge/repository-analysis/adapters/vue.ts +71 -0
- package/src/forge/repository-analysis/analyze.ts +434 -0
- package/src/forge/repository-analysis/benchmark.ts +336 -0
- package/src/forge/repository-analysis/cache-gc.ts +154 -0
- package/src/forge/repository-analysis/check-selection.ts +123 -0
- package/src/forge/repository-analysis/context-node.ts +17 -0
- package/src/forge/repository-analysis/context.ts +456 -0
- package/src/forge/repository-analysis/http-resolution.ts +135 -0
- package/src/forge/repository-analysis/identity.ts +45 -0
- package/src/forge/repository-analysis/index.ts +18 -0
- package/src/forge/repository-analysis/nuxt-resolution.ts +188 -0
- package/src/forge/repository-analysis/quality.ts +60 -0
- package/src/forge/repository-analysis/retrieval.ts +309 -0
- package/src/forge/repository-analysis/runtime-artifacts.ts +195 -0
- package/src/forge/repository-analysis/runtime-observation.ts +316 -0
- package/src/forge/repository-analysis/scanner.ts +174 -0
- package/src/forge/repository-analysis/storage.ts +193 -0
- package/src/forge/repository-analysis/test-associations.ts +59 -0
- package/src/forge/repository-analysis/types.ts +99 -0
- package/src/forge/repository-manifest/index.ts +178 -0
- package/src/forge/repository-manifest/types.ts +63 -0
- 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.
|