@dailephd/my-frontend-observer 0.8.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +397 -0
- package/LICENSE +21 -0
- package/README.md +255 -0
- package/dist/application/browserCaptureService.d.ts +11 -0
- package/dist/application/browserCaptureService.js +12 -0
- package/dist/application/browserCaptureService.js.map +1 -0
- package/dist/application/comparisonService.d.ts +56 -0
- package/dist/application/comparisonService.js +77 -0
- package/dist/application/comparisonService.js.map +1 -0
- package/dist/application/externalReferencePersistenceService.d.ts +75 -0
- package/dist/application/externalReferencePersistenceService.js +182 -0
- package/dist/application/externalReferencePersistenceService.js.map +1 -0
- package/dist/application/frontendContractEvaluationService.d.ts +49 -0
- package/dist/application/frontendContractEvaluationService.js +112 -0
- package/dist/application/frontendContractEvaluationService.js.map +1 -0
- package/dist/application/frontendContractPersistenceService.d.ts +56 -0
- package/dist/application/frontendContractPersistenceService.js +91 -0
- package/dist/application/frontendContractPersistenceService.js.map +1 -0
- package/dist/application/observationPersistence.d.ts +59 -0
- package/dist/application/observationPersistence.js +79 -0
- package/dist/application/observationPersistence.js.map +1 -0
- package/dist/application/projectCheckService.d.ts +3 -0
- package/dist/application/projectCheckService.js +169 -0
- package/dist/application/projectCheckService.js.map +1 -0
- package/dist/application/projectWorkflowService.d.ts +46 -0
- package/dist/application/projectWorkflowService.js +92 -0
- package/dist/application/projectWorkflowService.js.map +1 -0
- package/dist/application/referenceFidelityEvaluationService.d.ts +28 -0
- package/dist/application/referenceFidelityEvaluationService.js +45 -0
- package/dist/application/referenceFidelityEvaluationService.js.map +1 -0
- package/dist/artifacts/artifactReader.d.ts +19 -0
- package/dist/artifacts/artifactReader.js +36 -0
- package/dist/artifacts/artifactReader.js.map +1 -0
- package/dist/artifacts/artifactWriter.d.ts +25 -0
- package/dist/artifacts/artifactWriter.js +68 -0
- package/dist/artifacts/artifactWriter.js.map +1 -0
- package/dist/artifacts/comparisonArtifactReader.d.ts +18 -0
- package/dist/artifacts/comparisonArtifactReader.js +35 -0
- package/dist/artifacts/comparisonArtifactReader.js.map +1 -0
- package/dist/artifacts/comparisonArtifactWriter.d.ts +41 -0
- package/dist/artifacts/comparisonArtifactWriter.js +67 -0
- package/dist/artifacts/comparisonArtifactWriter.js.map +1 -0
- package/dist/artifacts/externalReferenceArtifactReader.d.ts +18 -0
- package/dist/artifacts/externalReferenceArtifactReader.js +35 -0
- package/dist/artifacts/externalReferenceArtifactReader.js.map +1 -0
- package/dist/artifacts/externalReferenceArtifactWriter.d.ts +44 -0
- package/dist/artifacts/externalReferenceArtifactWriter.js +77 -0
- package/dist/artifacts/externalReferenceArtifactWriter.js.map +1 -0
- package/dist/artifacts/frontendContractArtifactReader.d.ts +24 -0
- package/dist/artifacts/frontendContractArtifactReader.js +47 -0
- package/dist/artifacts/frontendContractArtifactReader.js.map +1 -0
- package/dist/artifacts/frontendContractArtifactWriter.d.ts +34 -0
- package/dist/artifacts/frontendContractArtifactWriter.js +70 -0
- package/dist/artifacts/frontendContractArtifactWriter.js.map +1 -0
- package/dist/artifacts/frontendContractEvaluationArtifactReader.d.ts +17 -0
- package/dist/artifacts/frontendContractEvaluationArtifactReader.js +34 -0
- package/dist/artifacts/frontendContractEvaluationArtifactReader.js.map +1 -0
- package/dist/artifacts/frontendContractEvaluationArtifactWriter.d.ts +32 -0
- package/dist/artifacts/frontendContractEvaluationArtifactWriter.js +58 -0
- package/dist/artifacts/frontendContractEvaluationArtifactWriter.js.map +1 -0
- package/dist/artifacts/types.d.ts +17 -0
- package/dist/artifacts/types.js +2 -0
- package/dist/artifacts/types.js.map +1 -0
- package/dist/browser/chromiumAdapter.d.ts +21 -0
- package/dist/browser/chromiumAdapter.js +204 -0
- package/dist/browser/chromiumAdapter.js.map +1 -0
- package/dist/browser/evidenceCapture.d.ts +62 -0
- package/dist/browser/evidenceCapture.js +500 -0
- package/dist/browser/evidenceCapture.js.map +1 -0
- package/dist/browser/scrollCapture.d.ts +32 -0
- package/dist/browser/scrollCapture.js +163 -0
- package/dist/browser/scrollCapture.js.map +1 -0
- package/dist/browser/types.d.ts +24 -0
- package/dist/browser/types.js +2 -0
- package/dist/browser/types.js.map +1 -0
- package/dist/cli.d.ts +8 -0
- package/dist/cli.js +2411 -0
- package/dist/cli.js.map +1 -0
- package/dist/domain/boundedAgentContext.d.ts +226 -0
- package/dist/domain/boundedAgentContext.js +355 -0
- package/dist/domain/boundedAgentContext.js.map +1 -0
- package/dist/domain/boundedAgentContextCorrelation.d.ts +74 -0
- package/dist/domain/boundedAgentContextCorrelation.js +441 -0
- package/dist/domain/boundedAgentContextCorrelation.js.map +1 -0
- package/dist/domain/boundedAgentContextIdentity.d.ts +26 -0
- package/dist/domain/boundedAgentContextIdentity.js +69 -0
- package/dist/domain/boundedAgentContextIdentity.js.map +1 -0
- package/dist/domain/boundedAgentContextProjection.d.ts +71 -0
- package/dist/domain/boundedAgentContextProjection.js +477 -0
- package/dist/domain/boundedAgentContextProjection.js.map +1 -0
- package/dist/domain/comparison.d.ts +220 -0
- package/dist/domain/comparison.js +350 -0
- package/dist/domain/comparison.js.map +1 -0
- package/dist/domain/comparisonEngine.d.ts +76 -0
- package/dist/domain/comparisonEngine.js +734 -0
- package/dist/domain/comparisonEngine.js.map +1 -0
- package/dist/domain/comparisonIdentity.d.ts +13 -0
- package/dist/domain/comparisonIdentity.js +46 -0
- package/dist/domain/comparisonIdentity.js.map +1 -0
- package/dist/domain/completion.d.ts +30 -0
- package/dist/domain/completion.js +22 -0
- package/dist/domain/completion.js.map +1 -0
- package/dist/domain/diagnostics.d.ts +17 -0
- package/dist/domain/diagnostics.js +77 -0
- package/dist/domain/diagnostics.js.map +1 -0
- package/dist/domain/evidence.d.ts +29 -0
- package/dist/domain/evidence.js +59 -0
- package/dist/domain/evidence.js.map +1 -0
- package/dist/domain/explicitState.d.ts +40 -0
- package/dist/domain/explicitState.js +54 -0
- package/dist/domain/explicitState.js.map +1 -0
- package/dist/domain/externalReference.d.ts +158 -0
- package/dist/domain/externalReference.js +167 -0
- package/dist/domain/externalReference.js.map +1 -0
- package/dist/domain/externalReferenceApplicability.d.ts +43 -0
- package/dist/domain/externalReferenceApplicability.js +52 -0
- package/dist/domain/externalReferenceApplicability.js.map +1 -0
- package/dist/domain/externalReferenceCompatibility.d.ts +40 -0
- package/dist/domain/externalReferenceCompatibility.js +48 -0
- package/dist/domain/externalReferenceCompatibility.js.map +1 -0
- package/dist/domain/externalReferenceFidelity.d.ts +171 -0
- package/dist/domain/externalReferenceFidelity.js +419 -0
- package/dist/domain/externalReferenceFidelity.js.map +1 -0
- package/dist/domain/externalReferenceIdentity.d.ts +38 -0
- package/dist/domain/externalReferenceIdentity.js +70 -0
- package/dist/domain/externalReferenceIdentity.js.map +1 -0
- package/dist/domain/externalReferenceImage.d.ts +35 -0
- package/dist/domain/externalReferenceImage.js +160 -0
- package/dist/domain/externalReferenceImage.js.map +1 -0
- package/dist/domain/externalReferenceRegionRelationships.d.ts +63 -0
- package/dist/domain/externalReferenceRegionRelationships.js +98 -0
- package/dist/domain/externalReferenceRegionRelationships.js.map +1 -0
- package/dist/domain/externalReferenceRegions.d.ts +65 -0
- package/dist/domain/externalReferenceRegions.js +105 -0
- package/dist/domain/externalReferenceRegions.js.map +1 -0
- package/dist/domain/externalReferenceRequirementIdentity.d.ts +12 -0
- package/dist/domain/externalReferenceRequirementIdentity.js +35 -0
- package/dist/domain/externalReferenceRequirementIdentity.js.map +1 -0
- package/dist/domain/externalReferenceRequirements.d.ts +215 -0
- package/dist/domain/externalReferenceRequirements.js +401 -0
- package/dist/domain/externalReferenceRequirements.js.map +1 -0
- package/dist/domain/externalReferenceRuntimeBinding.d.ts +146 -0
- package/dist/domain/externalReferenceRuntimeBinding.js +183 -0
- package/dist/domain/externalReferenceRuntimeBinding.js.map +1 -0
- package/dist/domain/frontendContractEvaluation.d.ts +57 -0
- package/dist/domain/frontendContractEvaluation.js +454 -0
- package/dist/domain/frontendContractEvaluation.js.map +1 -0
- package/dist/domain/frontendContractEvaluationArtifact.d.ts +65 -0
- package/dist/domain/frontendContractEvaluationArtifact.js +108 -0
- package/dist/domain/frontendContractEvaluationArtifact.js.map +1 -0
- package/dist/domain/frontendContractIdentity.d.ts +39 -0
- package/dist/domain/frontendContractIdentity.js +70 -0
- package/dist/domain/frontendContractIdentity.js.map +1 -0
- package/dist/domain/frontendContracts.d.ts +188 -0
- package/dist/domain/frontendContracts.js +260 -0
- package/dist/domain/frontendContracts.js.map +1 -0
- package/dist/domain/identity.d.ts +21 -0
- package/dist/domain/identity.js +47 -0
- package/dist/domain/identity.js.map +1 -0
- package/dist/domain/referenceCorrectionIdentity.d.ts +40 -0
- package/dist/domain/referenceCorrectionIdentity.js +77 -0
- package/dist/domain/referenceCorrectionIdentity.js.map +1 -0
- package/dist/domain/referenceCorrectionWorkflow.d.ts +160 -0
- package/dist/domain/referenceCorrectionWorkflow.js +165 -0
- package/dist/domain/referenceCorrectionWorkflow.js.map +1 -0
- package/dist/domain/referenceFidelityProjection.d.ts +65 -0
- package/dist/domain/referenceFidelityProjection.js +135 -0
- package/dist/domain/referenceFidelityProjection.js.map +1 -0
- package/dist/domain/relationships.d.ts +210 -0
- package/dist/domain/relationships.js +352 -0
- package/dist/domain/relationships.js.map +1 -0
- package/dist/domain/schema.d.ts +269 -0
- package/dist/domain/schema.js +442 -0
- package/dist/domain/schema.js.map +1 -0
- package/dist/domain/scrollEvidence.d.ts +51 -0
- package/dist/domain/scrollEvidence.js +134 -0
- package/dist/domain/scrollEvidence.js.map +1 -0
- package/dist/index.d.ts +114 -0
- package/dist/index.js +64 -0
- package/dist/index.js.map +1 -0
- package/dist/projectWorkflow/aliasCatalog.d.ts +21 -0
- package/dist/projectWorkflow/aliasCatalog.js +67 -0
- package/dist/projectWorkflow/aliasCatalog.js.map +1 -0
- package/dist/projectWorkflow/checkAcceptance.d.ts +25 -0
- package/dist/projectWorkflow/checkAcceptance.js +55 -0
- package/dist/projectWorkflow/checkAcceptance.js.map +1 -0
- package/dist/projectWorkflow/checkResult.d.ts +85 -0
- package/dist/projectWorkflow/checkResult.js +101 -0
- package/dist/projectWorkflow/checkResult.js.map +1 -0
- package/dist/projectWorkflow/projectConfig.d.ts +43 -0
- package/dist/projectWorkflow/projectConfig.js +84 -0
- package/dist/projectWorkflow/projectConfig.js.map +1 -0
- package/dist/projectWorkflow/projectDiscovery.d.ts +9 -0
- package/dist/projectWorkflow/projectDiscovery.js +20 -0
- package/dist/projectWorkflow/projectDiscovery.js.map +1 -0
- package/dist/projectWorkflow/projectPaths.d.ts +8 -0
- package/dist/projectWorkflow/projectPaths.js +23 -0
- package/dist/projectWorkflow/projectPaths.js.map +1 -0
- package/dist/request/paths.d.ts +14 -0
- package/dist/request/paths.js +33 -0
- package/dist/request/paths.js.map +1 -0
- package/dist/request/request.d.ts +111 -0
- package/dist/request/request.js +464 -0
- package/dist/request/request.js.map +1 -0
- package/dist/safety/policy.d.ts +14 -0
- package/dist/safety/policy.js +81 -0
- package/dist/safety/policy.js.map +1 -0
- package/dist/viewer/assets/index-CN_yb9Uf.css +1 -0
- package/dist/viewer/assets/index-D98S1_2d.js +9 -0
- package/dist/viewer/icons/icon-192.png +0 -0
- package/dist/viewer/icons/icon-512.png +0 -0
- package/dist/viewer/index.html +15 -0
- package/dist/viewer/manifest.webmanifest +1 -0
- package/dist/viewer/registerSW.js +1 -0
- package/dist/viewer/sw.js +1 -0
- package/dist/viewer/workbox-9c191d2f.js +1 -0
- package/dist/viewerServer/context.d.ts +48 -0
- package/dist/viewerServer/context.js +60 -0
- package/dist/viewerServer/context.js.map +1 -0
- package/dist/viewerServer/evidence/classify.d.ts +59 -0
- package/dist/viewerServer/evidence/classify.js +124 -0
- package/dist/viewerServer/evidence/classify.js.map +1 -0
- package/dist/viewerServer/evidence/comparisonView.d.ts +28 -0
- package/dist/viewerServer/evidence/comparisonView.js +43 -0
- package/dist/viewerServer/evidence/comparisonView.js.map +1 -0
- package/dist/viewerServer/evidence/contextSourceView.d.ts +25 -0
- package/dist/viewerServer/evidence/contextSourceView.js +20 -0
- package/dist/viewerServer/evidence/contextSourceView.js.map +1 -0
- package/dist/viewerServer/evidence/discovery.d.ts +31 -0
- package/dist/viewerServer/evidence/discovery.js +78 -0
- package/dist/viewerServer/evidence/discovery.js.map +1 -0
- package/dist/viewerServer/evidence/evaluationView.d.ts +32 -0
- package/dist/viewerServer/evidence/evaluationView.js +50 -0
- package/dist/viewerServer/evidence/evaluationView.js.map +1 -0
- package/dist/viewerServer/evidence/handles.d.ts +21 -0
- package/dist/viewerServer/evidence/handles.js +43 -0
- package/dist/viewerServer/evidence/handles.js.map +1 -0
- package/dist/viewerServer/evidence/index.d.ts +41 -0
- package/dist/viewerServer/evidence/index.js +82 -0
- package/dist/viewerServer/evidence/index.js.map +1 -0
- package/dist/viewerServer/evidence/limits.d.ts +27 -0
- package/dist/viewerServer/evidence/limits.js +28 -0
- package/dist/viewerServer/evidence/limits.js.map +1 -0
- package/dist/viewerServer/evidence/linkedEvidence.d.ts +43 -0
- package/dist/viewerServer/evidence/linkedEvidence.js +151 -0
- package/dist/viewerServer/evidence/linkedEvidence.js.map +1 -0
- package/dist/viewerServer/evidence/mediaResolver.d.ts +16 -0
- package/dist/viewerServer/evidence/mediaResolver.js +85 -0
- package/dist/viewerServer/evidence/mediaResolver.js.map +1 -0
- package/dist/viewerServer/evidence/observationView.d.ts +29 -0
- package/dist/viewerServer/evidence/observationView.js +46 -0
- package/dist/viewerServer/evidence/observationView.js.map +1 -0
- package/dist/viewerServer/evidence/pathSafety.d.ts +11 -0
- package/dist/viewerServer/evidence/pathSafety.js +31 -0
- package/dist/viewerServer/evidence/pathSafety.js.map +1 -0
- package/dist/viewerServer/evidence/projection.d.ts +55 -0
- package/dist/viewerServer/evidence/projection.js +152 -0
- package/dist/viewerServer/evidence/projection.js.map +1 -0
- package/dist/viewerServer/evidence/referenceView.d.ts +133 -0
- package/dist/viewerServer/evidence/referenceView.js +169 -0
- package/dist/viewerServer/evidence/referenceView.js.map +1 -0
- package/dist/viewerServer/httpServer.d.ts +27 -0
- package/dist/viewerServer/httpServer.js +381 -0
- package/dist/viewerServer/httpServer.js.map +1 -0
- package/dist/viewerServer/openBrowser.d.ts +7 -0
- package/dist/viewerServer/openBrowser.js +32 -0
- package/dist/viewerServer/openBrowser.js.map +1 -0
- package/dist/viewerServer/port.d.ts +16 -0
- package/dist/viewerServer/port.js +19 -0
- package/dist/viewerServer/port.js.map +1 -0
- package/dist/viewerServer/viewerService.d.ts +62 -0
- package/dist/viewerServer/viewerService.js +88 -0
- package/dist/viewerServer/viewerService.js.map +1 -0
- package/docs/ARCHITECTURE.md +1286 -0
- package/docs/CI_CD.md +250 -0
- package/docs/COMMANDS.md +972 -0
- package/docs/CONTRACTS.md +1856 -0
- package/docs/CURRENT_STATE.md +1049 -0
- package/docs/DEVELOPMENT.md +202 -0
- package/docs/DOCUMENTATION_PRESERVATION_POLICY.md +50 -0
- package/docs/PROJECT_DESCRIPTION.md +2221 -0
- package/docs/PROJECT_MILESTONES.md +2526 -0
- package/docs/PROJECT_OVERVIEW.md +150 -0
- package/docs/QUICKSTART.md +83 -0
- package/docs/RELEASE.md +27 -0
- package/docs/ROADMAP.md +641 -0
- package/docs/SECURITY.md +218 -0
- package/docs/WORKFLOWS.md +642 -0
- package/docs/plans/v0.8-implementation-plan.md +655 -0
- package/docs/plans/v0.8.1-cli-usability-patch-plan.md +505 -0
- package/docs/reports/v0.7-bounded-fidelity-context-prompt7.md +243 -0
- package/docs/reports/v0.7-implementation-completeness-documentation-reconciliation.md +497 -0
- package/docs/reports/v0.7-pre-release-readiness.md +337 -0
- package/docs/reports/v0.7-reference-binding-prompt5.md +223 -0
- package/docs/reports/v0.7-reference-compatibility-prompt4.md +234 -0
- package/docs/reports/v0.7-reference-correction-workflow-prompt8.md +222 -0
- package/docs/reports/v0.7-reference-fidelity-prompt6.md +216 -0
- package/docs/reports/v0.7-reference-foundation-prompt1.md +151 -0
- package/docs/reports/v0.7-reference-regions-prompt2.md +195 -0
- package/docs/reports/v0.7-reference-requirements-prompt3.md +217 -0
- package/docs/reports/v0.7-release-prep.md +423 -0
- package/docs/reports/v0.8-binding-fidelity-interaction-batch6.md +279 -0
- package/docs/reports/v0.8-bounded-context-correlation-batch7.md +233 -0
- package/docs/reports/v0.8-comparison-contract-inspection-batch4.md +279 -0
- package/docs/reports/v0.8-evidence-index-readers-batch2.md +247 -0
- package/docs/reports/v0.8-implementation-completeness-documentation-reconciliation.md +741 -0
- package/docs/reports/v0.8-integrated-viewer-acceptance-batch8.md +128 -0
- package/docs/reports/v0.8-observation-svg-inspection-batch3.md +223 -0
- package/docs/reports/v0.8-prerelease-readiness-cross-platform-security-code-rot.md +687 -0
- package/docs/reports/v0.8-reference-candidate-inspection-batch5.md +232 -0
- package/docs/reports/v0.8-viewer-runtime-pwa-batch1.md +278 -0
- package/docs/reports/v0.8.1-check-orchestration-prompt2.md +69 -0
- package/docs/reports/v0.8.1-implementation-completeness-documentation-reconciliation.md +114 -0
- package/docs/reports/v0.8.1-prerelease-readiness-cross-platform-security-code-rot.md +170 -0
- package/docs/reports/v0.8.1-project-workflow-foundation-prompt1.md +66 -0
- package/package.json +58 -0
package/docs/COMMANDS.md
ADDED
|
@@ -0,0 +1,972 @@
|
|
|
1
|
+
# Commands
|
|
2
|
+
|
|
3
|
+
## v0.8.1 common workflow
|
|
4
|
+
|
|
5
|
+
`init --url <loopback-url> [--viewport WIDTHxHEIGHT] [--target id=selector ... | --targets-file file] [--default-baseline alias] [--replace]` creates schema-`1.1.0` project configuration; schema `1.0.0` remains readable and forbids `acceptance`. Schema `1.1.0` may add exactly:
|
|
6
|
+
|
|
7
|
+
```json
|
|
8
|
+
{
|
|
9
|
+
"acceptance": {
|
|
10
|
+
"comparisonConfigFile": "config/comparison.json",
|
|
11
|
+
"contract": {
|
|
12
|
+
"baselineArtifact": ".frontend-observer/evidence/contracts/baseline/<id>",
|
|
13
|
+
"changeArtifact": ".frontend-observer/evidence/contracts/change/<id>"
|
|
14
|
+
},
|
|
15
|
+
"reference": {
|
|
16
|
+
"approvedArtifact": ".frontend-observer/evidence/references/approved/<id>",
|
|
17
|
+
"bindingsFile": "config/reference-bindings.json"
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
```
|
|
22
|
+
|
|
23
|
+
Every acceptance path is portable and project-relative and is realpath-checked
|
|
24
|
+
before use. Both contract paths are required together. The reference must be
|
|
25
|
+
explicitly approved; bindings are explicit and default to an empty collection.
|
|
26
|
+
`comparisonConfigFile` uses the existing `compare --config-file` format.
|
|
27
|
+
|
|
28
|
+
`capture <alias> [--replace]` creates immutable canonical evidence. `current`
|
|
29
|
+
is reserved for `check`. `check [<baseline>] [--json]` resolves the explicit
|
|
30
|
+
alias or `defaultBaseline`, captures a new immutable `current`, compares it
|
|
31
|
+
canonically, and evaluates configured contract/reference acceptance. Its exact
|
|
32
|
+
exit codes are:
|
|
33
|
+
|
|
34
|
+
```text
|
|
35
|
+
PASS 0
|
|
36
|
+
FAIL 1
|
|
37
|
+
REVIEW_REQUIRED 2
|
|
38
|
+
BLOCKED 3
|
|
39
|
+
```
|
|
40
|
+
|
|
41
|
+
Comparison alone is evidence and returns `REVIEW_REQUIRED`, even with zero
|
|
42
|
+
differences. `--json` emits exactly one bounded schema-`1.0.0` document and
|
|
43
|
+
never embeds screenshots or complete artifacts. `view [--root path]` uses
|
|
44
|
+
project evidence and aliases when root is omitted and preserves standalone
|
|
45
|
+
behavior when supplied. Advanced commands below remain supported.
|
|
46
|
+
|
|
47
|
+
## Product command surface
|
|
48
|
+
|
|
49
|
+
`node dist/cli.js observe` (or `my-frontend-observer observe` once installed
|
|
50
|
+
as a bin) captures one bounded, loopback-only browser observation and
|
|
51
|
+
persists it as a portable artifact.
|
|
52
|
+
|
|
53
|
+
```text
|
|
54
|
+
my-frontend-observer observe --url <loopback-url> [options]
|
|
55
|
+
```
|
|
56
|
+
|
|
57
|
+
Required:
|
|
58
|
+
|
|
59
|
+
- `--url <url>` — loopback target URL (`http`/`https`; `localhost`,
|
|
60
|
+
`127.x.x.x`, or `::1` only - enforced by the existing request/safety
|
|
61
|
+
contracts, not by CLI-local logic).
|
|
62
|
+
|
|
63
|
+
Options:
|
|
64
|
+
|
|
65
|
+
- `--viewport <WIDTHxHEIGHT>` — e.g. `1280x720`. Malformed syntax (missing
|
|
66
|
+
`x`, non-numeric, empty side) is rejected before any browser launches;
|
|
67
|
+
in-range bounds are enforced by the existing request validator.
|
|
68
|
+
- `--target <id=css-selector>` — an explicit CSS-shorthand observation
|
|
69
|
+
target. Repeatable; order is preserved. Parsed on the *first* `=` only, so
|
|
70
|
+
a selector containing `=` survives intact, e.g.
|
|
71
|
+
`--target action=button[data-state="active"]`. Cannot be combined with
|
|
72
|
+
`--targets-file`.
|
|
73
|
+
- `--targets-file <json-file>` — loads structured semantic observation
|
|
74
|
+
targets from a local JSON file instead of `--target`. Cannot be combined
|
|
75
|
+
with `--target`. See "Structured semantic targets" below.
|
|
76
|
+
- `--scroll-scenario-file <json-file>` — loads one bounded runtime scroll
|
|
77
|
+
scenario from a local JSON file. May be combined with either `--target` or
|
|
78
|
+
`--targets-file` (it is independent of target configuration). See "Scroll
|
|
79
|
+
scenario (`--scroll-scenario-file`)" below.
|
|
80
|
+
- `--state-file <json-file>` — loads explicit, caller-declared frontend
|
|
81
|
+
state identity (`theme`, `applicationState`, `authenticatedState`) from a
|
|
82
|
+
local JSON file. Never inferred by the observer from screenshot pixels,
|
|
83
|
+
CSS, DOM, or URLs - this is caller-declared metadata only, used solely for
|
|
84
|
+
later comparability/compatibility evaluation (see "v0.7 Prompt 4 reference
|
|
85
|
+
applicability and candidate-state compatibility" in `docs/CONTRACTS.md`).
|
|
86
|
+
Independent of every other flag.
|
|
87
|
+
- `--output <directory>` — portable, relative output location for the
|
|
88
|
+
observation artifact (same contract as the request's `outputLocation`; no
|
|
89
|
+
drive letter, no leading `/`, no `..` segments).
|
|
90
|
+
- `--timeout <ms>` — overall request timeout in milliseconds.
|
|
91
|
+
- `--help` — show `observe` usage.
|
|
92
|
+
|
|
93
|
+
Also available: `--help` / `-h` (top-level usage) and `--version` (prints the
|
|
94
|
+
actual package version).
|
|
95
|
+
|
|
96
|
+
On success the command prints exactly:
|
|
97
|
+
|
|
98
|
+
```text
|
|
99
|
+
Observation: <observation-id>
|
|
100
|
+
State: <complete|partial|warning|fatal|invalid-request>
|
|
101
|
+
Artifact: <artifact-root-path>
|
|
102
|
+
Targets: <configured-target-count>
|
|
103
|
+
Diagnostics: <diagnostic-count>
|
|
104
|
+
```
|
|
105
|
+
|
|
106
|
+
and exits `0` for a validly persisted observation - including one whose
|
|
107
|
+
`State` truthfully reports `partial` (e.g. a missing or ambiguous target)
|
|
108
|
+
- or exits nonzero for invalid CLI syntax, a request the existing validator
|
|
109
|
+
rejects, an unsafe/failed navigation with no persistable artifact, or a
|
|
110
|
+
failed artifact write. No progress output is printed during a normal
|
|
111
|
+
capture. CLI-syntax errors (e.g. a missing `--url`) print as `error:
|
|
112
|
+
<message>` followed by `observe` usage; request/capture/persistence
|
|
113
|
+
diagnostics print one per line as `[code] message`.
|
|
114
|
+
|
|
115
|
+
### Structured semantic targets (`--targets-file`)
|
|
116
|
+
|
|
117
|
+
**Current status: shipped as part of the published `my-frontend-observer@0.3.0`
|
|
118
|
+
package.** `--target` (CSS shorthand) remains fully supported alongside it.
|
|
119
|
+
|
|
120
|
+
`--targets-file <json-file>` is the public entry point to the v0.2 canonical
|
|
121
|
+
target/locator model established in `src/request/request.ts`. It supplies
|
|
122
|
+
the same `targets` collection that `--target` supplies, just in structured
|
|
123
|
+
form; both converge on the same `normalizeRequest()` validation and the same
|
|
124
|
+
downstream browser resolver - there is no separate semantic observation path.
|
|
125
|
+
|
|
126
|
+
File format (the exact, first frozen structure - the root object supports
|
|
127
|
+
only the `targets` field; any other top-level field is rejected):
|
|
128
|
+
|
|
129
|
+
```json
|
|
130
|
+
{
|
|
131
|
+
"targets": [
|
|
132
|
+
{
|
|
133
|
+
"name": "primary-navigation",
|
|
134
|
+
"locators": [
|
|
135
|
+
{ "kind": "role", "role": "navigation", "name": "Primary" },
|
|
136
|
+
{ "kind": "id", "value": "nav" }
|
|
137
|
+
]
|
|
138
|
+
},
|
|
139
|
+
{
|
|
140
|
+
"name": "workspace",
|
|
141
|
+
"locators": [
|
|
142
|
+
{ "kind": "data-attribute", "attribute": "data-region", "value": "workspace" }
|
|
143
|
+
]
|
|
144
|
+
}
|
|
145
|
+
]
|
|
146
|
+
}
|
|
147
|
+
```
|
|
148
|
+
|
|
149
|
+
Each target has a stable `name` and an ordered `locators` array (1-5
|
|
150
|
+
entries; order is the fallback order - the first locator that resolves
|
|
151
|
+
uniquely wins, an ambiguous or unevaluable locator stops immediately without
|
|
152
|
+
trying the next one). Each locator is one of the six frozen kinds:
|
|
153
|
+
|
|
154
|
+
- `{ "kind": "role", "role": "<string>", "name"?: "<string>" }`
|
|
155
|
+
- `{ "kind": "id", "value": "<string>" }`
|
|
156
|
+
- `{ "kind": "data-attribute", "attribute": "data-*", "value": "<string>" }`
|
|
157
|
+
- `{ "kind": "semantic-element", "tag": "<one of the frozen structural tags>" }`
|
|
158
|
+
- `{ "kind": "css", "selector": "<string>" }`
|
|
159
|
+
- `{ "kind": "text", "text": "<exact string>" }`
|
|
160
|
+
|
|
161
|
+
`--targets-file` itself only validates that the file is readable, is valid
|
|
162
|
+
JSON, and has an object root containing exactly a `targets` field - every
|
|
163
|
+
target/locator-internal rule (bounds, per-kind required fields, supported
|
|
164
|
+
values) is enforced by the same `normalizeRequest()` validator `--target`
|
|
165
|
+
already goes through, so both input modes produce identical diagnostics for
|
|
166
|
+
equivalent mistakes.
|
|
167
|
+
|
|
168
|
+
The path may be relative (resolved from the current working directory) or
|
|
169
|
+
absolute; it is operational input only - it never affects the observation's
|
|
170
|
+
request identity and is never written into `manifest.json`.
|
|
171
|
+
|
|
172
|
+
Example:
|
|
173
|
+
|
|
174
|
+
```powershell
|
|
175
|
+
my-frontend-observer observe `
|
|
176
|
+
--url http://localhost:3000/ `
|
|
177
|
+
--viewport 1280x720 `
|
|
178
|
+
--targets-file .\targets.json `
|
|
179
|
+
--output observations
|
|
180
|
+
```
|
|
181
|
+
|
|
182
|
+
### Scroll scenario (`--scroll-scenario-file`)
|
|
183
|
+
|
|
184
|
+
**Current status: shipped as part of the published `my-frontend-observer@0.3.0`
|
|
185
|
+
package.** Observation schema is `1.2.0`.
|
|
186
|
+
|
|
187
|
+
`--scroll-scenario-file <json-file>` is the public entry point to the v0.3
|
|
188
|
+
runtime scroll-scenario contract established in `src/request/request.ts`
|
|
189
|
+
(`ScrollScenario`/`ScrollAction`) and executed in `src/browser/`. It supplies
|
|
190
|
+
exactly the value of the normalized request's `scrollScenario` field - the
|
|
191
|
+
file root *is* the scenario object itself, with no wrapper field (unlike
|
|
192
|
+
`--targets-file`'s `{ "targets": [...] }` root).
|
|
193
|
+
|
|
194
|
+
A request supports **zero or one** scroll scenario. There are exactly two
|
|
195
|
+
supported action kinds:
|
|
196
|
+
|
|
197
|
+
Window scrolling:
|
|
198
|
+
|
|
199
|
+
```json
|
|
200
|
+
{
|
|
201
|
+
"action": {
|
|
202
|
+
"kind": "window-scroll-by",
|
|
203
|
+
"deltaX": 0,
|
|
204
|
+
"deltaY": 600
|
|
205
|
+
}
|
|
206
|
+
}
|
|
207
|
+
```
|
|
208
|
+
|
|
209
|
+
Target scrolling (the `target` value must be the stable `name` of one of the
|
|
210
|
+
observation's own configured targets - never a CSS selector, DOM id, or
|
|
211
|
+
source symbol):
|
|
212
|
+
|
|
213
|
+
```json
|
|
214
|
+
{
|
|
215
|
+
"action": {
|
|
216
|
+
"kind": "target-scroll-by",
|
|
217
|
+
"target": "tool-workspace",
|
|
218
|
+
"deltaX": 0,
|
|
219
|
+
"deltaY": 400
|
|
220
|
+
}
|
|
221
|
+
}
|
|
222
|
+
```
|
|
223
|
+
|
|
224
|
+
`deltaX`/`deltaY` are signed integers bounded to `[-20000, 20000]`; at least
|
|
225
|
+
one must be non-zero (both zero is rejected). Every scroll/action rule -
|
|
226
|
+
supported action kind, required fields, delta types/bounds, the both-zero
|
|
227
|
+
rule, and the stable-target-name reference for `target-scroll-by` - is
|
|
228
|
+
enforced by the same `normalizeRequest()` validator used everywhere else, not
|
|
229
|
+
duplicated in CLI code; `--scroll-scenario-file` itself only validates that
|
|
230
|
+
the file is readable, is valid JSON, and has a non-array object root.
|
|
231
|
+
|
|
232
|
+
The observer performs the requested scroll immediately (no smooth-scroll
|
|
233
|
+
animation), waits exactly two `requestAnimationFrame` cycles, and captures a
|
|
234
|
+
final runtime snapshot - the same final state that the observation's ordinary
|
|
235
|
+
`pageEvidence`, `targetEvidence`, and `screenshot.png` describe. The actual
|
|
236
|
+
resulting scroll position is browser-authoritative and may be clamped by
|
|
237
|
+
document/element boundaries; a scenario that produces no movement (already at
|
|
238
|
+
a boundary, or a non-scrollable target) is still a valid, successfully
|
|
239
|
+
persisted observation, never a fabricated failure.
|
|
240
|
+
|
|
241
|
+
Usable with either target input mode:
|
|
242
|
+
|
|
243
|
+
```powershell
|
|
244
|
+
my-frontend-observer observe `
|
|
245
|
+
--url http://localhost:3000/ `
|
|
246
|
+
--target workspace=.workspace `
|
|
247
|
+
--scroll-scenario-file .\scroll.json `
|
|
248
|
+
--output observations
|
|
249
|
+
```
|
|
250
|
+
|
|
251
|
+
```powershell
|
|
252
|
+
my-frontend-observer observe `
|
|
253
|
+
--url http://localhost:3000/ `
|
|
254
|
+
--targets-file .\targets.json `
|
|
255
|
+
--scroll-scenario-file .\scroll.json `
|
|
256
|
+
--output observations
|
|
257
|
+
```
|
|
258
|
+
|
|
259
|
+
`--target` and `--targets-file` remain mutually exclusive with each other,
|
|
260
|
+
exactly as before; `--scroll-scenario-file` is independent of both and is
|
|
261
|
+
never itself a third mutually-exclusive target mode. `window-scroll-by`
|
|
262
|
+
requires no configured target at all.
|
|
263
|
+
|
|
264
|
+
The path may be relative (resolved from the current working directory) or
|
|
265
|
+
absolute; it is operational input only - like `--targets-file`'s path, it
|
|
266
|
+
never affects the observation's request identity and is never written into
|
|
267
|
+
`manifest.json`. Two different scenario files with identical content produce
|
|
268
|
+
the same `requestId`; only the requested scenario *configuration*
|
|
269
|
+
participates in identity, never the runtime outcome (actual scroll
|
|
270
|
+
distance, clamping, or scroll-owner result).
|
|
271
|
+
|
|
272
|
+
If a `target-scroll-by` scenario's configured action target cannot be
|
|
273
|
+
uniquely resolved at runtime (missing, ambiguous, or otherwise unavailable),
|
|
274
|
+
the scroll is not performed, no movement is fabricated, and the observation
|
|
275
|
+
persists honestly - typically as `partial` - carrying the same
|
|
276
|
+
`target-missing`/`target-ambiguous`/`browser-evidence-unavailable` diagnostic
|
|
277
|
+
that any other unresolved configured target would produce.
|
|
278
|
+
|
|
279
|
+
## `compare`
|
|
280
|
+
|
|
281
|
+
**Current status: shipped as part of the published `my-frontend-observer@0.4.0`
|
|
282
|
+
package.** Comparison schema is `1.0.0`, independent of and never reused for
|
|
283
|
+
the observation schema (`1.2.0`).
|
|
284
|
+
|
|
285
|
+
`my-frontend-observer compare` (or `node dist/cli.js compare` from a source
|
|
286
|
+
checkout) reads two already-persisted observation artifacts and derives
|
|
287
|
+
before/after evidence purely from their existing content:
|
|
288
|
+
|
|
289
|
+
```text
|
|
290
|
+
my-frontend-observer compare --before <observation-artifact-root> --after <observation-artifact-root> --output <directory> [options]
|
|
291
|
+
```
|
|
292
|
+
|
|
293
|
+
Required:
|
|
294
|
+
|
|
295
|
+
- `--before <path>` — root directory of the "before" persisted observation
|
|
296
|
+
artifact (the directory containing its `manifest.json`, as produced by
|
|
297
|
+
`observe`).
|
|
298
|
+
- `--after <path>` — root directory of the "after" persisted observation
|
|
299
|
+
artifact.
|
|
300
|
+
- `--output <directory>` — portable, relative output location for the
|
|
301
|
+
comparison artifact (same contract as `observe --output`).
|
|
302
|
+
|
|
303
|
+
Options:
|
|
304
|
+
|
|
305
|
+
- `--config-file <json-file>` — loads a comparison configuration directly
|
|
306
|
+
(no wrapper field): `{ "geometryTolerancePx": <0-10>,
|
|
307
|
+
"expectedDependencies": [...] }`. Without it, `geometryTolerancePx`
|
|
308
|
+
defaults to `0.5` CSS px with no declared dependencies. As with
|
|
309
|
+
`--targets-file`/`--scroll-scenario-file`, `--config-file` only validates
|
|
310
|
+
file readability, JSON validity, and a non-array object root; every
|
|
311
|
+
semantic rule (tolerance bounds, dependency property/direction
|
|
312
|
+
vocabulary, dependency source marker) is enforced by the same domain
|
|
313
|
+
validator the comparison engine itself uses.
|
|
314
|
+
- `--help` — show `compare` usage.
|
|
315
|
+
|
|
316
|
+
**Comparison never launches a browser.** It reads two manifests through the
|
|
317
|
+
existing observation-artifact reader, runs the pure comparison engine, and
|
|
318
|
+
persists a portable `manifest.json` — no navigation, no target
|
|
319
|
+
re-resolution, no Chromium process.
|
|
320
|
+
|
|
321
|
+
On success the command prints exactly:
|
|
322
|
+
|
|
323
|
+
```text
|
|
324
|
+
Comparison: <comparison-id>
|
|
325
|
+
State: <comparable|comparable-with-warnings|incomparable>
|
|
326
|
+
Artifact: <comparison-artifact-root>
|
|
327
|
+
Differences: <count>
|
|
328
|
+
Relationship changes: <count>
|
|
329
|
+
Diagnostics: <count>
|
|
330
|
+
```
|
|
331
|
+
|
|
332
|
+
and exits `0` — **including when `State` is `incomparable`**: comparison
|
|
333
|
+
determining that two observations should not be treated as equivalent
|
|
334
|
+
frontend states is itself a successful outcome, not a failure. The command
|
|
335
|
+
exits nonzero only for invalid CLI syntax, an unreadable/malformed/
|
|
336
|
+
structurally-invalid source artifact, invalid comparison configuration, or
|
|
337
|
+
a failed artifact write.
|
|
338
|
+
|
|
339
|
+
### Comparability
|
|
340
|
+
|
|
341
|
+
Before any rendered difference is calculated, the engine evaluates whether
|
|
342
|
+
the two observations are comparable at all:
|
|
343
|
+
|
|
344
|
+
- **Hard incompatibilities** (force `incomparable`): different logical page
|
|
345
|
+
URL, different viewport, different browser engine, or a mismatched scroll
|
|
346
|
+
scenario configuration (no scenario vs. a scenario, or two different
|
|
347
|
+
scenario configurations).
|
|
348
|
+
- **Warnings** (still `comparable-with-warnings`, comparison proceeds):
|
|
349
|
+
different producer package version, different browser version, or a
|
|
350
|
+
changed/added/removed configured target.
|
|
351
|
+
- **Unassessed dimensions** the observer does not yet model (theme,
|
|
352
|
+
authenticated state, application state) are always recorded, never
|
|
353
|
+
silently claimed identical.
|
|
354
|
+
|
|
355
|
+
An `incomparable` result still persists a structurally valid
|
|
356
|
+
`ComparisonArtifact`: the comparability reasons are recorded, and ordinary
|
|
357
|
+
rendered differences/relationship changes stay empty rather than fabricated.
|
|
358
|
+
|
|
359
|
+
### Difference and relationship evidence
|
|
360
|
+
|
|
361
|
+
For a `comparable`/`comparable-with-warnings` result, the manifest's
|
|
362
|
+
`differences` and `relationshipChanges` arrays carry structured before/
|
|
363
|
+
after evidence: appeared/disappeared targets (only for a stable target name
|
|
364
|
+
configured on both sides — a target added/removed from configuration is
|
|
365
|
+
recorded separately as a `configurationChanges` entry, never fabricated as
|
|
366
|
+
appeared/disappeared), moved/resized targets, visibility changes, clipping
|
|
367
|
+
changes, actual dimensional overflow changes, DOM containment changes,
|
|
368
|
+
page-size changes, scroll-owner changes, and layout-relationship
|
|
369
|
+
transitions (e.g. `does-not-overlap` → `overlaps`, or
|
|
370
|
+
`document-width-fits-viewport` → `document-width-exceeds-viewport`) reused
|
|
371
|
+
verbatim from the same canonical relationship engine `observe` output feeds
|
|
372
|
+
Batch 2's `deriveLayoutRelationships`.
|
|
373
|
+
|
|
374
|
+
### Explicit dependency evidence (non-causal)
|
|
375
|
+
|
|
376
|
+
`--config-file`'s `expectedDependencies` lets you declare an expected
|
|
377
|
+
layout relationship such as "`navigation.width` decreases →
|
|
378
|
+
`workspace.width` increases" using only the frozen `x`/`y`/`width`/`height`
|
|
379
|
+
property vocabulary and `increase`/`decrease`/`change`/`unchanged`
|
|
380
|
+
direction vocabulary. Each declaration is evaluated independently against
|
|
381
|
+
the two observations and persists exactly one outcome: `consistent`,
|
|
382
|
+
`not-observed`, `contradictory-to-declaration`, or `unavailable`. **The
|
|
383
|
+
observer never infers a dependency from co-change, and never emits a
|
|
384
|
+
causal claim, a PASS/FAIL verdict, or a change-contract decision** — v0.4
|
|
385
|
+
produces comparison evidence; whether that evidence satisfies some
|
|
386
|
+
contract is v0.5+ scope.
|
|
387
|
+
|
|
388
|
+
### Path privacy
|
|
389
|
+
|
|
390
|
+
`--before`, `--after`, `--config-file`, and `--output` are operational
|
|
391
|
+
filesystem input only. None of them affect `comparisonRequestId`, and none
|
|
392
|
+
of them are written into the persisted manifest — the manifest instead
|
|
393
|
+
retains logical source references (`observationId`, `requestId`,
|
|
394
|
+
`producer`, `observationSchemaVersion`, and the source `screenshot.path`).
|
|
395
|
+
Two semantically identical observation/config pairs read from different
|
|
396
|
+
filesystem locations produce the same `comparisonRequestId`; each execution
|
|
397
|
+
still gets a fresh `comparisonId`.
|
|
398
|
+
|
|
399
|
+
### Source observations remain immutable
|
|
400
|
+
|
|
401
|
+
Comparison is read-only with respect to its inputs: it never modifies
|
|
402
|
+
either source observation's `manifest.json` or `screenshot.png`, and it
|
|
403
|
+
never copies screenshot bytes into the comparison directory — the
|
|
404
|
+
comparison artifact directory contains `manifest.json` only.
|
|
405
|
+
|
|
406
|
+
Example:
|
|
407
|
+
|
|
408
|
+
```powershell
|
|
409
|
+
node dist/cli.js compare `
|
|
410
|
+
--before observations/<before-id> `
|
|
411
|
+
--after observations/<after-id> `
|
|
412
|
+
--output comparisons `
|
|
413
|
+
--config-file .\comparison-config.json
|
|
414
|
+
```
|
|
415
|
+
|
|
416
|
+
## `approve-baseline`
|
|
417
|
+
|
|
418
|
+
**Current status: shipped as part of the published `my-frontend-observer@0.5.0`
|
|
419
|
+
package.** Frontend contract schema is `1.0.0`, independent of the
|
|
420
|
+
observation (`1.2.0`) and comparison (`1.0.0`) schemas.
|
|
421
|
+
|
|
422
|
+
`my-frontend-observer approve-baseline` is the *only* baseline-approval
|
|
423
|
+
operation in the observer — approval is never inferred from a successful
|
|
424
|
+
comparison or evaluation, and no command automatically supersedes or selects
|
|
425
|
+
a baseline. It explicitly approves and persists one already-authored
|
|
426
|
+
`PersistentBaselineContract` against the observation it claims to approve:
|
|
427
|
+
|
|
428
|
+
```text
|
|
429
|
+
my-frontend-observer approve-baseline --observation <observation-artifact-root> --contract-file <json-file> --output <directory>
|
|
430
|
+
```
|
|
431
|
+
|
|
432
|
+
Required:
|
|
433
|
+
|
|
434
|
+
- `--observation <path>` — root directory of the persisted observation
|
|
435
|
+
artifact this baseline claims to approve (read through the existing
|
|
436
|
+
observation-artifact reader).
|
|
437
|
+
- `--contract-file <json-file>` — local JSON file containing one raw
|
|
438
|
+
`PersistentBaselineContract` (no wrapper field). As with `--config-file`,
|
|
439
|
+
only file readability/JSON-validity/non-array-object-root is checked here;
|
|
440
|
+
every structural rule (artifact kind, schema version, clause shape) is
|
|
441
|
+
enforced by the existing frozen domain validator.
|
|
442
|
+
- `--output <directory>` — portable, relative output location for the
|
|
443
|
+
baseline artifact.
|
|
444
|
+
|
|
445
|
+
Before persisting, the application layer verifies the contract's frozen
|
|
446
|
+
`sourceObservation` reference (`observationId`, `requestId`, `producer`,
|
|
447
|
+
`observationSchemaVersion`) actually matches the supplied observation
|
|
448
|
+
artifact's stable identity — approving a baseline against an unrelated
|
|
449
|
+
observation is rejected, even if both artifacts are individually valid. Any
|
|
450
|
+
`supersedesBaselineId` already authored in the contract is preserved exactly
|
|
451
|
+
as supplied; this command never discovers a prior baseline, infers
|
|
452
|
+
supersession, or deletes anything.
|
|
453
|
+
|
|
454
|
+
On success the command prints exactly:
|
|
455
|
+
|
|
456
|
+
```text
|
|
457
|
+
Baseline: <baseline-id>
|
|
458
|
+
State: approved
|
|
459
|
+
Artifact: <baseline-artifact-root>
|
|
460
|
+
Clauses: <count>
|
|
461
|
+
Supersedes: <baseline-id|none>
|
|
462
|
+
```
|
|
463
|
+
|
|
464
|
+
and exits `0`. It exits nonzero for invalid CLI syntax, an unreadable/
|
|
465
|
+
malformed/structurally-invalid contract file, a `PerChangeContract` passed
|
|
466
|
+
where a baseline is expected, a source-observation mismatch, an existing
|
|
467
|
+
artifact collision (baseline identities are never overwritten), or a failed
|
|
468
|
+
artifact write.
|
|
469
|
+
|
|
470
|
+
## `save-change-contract`
|
|
471
|
+
|
|
472
|
+
**Current status: shipped as part of the published `my-frontend-observer@0.5.0`
|
|
473
|
+
package.**
|
|
474
|
+
|
|
475
|
+
`my-frontend-observer save-change-contract` validates and persists one
|
|
476
|
+
already-authored `PerChangeContract` so it can later be evaluated — this is
|
|
477
|
+
persistence only, never approval:
|
|
478
|
+
|
|
479
|
+
```text
|
|
480
|
+
my-frontend-observer save-change-contract --contract-file <json-file> --output <directory>
|
|
481
|
+
```
|
|
482
|
+
|
|
483
|
+
Required:
|
|
484
|
+
|
|
485
|
+
- `--contract-file <json-file>` — local JSON file containing one raw
|
|
486
|
+
`PerChangeContract` (no wrapper field).
|
|
487
|
+
- `--output <directory>` — portable, relative output location for the
|
|
488
|
+
change-contract artifact.
|
|
489
|
+
|
|
490
|
+
Domain/application validation rejects a `PersistentBaselineContract` passed
|
|
491
|
+
here, malformed clauses, an unsupported authored category, an authored
|
|
492
|
+
`category: "unexpected"` (the derived-only fifth classification can never be
|
|
493
|
+
authored as a permission), and invalid tolerance/mode fields — none of this
|
|
494
|
+
is duplicated in CLI code. Any `supersedesBaselineClauseIds` already
|
|
495
|
+
authored on a clause is preserved exactly; resolving those references
|
|
496
|
+
against a particular baseline remains `evaluate-contract`'s responsibility.
|
|
497
|
+
|
|
498
|
+
On success the command prints exactly:
|
|
499
|
+
|
|
500
|
+
```text
|
|
501
|
+
Change contract: <contract-id>
|
|
502
|
+
Artifact: <contract-artifact-root>
|
|
503
|
+
Clauses: <count>
|
|
504
|
+
Supersedes baseline clauses: <count>
|
|
505
|
+
```
|
|
506
|
+
|
|
507
|
+
and exits `0`. It exits nonzero for invalid CLI syntax, an unreadable/
|
|
508
|
+
malformed/structurally-invalid contract file, a persistent baseline contract
|
|
509
|
+
passed here, an existing artifact collision, or a failed artifact write.
|
|
510
|
+
|
|
511
|
+
## `evaluate-contract`
|
|
512
|
+
|
|
513
|
+
**Current status: shipped as part of the published `my-frontend-observer@0.5.0`
|
|
514
|
+
package.** Frontend contract evaluation artifact schema is `1.0.0`, its own
|
|
515
|
+
independent family.
|
|
516
|
+
|
|
517
|
+
`my-frontend-observer evaluate-contract` executes the canonical Batch 2
|
|
518
|
+
evaluator against already-persisted evidence/contracts and persists the
|
|
519
|
+
result:
|
|
520
|
+
|
|
521
|
+
```text
|
|
522
|
+
my-frontend-observer evaluate-contract --before <observation-artifact-root> --after <observation-artifact-root> --comparison <comparison-artifact-root> --baseline <baseline-contract-artifact-root> --change <per-change-contract-artifact-root> --output <directory> [--enforce]
|
|
523
|
+
```
|
|
524
|
+
|
|
525
|
+
Required:
|
|
526
|
+
|
|
527
|
+
- `--before <path>` / `--after <path>` — root directories of the persisted
|
|
528
|
+
before/after observation artifacts.
|
|
529
|
+
- `--comparison <path>` — root directory of the already-persisted comparison
|
|
530
|
+
artifact for that before/after pair.
|
|
531
|
+
- `--baseline <path>` — root directory of the already-approved baseline
|
|
532
|
+
contract artifact.
|
|
533
|
+
- `--change <path>` — root directory of the already-persisted per-change
|
|
534
|
+
contract artifact.
|
|
535
|
+
- `--output <directory>` — portable, relative output location for the
|
|
536
|
+
evaluation artifact.
|
|
537
|
+
|
|
538
|
+
Options:
|
|
539
|
+
|
|
540
|
+
- `--enforce` — makes a `FAIL` verdict produce a nonzero process exit
|
|
541
|
+
status. A `FAIL` evaluation is always persisted and printed identically
|
|
542
|
+
with or without this flag; `--enforce` changes only the process exit code
|
|
543
|
+
— never evaluation identity, contents, or persistence.
|
|
544
|
+
|
|
545
|
+
**`evaluate-contract` never launches a browser, never re-resolves targets,
|
|
546
|
+
and never recomputes comparison or relationship evidence** — it reads the
|
|
547
|
+
already-persisted before/after observations and comparison exactly as given
|
|
548
|
+
(through the existing observation-artifact reader and a new comparison
|
|
549
|
+
reader) and calls the canonical `evaluateFrontendContract` exactly once.
|
|
550
|
+
|
|
551
|
+
A `FAIL` verdict (a found regression or unsatisfied contract clause) is a
|
|
552
|
+
successful, persisted evaluation outcome — not an execution error. On
|
|
553
|
+
success (evaluation constructed and persisted, verdict `PASS`, or verdict
|
|
554
|
+
`FAIL` without `--enforce`), the command prints exactly:
|
|
555
|
+
|
|
556
|
+
```text
|
|
557
|
+
Evaluation: <evaluation-id>
|
|
558
|
+
Verdict: <PASS|FAIL>
|
|
559
|
+
Artifact: <evaluation-artifact-root>
|
|
560
|
+
Clauses: <total-clause-result-count>
|
|
561
|
+
Unexpected: <unexpected-change-count>
|
|
562
|
+
Enforced: <yes|no>
|
|
563
|
+
```
|
|
564
|
+
|
|
565
|
+
and exits `0`; with `--enforce` and verdict `FAIL`, it prints the same
|
|
566
|
+
result and exits nonzero. It exits nonzero and persists nothing for invalid
|
|
567
|
+
CLI syntax or an unreadable/malformed/incoherent source artifact (evaluation
|
|
568
|
+
could not even be constructed) — distinct from a legitimate persisted `FAIL`.
|
|
569
|
+
|
|
570
|
+
The evaluation artifact directory contains `manifest.json` only — no
|
|
571
|
+
screenshot is copied. Operational `--before`/`--after`/`--comparison`/
|
|
572
|
+
`--baseline`/`--change`/`--output` paths never enter the persisted
|
|
573
|
+
`evaluationRequestId` or any other semantic field; two semantically
|
|
574
|
+
identical evaluations invoked from different filesystem locations share the
|
|
575
|
+
same `evaluationRequestId` even though each execution gets a fresh
|
|
576
|
+
`evaluationId`.
|
|
577
|
+
|
|
578
|
+
## `evaluate-reference-fidelity`
|
|
579
|
+
|
|
580
|
+
**Current status: shipped as part of the published `my-frontend-observer@0.7.0`
|
|
581
|
+
package.** No new artifact
|
|
582
|
+
family or schema version — this command persists nothing.
|
|
583
|
+
|
|
584
|
+
`my-frontend-observer evaluate-reference-fidelity` evaluates whether an
|
|
585
|
+
already-persisted candidate observation satisfies an external reference's
|
|
586
|
+
selected design requirements, gated by reference adequacy (v0.7 Prompt 3),
|
|
587
|
+
reference/candidate compatibility (v0.7 Prompt 4), and explicit
|
|
588
|
+
region-to-target bindings (v0.7 Prompt 5):
|
|
589
|
+
|
|
590
|
+
```text
|
|
591
|
+
my-frontend-observer evaluate-reference-fidelity --reference <external-reference-artifact-root> --candidate <observation-artifact-root> [--bindings-file <json-file>] [--enforce]
|
|
592
|
+
```
|
|
593
|
+
|
|
594
|
+
Required:
|
|
595
|
+
|
|
596
|
+
- `--reference <path>` — root directory of an already-imported or
|
|
597
|
+
already-approved external-reference artifact.
|
|
598
|
+
- `--candidate <path>` — root directory of the already-persisted candidate
|
|
599
|
+
observation artifact to evaluate against it.
|
|
600
|
+
|
|
601
|
+
Options:
|
|
602
|
+
|
|
603
|
+
- `--bindings-file <json-file>` — local JSON file of the form
|
|
604
|
+
`{ "bindings": [ { "referenceRegion": "...", "runtimeTarget": "..." } ] }`
|
|
605
|
+
declaring which stable observer runtime target (a configured target name)
|
|
606
|
+
explicitly corresponds to each reference region a selected requirement
|
|
607
|
+
depends on. Never inferred from geometry, matching names, or source code.
|
|
608
|
+
Optional — omitting it evaluates with no bindings at all, so every
|
|
609
|
+
requirement whose subject depends on a reference region becomes
|
|
610
|
+
`unavailable`.
|
|
611
|
+
- `--enforce` — makes a `fail` fidelity state produce a nonzero process
|
|
612
|
+
exit status. A `fail` result is always printed identically with or
|
|
613
|
+
without this flag; `--enforce` changes only the process exit code, never
|
|
614
|
+
the result's content, and has no effect on a `not-evaluated` result.
|
|
615
|
+
|
|
616
|
+
**This command never launches a browser, never re-resolves targets, and
|
|
617
|
+
never recomputes reference regions/requirements/adequacy, compatibility, or
|
|
618
|
+
bindings** — it reads the already-persisted reference and candidate exactly
|
|
619
|
+
as given and evaluates every selected requirement exactly once via
|
|
620
|
+
`evaluateReferenceCandidateFidelity`.
|
|
621
|
+
|
|
622
|
+
A `not-evaluated` result (reference adequacy inadequate, or reference/
|
|
623
|
+
candidate incompatible) and a `fail` result (a found design mismatch) are
|
|
624
|
+
both successful, structured evaluation outcomes — not execution errors. On
|
|
625
|
+
success, the command prints exactly:
|
|
626
|
+
|
|
627
|
+
```text
|
|
628
|
+
Reference: <referenceId>
|
|
629
|
+
Candidate: <candidateObservationId>
|
|
630
|
+
Adequacy: <adequate|partial|inadequate>
|
|
631
|
+
Compatibility: <comparable|comparable-with-warnings|incomparable>
|
|
632
|
+
State: <not-evaluated|pass|fail>
|
|
633
|
+
Blocked by: <reference-inadequate|incompatible>
|
|
634
|
+
Requirements: <count> (pass: <n>, fail: <n>, unavailable: <n>)
|
|
635
|
+
Enforced: <yes|no>
|
|
636
|
+
```
|
|
637
|
+
|
|
638
|
+
(`Compatibility`/`Blocked by` are printed only when computed/applicable)
|
|
639
|
+
and exits `0`, unless `--enforce` is given and the state is `fail`, in
|
|
640
|
+
which case it exits nonzero. It exits nonzero and persists nothing for
|
|
641
|
+
invalid CLI syntax, an unreadable/malformed `--reference`/`--candidate`
|
|
642
|
+
target, a malformed `--bindings-file`, or an invalid/out-of-bound binding
|
|
643
|
+
declaration.
|
|
644
|
+
|
|
645
|
+
## `import-reference`
|
|
646
|
+
|
|
647
|
+
**Current status: shipped as part of the published `my-frontend-observer@0.7.0`
|
|
648
|
+
package.** Persists a new `ExternalReferenceArtifact` in the
|
|
649
|
+
`imported` lifecycle state (external-reference schema `1.0.0`).
|
|
650
|
+
|
|
651
|
+
```text
|
|
652
|
+
my-frontend-observer import-reference <image-file> --output <directory> [options]
|
|
653
|
+
```
|
|
654
|
+
|
|
655
|
+
Required:
|
|
656
|
+
|
|
657
|
+
- `<image-file>` — local path to a PNG, JPEG, or WebP external
|
|
658
|
+
design-reference image.
|
|
659
|
+
- `--output <directory>` — portable, relative output location for the
|
|
660
|
+
external-reference artifact.
|
|
661
|
+
|
|
662
|
+
Options:
|
|
663
|
+
|
|
664
|
+
- `--label <text>` — optional human-readable label, stored as pure
|
|
665
|
+
provenance — never part of the reference's logical identity.
|
|
666
|
+
- `--supersedes <path>` — root directory of a prior external-reference
|
|
667
|
+
artifact (imported or approved) that this import explicitly supersedes.
|
|
668
|
+
The prior artifact is never modified.
|
|
669
|
+
- `--regions-file <json-file>` — local JSON file of the form
|
|
670
|
+
`{ "regions": [...] }` declaring explicit, meaningful reference-image
|
|
671
|
+
regions (id plus a `{x, y, width, height}` rectangle in reference-image
|
|
672
|
+
pixels, origin at the image's top-left corner). Optional — a reference
|
|
673
|
+
imported without this flag behaves exactly as in v0.7 Prompt 1. Region
|
|
674
|
+
content participates in the reference's logical identity; the file path
|
|
675
|
+
itself never does.
|
|
676
|
+
- `--requirements-file <json-file>` — local JSON file of the form
|
|
677
|
+
`{ "requirements": [...] }` declaring explicit, user-selected design
|
|
678
|
+
requirements over the regions above — what actually matters for later
|
|
679
|
+
candidate evaluation, never inferred merely because a region
|
|
680
|
+
property/relationship exists. Each requirement has a `category`
|
|
681
|
+
(`requested` | `expected-dependent` | `protected` | `preserved` —
|
|
682
|
+
`unexpected` is never authorable), a `subject` (a region property, a
|
|
683
|
+
region-to-region relationship, or a derived two-region measurement), and
|
|
684
|
+
— for property/measurement subjects — a `tolerance` (`exact` |
|
|
685
|
+
`absolute-reference-px` | `percent`; relationship subjects must omit
|
|
686
|
+
tolerance). Requires `--regions-file` (or an already-present region set)
|
|
687
|
+
supplying every region a requirement refers to. Optional — a reference
|
|
688
|
+
imported without this flag behaves exactly as in v0.7 Prompt 1/2.
|
|
689
|
+
Requirement content participates in the reference's logical identity.
|
|
690
|
+
- `--applicability-file <json-file>` — local JSON file declaring the
|
|
691
|
+
runtime frontend state this reference is intended to represent:
|
|
692
|
+
`{ "viewport": { "width", "height" }, "theme": "...", "applicationState":
|
|
693
|
+
"...", "authenticatedState": "authenticated"|"unauthenticated" }` (each
|
|
694
|
+
field independently optional; at least one required). `viewport` here is
|
|
695
|
+
the CSS-pixel runtime viewport the design represents — distinct from the
|
|
696
|
+
reference image's own pixel dimensions, which are never assumed equal.
|
|
697
|
+
Never inferred from the image — caller-declared metadata only, used for
|
|
698
|
+
later reference/candidate compatibility evaluation (see
|
|
699
|
+
[CONTRACTS.md](CONTRACTS.md) "v0.7 Prompt 4"). Optional — a reference
|
|
700
|
+
imported without this flag behaves exactly as in v0.7 Prompt 1/2/3.
|
|
701
|
+
Applicability content participates in the reference's logical identity.
|
|
702
|
+
|
|
703
|
+
Detects the image format from its header bytes only (never from the file
|
|
704
|
+
extension), reads its pixel dimensions from the same bounded header bytes
|
|
705
|
+
(never decoding pixel data), and persists a new external-reference artifact
|
|
706
|
+
in the `imported` lifecycle state — importing never approves it. On
|
|
707
|
+
success, prints a concise result (including the accepted region/requirement
|
|
708
|
+
counts, the resulting reference-side requirement adequacy — `adequate`,
|
|
709
|
+
`partial`, or `inadequate` — and whether applicability was declared) and
|
|
710
|
+
exits `0`. On an unreadable file, an unsupported or undetectable format,
|
|
711
|
+
invalid/out-of-bound dimensions, an over-limit file size, an unresolvable
|
|
712
|
+
`--supersedes` target, an invalid region, an invalid requirement, or invalid
|
|
713
|
+
applicability, prints structured diagnostics to stderr and exits nonzero.
|
|
714
|
+
|
|
715
|
+
## `approve-reference`
|
|
716
|
+
|
|
717
|
+
**Current status: shipped as part of the published `my-frontend-observer@0.7.0`
|
|
718
|
+
package.** Persists a new
|
|
719
|
+
`ExternalReferenceArtifact` in the `approved` lifecycle state
|
|
720
|
+
(external-reference schema `1.0.0`).
|
|
721
|
+
|
|
722
|
+
```text
|
|
723
|
+
my-frontend-observer approve-reference --reference <external-reference-artifact-root> --output <directory> [options]
|
|
724
|
+
```
|
|
725
|
+
|
|
726
|
+
Required:
|
|
727
|
+
|
|
728
|
+
- `--reference <path>` — root directory of the already-imported
|
|
729
|
+
external-reference artifact (the directory containing its
|
|
730
|
+
`manifest.json`) to approve.
|
|
731
|
+
- `--output <directory>` — portable, relative output location for the
|
|
732
|
+
newly persisted approved artifact.
|
|
733
|
+
|
|
734
|
+
Options:
|
|
735
|
+
|
|
736
|
+
- `--supersedes <path>` — root directory of a prior external-reference
|
|
737
|
+
artifact (imported or approved) that this approval explicitly
|
|
738
|
+
supersedes. The prior artifact is never modified.
|
|
739
|
+
|
|
740
|
+
This is the only explicit reference-approval act in the observer — approval
|
|
741
|
+
is never inferred from a successful import or from any later fidelity
|
|
742
|
+
evaluation. Approving persists a brand-new artifact instance (a fresh
|
|
743
|
+
`referenceId` sharing the imported artifact's `referenceRequestId`) that
|
|
744
|
+
carries a reference back to the imported artifact's image rather than a
|
|
745
|
+
second copy of its bytes; the imported artifact's own manifest is never
|
|
746
|
+
modified. Any regions, requirements, and applicability already declared on
|
|
747
|
+
the imported artifact are carried forward unchanged (not re-validated
|
|
748
|
+
against new input, not re-derived) — approval never adds, removes, or edits
|
|
749
|
+
regions, requirements, or applicability. Only a reference currently in the
|
|
750
|
+
`imported` lifecycle state can be approved. On success, prints a concise
|
|
751
|
+
result (including the carried-forward region/requirement counts,
|
|
752
|
+
reference-side requirement adequacy, and whether applicability was
|
|
753
|
+
declared) and exits `0`. On an unreadable/malformed `--reference` target, a
|
|
754
|
+
target that is not in the `imported` state, an unresolvable `--supersedes`
|
|
755
|
+
target, or a persistence failure, prints structured diagnostics to stderr
|
|
756
|
+
and exits nonzero.
|
|
757
|
+
|
|
758
|
+
## `view`
|
|
759
|
+
|
|
760
|
+
**Current status: v0.8.1 viewer behavior is released as package
|
|
761
|
+
`@dailephd/my-frontend-observer@0.8.1`.** Starts one
|
|
762
|
+
loopback-only Node viewer server and serves the same React + TypeScript +
|
|
763
|
+
Vite application to a normal browser or an installed Progressive Web App.
|
|
764
|
+
`--root` is used as a bounded, read-only evidence-discovery root: the server
|
|
765
|
+
exposes a metadata-first `GET /api/index` of recognized Observer evidence
|
|
766
|
+
beneath it, an on-demand `GET /api/artifacts/<handle>` for one selected
|
|
767
|
+
supported artifact, an on-demand `GET /api/media/<handle>/<role>` for its
|
|
768
|
+
owned/referenced media, an on-demand `GET /api/observations/<handle>/relationships`
|
|
769
|
+
(existing canonical `deriveLayoutRelationships(...)`), `GET /api/comparisons/<handle>/view`
|
|
770
|
+
and `GET /api/evaluations/<handle>/view` (exact-identity linked-evidence
|
|
771
|
+
resolution), `GET /api/references/<handle>/view` (region-relationship graph
|
|
772
|
+
and requirement adequacy, plus — new this batch — `coordinateMapping`, the
|
|
773
|
+
exact result of the existing canonical `deriveCoordinateScale(reference)`,
|
|
774
|
+
used only to gate view-lock eligibility), and
|
|
775
|
+
`GET /api/references/<handle>/candidate/<handle>/view` (page/state-level
|
|
776
|
+
compatibility plus optional matching-evaluation handles). New this batch:
|
|
777
|
+
`GET /api/references/<handle>/candidate/<handle>/bindings` validates the
|
|
778
|
+
session's explicit binding declarations against the selected reference and
|
|
779
|
+
calls the existing canonical `evaluateReferenceRuntimeBindings` exactly
|
|
780
|
+
once, and `GET /api/references/<handle>/candidate/<handle>/fidelity` is the
|
|
781
|
+
explicit on-demand trigger that calls the existing canonical
|
|
782
|
+
`evaluateReferenceCandidateFidelity` exactly once — never a second copy of a
|
|
783
|
+
linked artifact's own payload, never a recomputed
|
|
784
|
+
`compareObservations`/`evaluateFrontendContract`/
|
|
785
|
+
`deriveReferenceRegionRelationships`/`deriveReferenceRequirementAdequacy`/
|
|
786
|
+
`evaluateReferenceCandidateCompatibility` result, and both new routes are
|
|
787
|
+
plain `GET` (deterministic, ephemeral, never persisted). New this batch:
|
|
788
|
+
`GET /api/context` returns the viewer session's bounded-agent-context state
|
|
789
|
+
established at startup by an optional `--context-file` (below) — `none` (no
|
|
790
|
+
file supplied), `unsupported-version` (a recognized `artifactKind` with a
|
|
791
|
+
`schemaVersion` this viewer does not currently support — shown honestly,
|
|
792
|
+
never coerced), or the validated current context plus `sourceResolution`,
|
|
793
|
+
the exact-identity resolution of its `sources` against the current evidence
|
|
794
|
+
root (reusing/extending the Batch 4 `linkedEvidence.ts` resolver pattern) —
|
|
795
|
+
see `docs/ARCHITECTURE.md` "v0.8 Batch 2" through "v0.8 Batch 7" for the
|
|
796
|
+
exact discovery bounds, classification model, coordinate mapping, and
|
|
797
|
+
handle/media/linked-evidence-resolution contracts.
|
|
798
|
+
|
|
799
|
+
Selecting a supported `observation` record shows the Batch 3 screenshot/SVG
|
|
800
|
+
workspace. Selecting a supported `comparison` record shows the Batch 4
|
|
801
|
+
before/after side-by-side workspace. Selecting a supported
|
|
802
|
+
`contract-evaluation` record shows the Batch 4 clause-result/overall-verdict
|
|
803
|
+
workspace. Selecting a supported `external-reference-imported`/
|
|
804
|
+
`external-reference-approved` record shows the reference image with region
|
|
805
|
+
overlays in the reference image's own pixel coordinate domain, selected
|
|
806
|
+
requirements/tolerances/adequacy/applicability/lifecycle/provenance/
|
|
807
|
+
supersession, and, once a candidate observation is **explicitly** selected
|
|
808
|
+
(never auto-selected), that candidate side by side using the reused Batch
|
|
809
|
+
3/4 runtime screenshot/SVG machinery plus the real canonical compatibility
|
|
810
|
+
result. New this batch: both panes support independent, bounded (`1x`–`8x`)
|
|
811
|
+
zoom and pointer-drag pan (Fit/Reset controls included) that never rewrites
|
|
812
|
+
any evidence coordinate — only when explicit binding declarations were
|
|
813
|
+
supplied (`--bindings-file`, below) and the selected reference/candidate
|
|
814
|
+
resolve a real canonical `bound` result does selecting a reference region
|
|
815
|
+
cross-highlight its exact declared runtime target (and selecting a runtime
|
|
816
|
+
target cross-highlight every region that names it) — `ambiguous`/
|
|
817
|
+
`unavailable` results and undeclared regions/targets never cross-select,
|
|
818
|
+
even when their names happen to match. A "Lock view" control synchronizes
|
|
819
|
+
both panes' zoom/pan in source-space (via the exact `coordinateMapping`
|
|
820
|
+
scale factor) but is enabled only when a candidate is selected,
|
|
821
|
+
compatibility is not `incomparable`, and `coordinateMapping.ok` is `true` —
|
|
822
|
+
otherwise it stays disabled with an actionable reason, and any change to
|
|
823
|
+
that eligibility (including switching reference/candidate) turns it off
|
|
824
|
+
immediately. An explicit "Evaluate Fidelity" action calls the fidelity
|
|
825
|
+
endpoint on demand (never automatically) and displays the canonical
|
|
826
|
+
`not-evaluated`/`pass`/`fail` state, `blockedBy`, and every requirement
|
|
827
|
+
result's status/numeric-or-relationship fields with correct unit labels
|
|
828
|
+
(reference-image pixels vs. raw candidate CSS pixels) exactly as returned —
|
|
829
|
+
alongside, never merged into, any selected existing contract-evaluation's
|
|
830
|
+
own `overallVerdict`. A dedicated "Bounded context" mode (toggled from the
|
|
831
|
+
viewer header, alongside the normal "Evidence" mode) shows: context
|
|
832
|
+
identity/profile/adequacy/reason codes; every bounded runtime target's
|
|
833
|
+
included fields (absent fields read "not included in this bounded context",
|
|
834
|
+
never a fabricated falsy value); source references with their exact
|
|
835
|
+
resolution status and, for each exactly-resolved source, one-click
|
|
836
|
+
navigation back to its existing Batch 3/4/5 viewer surface plus a "View raw
|
|
837
|
+
structured evidence" panel reusing the existing `GET /api/artifacts/<handle>`
|
|
838
|
+
route unchanged; omissions/truncations with required loss visually
|
|
839
|
+
distinguished from optional loss; runtime/static correlation — `correlated`
|
|
840
|
+
(its one candidate, labeled "Correlated candidate", never "owner"),
|
|
841
|
+
`ambiguous` (every supplied candidate, none visually promoted), or
|
|
842
|
+
`unavailable` (zero fabricated candidates) — exactly as the artifact states,
|
|
843
|
+
or "Static correlation not included in this context" when the `correlations`
|
|
844
|
+
field itself is absent (never reported as `unavailable`); and the bounded
|
|
845
|
+
reference-fidelity projection (`mismatches`/`protectedContext`/`blockedBy`)
|
|
846
|
+
alongside — never merged into — a live, separately-triggered Batch 6
|
|
847
|
+
on-demand fidelity evaluation for the same reference/candidate, when both
|
|
848
|
+
are available. This mode never calls `projectBoundedAgentContext`,
|
|
849
|
+
`deriveRuntimeStaticCorrelations`, or `attachRuntimeStaticCorrelations` —
|
|
850
|
+
only the exact context the session was started with is ever displayed.
|
|
851
|
+
Every other evidence family still shows the bounded metadata/raw-payload
|
|
852
|
+
view established in Batch 2. Every route remains strictly read-only: no
|
|
853
|
+
artifact is ever created, modified, or interpreted beyond its existing
|
|
854
|
+
canonical reader/validator; no binding, fidelity, or bounded-context
|
|
855
|
+
artifact is ever persisted; bounded agent context remains a programmatic-
|
|
856
|
+
only Observer contract — this command adds no way to generate, save, or
|
|
857
|
+
write one; and no batch in this lineage recomputes an "overall" verdict
|
|
858
|
+
spanning contract and fidelity — they remain two independent,
|
|
859
|
+
separately-displayed evidence dimensions.
|
|
860
|
+
|
|
861
|
+
```text
|
|
862
|
+
my-frontend-observer view [--root <evidence-root>] [--bindings-file <json-file>] [--context-file <json-file>] [options]
|
|
863
|
+
```
|
|
864
|
+
|
|
865
|
+
Without `--root`, `view` discovers the nearest initialized project and uses
|
|
866
|
+
its managed evidence root plus ephemeral alias metadata. With `--root`, it
|
|
867
|
+
uses standalone evidence-root behavior and does not require a project or
|
|
868
|
+
catalog.
|
|
869
|
+
|
|
870
|
+
Options:
|
|
871
|
+
|
|
872
|
+
- `--root <path>` — local evidence-root directory the viewer session
|
|
873
|
+
represents. Validated operationally (must exist and be a directory); this
|
|
874
|
+
command never reads or interprets any Observer artifacts under it beyond
|
|
875
|
+
the bounded discovery/classification the routes above describe.
|
|
876
|
+
|
|
877
|
+
Options:
|
|
878
|
+
|
|
879
|
+
- `--bindings-file <json-file>` — local JSON file of the form
|
|
880
|
+
`{ "bindings": [ { "referenceRegion": "...", "runtimeTarget": "..." } ] }`
|
|
881
|
+
— the exact same operational wrapper format, and the exact same shared
|
|
882
|
+
parser, as `evaluate-reference-fidelity --bindings-file`. Read once at
|
|
883
|
+
startup; unreadable/invalid-JSON/wrong-wrapper-shape fails startup
|
|
884
|
+
clearly (no server is started). Reference-specific validity (region
|
|
885
|
+
existence) is checked only once a reference is actually selected in the
|
|
886
|
+
viewer, never at startup. The declarations become session-only viewer
|
|
887
|
+
input: never persisted, never written into any Observer artifact, and the
|
|
888
|
+
file's own path is never exposed to the browser. Omit to run with no
|
|
889
|
+
binding declarations — the viewer remains fully usable; reference/runtime
|
|
890
|
+
cross-selection simply stays disabled and fidelity may still be
|
|
891
|
+
explicitly evaluated with an empty declaration collection.
|
|
892
|
+
- `--context-file <json-file>` — local JSON file containing exactly one
|
|
893
|
+
`BoundedAgentContextArtifact` value directly (no wrapper object). Read
|
|
894
|
+
once at startup and validated through the existing canonical
|
|
895
|
+
`isValidBoundedAgentContextArtifact` — never a second validator. Explicit,
|
|
896
|
+
session-only viewer input: held only in server memory, never persisted,
|
|
897
|
+
never written into any Observer artifact, and the file's own path is
|
|
898
|
+
never exposed to the browser. Bounded agent context remains
|
|
899
|
+
programmatic-only as an Observer-produced contract — this command does
|
|
900
|
+
not add a way to generate, save, or write one; the viewer never rebuilds
|
|
901
|
+
it (`projectBoundedAgentContext` is never called at runtime) and never
|
|
902
|
+
derives or re-derives runtime/static correlation
|
|
903
|
+
(`deriveRuntimeStaticCorrelations`/`attachRuntimeStaticCorrelations` are
|
|
904
|
+
never called at runtime) — it only displays the exact context it was
|
|
905
|
+
given. A recognized `artifactKind` with a `schemaVersion` other than the
|
|
906
|
+
currently supported one (`1.0.0`) starts the viewer showing an honest
|
|
907
|
+
"unsupported version" context state rather than failing. An unreadable
|
|
908
|
+
file, invalid JSON, a non-object root, the wrong `artifactKind`, or a
|
|
909
|
+
structurally invalid current-schema artifact fails startup clearly (no
|
|
910
|
+
server is started). Omit to run with no bounded context supplied — the
|
|
911
|
+
viewer remains fully usable; the "Bounded context" mode reports that none
|
|
912
|
+
was supplied. May be freely combined with `--bindings-file`.
|
|
913
|
+
- `--port <n>` — TCP port to bind, in `[0, 65535]`. Defaults to `4319`
|
|
914
|
+
(chosen after checking that no fixture or test in this repository binds a
|
|
915
|
+
fixed port — see `tests/fixtures/server.ts`, which always uses `0`/
|
|
916
|
+
OS-assigned). An explicit alternate port is a different web origin than
|
|
917
|
+
the default; an installed PWA is not portable across origins. If the
|
|
918
|
+
requested port is already in use, the command fails with an actionable
|
|
919
|
+
diagnostic — it never silently falls back to a different port.
|
|
920
|
+
- `--no-open` — do not attempt to open the system default browser after the
|
|
921
|
+
server starts. Auto-open is a best-effort convenience only: its failure is
|
|
922
|
+
never fatal and never affects server startup success.
|
|
923
|
+
- `--help` — show `view` usage.
|
|
924
|
+
|
|
925
|
+
The server binds only to `127.0.0.1` (never `0.0.0.0`), serves only the
|
|
926
|
+
built viewer application assets plus the bounded, read-only `/api/*`
|
|
927
|
+
endpoints described above, and never exposes the supplied evidence root as a
|
|
928
|
+
generic static directory or arbitrary filesystem path. It accepts no write
|
|
929
|
+
methods and mutates nothing. On success,
|
|
930
|
+
prints the viewer URL and keeps running (serving the viewer) until
|
|
931
|
+
interrupted. On invalid syntax, a missing/non-directory `--root`, an
|
|
932
|
+
invalid `--port`, an invalid `--bindings-file`, an invalid `--context-file`
|
|
933
|
+
(other than a recognized-kind future `schemaVersion`, which starts
|
|
934
|
+
normally), or a port already in use, prints structured diagnostics to
|
|
935
|
+
stderr and exits nonzero without starting a server.
|
|
936
|
+
|
|
937
|
+
## Foundation commands
|
|
938
|
+
|
|
939
|
+
- `npm install` — install dependencies (includes the `playwright` runtime
|
|
940
|
+
dependency since Batch 2).
|
|
941
|
+
- `npx playwright install chromium` — install the Chromium binary once per
|
|
942
|
+
machine (see `docs/DEVELOPMENT.md`).
|
|
943
|
+
- `npm run typecheck` — run TypeScript no-emit checking.
|
|
944
|
+
- `npm run lint` — lint the repository and scripts.
|
|
945
|
+
- `npm test` — run the fast unit suite (`tests/unit/`).
|
|
946
|
+
- `npm run test:browser` — run the real-Chromium integration suite
|
|
947
|
+
(`tests/browser/`), including a real `observe` end-to-end test against the
|
|
948
|
+
deterministic local fixture.
|
|
949
|
+
- `npm run test:security` — run only the safety-relevant subset of the suite
|
|
950
|
+
(`tests/unit/policy.test.ts` plus the real-Chromium enforcement cases in
|
|
951
|
+
`tests/browser/chromiumAdapter.test.ts`: unsafe initial target, prohibited
|
|
952
|
+
redirect, prohibited subresource request, and browser cleanup around
|
|
953
|
+
safety/navigation failure) — a discoverable entry point for security
|
|
954
|
+
review tooling; it is a subset of, not a replacement for, `npm test` and
|
|
955
|
+
`npm run test:browser`.
|
|
956
|
+
- `npm run build` — clean, then compile `src/` (including `src/cli.ts`) to
|
|
957
|
+
`dist/`, then build the viewer web app (`viewer/`) with Vite into
|
|
958
|
+
`dist/viewer/` (v0.8 Batch 1). Both outputs ship inside the existing
|
|
959
|
+
`dist` package allowlist — there is no second npm package.
|
|
960
|
+
- `npm run typecheck` also type-checks the browser-side viewer project
|
|
961
|
+
(`viewer/tsconfig.json`) in addition to `tsconfig.json`, since the viewer's
|
|
962
|
+
DOM/JSX-targeting TypeScript config is intentionally separate from the
|
|
963
|
+
Node-only `src/` compilation.
|
|
964
|
+
- `npm run check:docs` — validate canonical documents and roadmap structure.
|
|
965
|
+
- `npm pack --dry-run` — inspect the public package's tarball inventory
|
|
966
|
+
before publishing. The real tarball has been installed and exercised in a
|
|
967
|
+
clean temporary consumer directory (real Chromium install, real `observe`
|
|
968
|
+
run, real artifact) on Windows, Linux, and macOS as part of v0.1
|
|
969
|
+
validation, again for v0.2's packed semantic `--targets-file` behavior,
|
|
970
|
+
and again for v0.3's packed `--scroll-scenario-file` window/target scroll
|
|
971
|
+
behavior (`scripts/ci/runPackedObservationSmoke.mjs`); this is local
|
|
972
|
+
package validation, not a release/publication step.
|