@coldtea/pr-lens-schema 0.1.0 → 0.1.2
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/LICENSE +1 -1
- package/README.md +21 -21
- package/package.json +2 -2
package/LICENSE
CHANGED
package/README.md
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
# @coldtea/pr-lens-schema
|
|
2
2
|
|
|
3
|
-
The PR Lens contract. Extraction produces these documents, the renderer consumes them, and every other surface
|
|
3
|
+
The PR Lens contract. Extraction produces these documents, the renderer consumes them, and every other surface (CLI, GitHub Action, agent skill, hosted app) passes them around. If a document validates here, it is safe to render.
|
|
4
4
|
|
|
5
|
-
MIT ©
|
|
5
|
+
MIT © Coldtea AI.
|
|
6
6
|
|
|
7
7
|
```bash
|
|
8
8
|
pnpm add @coldtea/pr-lens-schema
|
|
@@ -19,7 +19,7 @@ const result = safeParseGraphDoc(json); // { ok: true, value } | { ok: false
|
|
|
19
19
|
|
|
20
20
|
| Document | Purpose | Parser |
|
|
21
21
|
| --- | --- | --- |
|
|
22
|
-
| `GraphDoc` | Lanes, nodes, edges, flows, stats and the drill-down tree for one pull request
|
|
22
|
+
| `GraphDoc` | Lanes, nodes, edges, flows, stats and the drill-down tree for one pull request, or for a stored baseline map | `parseGraphDoc` |
|
|
23
23
|
| `PatchDoc` | Ordered operations that move a stored graph forward as pull requests merge | `parsePatchDoc` |
|
|
24
24
|
| `Config` | What a repository commits as `.github/pr-lens.yml` | `parseConfig` |
|
|
25
25
|
| `RenderManifest` | The SVGs a render produced, and where they live | `parseRenderManifest` |
|
|
@@ -34,13 +34,13 @@ A render is one asset per view per theme, so the size of a drill-down tree and t
|
|
|
34
34
|
MAX_VIEWS * THEMES.length === MAX_RENDER_ASSETS; // 128 * 2 === 256
|
|
35
35
|
```
|
|
36
36
|
|
|
37
|
-
Each array in the view tree is capped, but its depth is not, so the total is bounded by `graphIntegrityIssues`: a document carrying more views than a manifest could describe is rejected here rather than at the renderer, which would otherwise be left holding a document it was told was fine. Import `MAX_VIEWS`, `MAX_RENDER_ASSETS` and `THEMES` rather than restating any of them
|
|
37
|
+
Each array in the view tree is capped, but its depth is not, so the total is bounded by `graphIntegrityIssues`: a document carrying more views than a manifest could describe is rejected here rather than at the renderer, which would otherwise be left holding a document it was told was fine. Import `MAX_VIEWS`, `MAX_RENDER_ASSETS` and `THEMES` rather than restating any of them: raise the budget or add a theme and the other end moves with it.
|
|
38
38
|
|
|
39
|
-
The cap is the worst case, every theme rendered, not what a particular render would emit. A single-theme render could describe twice as many views, but then whether a document is renderable would depend on how it was asked to be rendered
|
|
39
|
+
The cap is the worst case, every theme rendered, not what a particular render would emit. A single-theme render could describe twice as many views, but then whether a document is renderable would depend on how it was asked to be rendered, and **if it parses, it renders** is the promise this package exists to make.
|
|
40
40
|
|
|
41
41
|
## Two lenses
|
|
42
42
|
|
|
43
|
-
`architecture` shows blast radius against the existing system. `data-flow` animates an ordered pipeline. There is deliberately no security lens and no findings field: PR Lens is the comprehension layer, and a document that carries findings is rejected rather than quietly stripped. The `Lens` enum is additive
|
|
43
|
+
`architecture` shows blast radius against the existing system. `data-flow` animates an ordered pipeline. There is deliberately no security lens and no findings field: PR Lens is the comprehension layer, and a document that carries findings is rejected rather than quietly stripped. The `Lens` enum is additive: a future contract version may add lenses, so treat one you do not recognise as a view to skip, not as a failure.
|
|
44
44
|
|
|
45
45
|
## Deltas
|
|
46
46
|
|
|
@@ -48,12 +48,12 @@ Every node, edge and flow step declares how it relates to the base commit: `adde
|
|
|
48
48
|
|
|
49
49
|
## What validation covers
|
|
50
50
|
|
|
51
|
-
Parsing runs
|
|
51
|
+
Parsing runs four things in one pass, and reports every problem it finds rather than only the first:
|
|
52
52
|
|
|
53
|
-
1. **Structure
|
|
54
|
-
2. **Contract version
|
|
55
|
-
3. **Referential integrity
|
|
56
|
-
4. **That a render could describe the document
|
|
53
|
+
1. **Structure**: types, lengths, enums, no unknown keys, and file paths that can actually become a diff permalink (repository-relative, POSIX, no `..` segment).
|
|
54
|
+
2. **Contract version**: below `1.0.0` an exact `major.minor` match; from `1.0.0` on, the same major and a minor no newer than this package's.
|
|
55
|
+
3. **Referential integrity**: every node sits in a declared lane, every edge joins declared nodes, every flow step runs between declared participants, every drill-down view and layout hint names elements that exist, and a document carrying flows declares the `data-flow` lens.
|
|
56
|
+
4. **That a render could describe the document**: see below.
|
|
57
57
|
|
|
58
58
|
A document nested deeper than the stack can walk is reported as a document too deep to read, not thrown: `safeParse*` returns a result whatever it is handed.
|
|
59
59
|
|
|
@@ -69,11 +69,11 @@ import { applyPatchDoc, parseGraphDoc, parsePatchDoc } from "@coldtea/pr-lens-sc
|
|
|
69
69
|
const result = applyPatchDoc(parseGraphDoc(baseline), parsePatchDoc(patch));
|
|
70
70
|
```
|
|
71
71
|
|
|
72
|
-
- A patch names the map it targets and the commits it carries it between
|
|
72
|
+
- A patch names the map it targets and the commits it carries it between: `graphId`, `fromSha` and `toSha` are all required, they are full 40-character commit names, and they must differ. Abbreviations are fine for something a human reads but not for deciding whether two records mean the same commit, and a patch that does not move the map is a patch that can be replayed.
|
|
73
73
|
- The target is checked before anything is applied: a patch aimed at another map, or written against a commit the map has already moved past, is a `PATCH_CONFLICT` rather than a merge.
|
|
74
|
-
- A stored map is a snapshot rather than a diff: it has an id, it records the single commit it reflects in full on both `base` and `head`, and nothing in it is annotated as a change. `graphSnapshotIssues` is that rule, exported for anything that stores a map, and `applyPatchDoc` runs it on the way in and on the way out
|
|
74
|
+
- A stored map is a snapshot rather than a diff: it has an id, it records the single commit it reflects in full on both `base` and `head`, and nothing in it is annotated as a change. `graphSnapshotIssues` is that rule, exported for anything that stores a map, and `applyPatchDoc` runs it on the way in and on the way out, so a patch can neither leave an annotation behind nor launder a map that already carries one. Failures are `NOT_A_SNAPSHOT` and name the offender, down to the step of a flow.
|
|
75
75
|
- The target rules are re-checked inside `applyPatchDoc` rather than trusted from parsing, because a zod refinement does not survive into the inferred type: a `PatchDoc` a caller assembled itself is held to the same rules as one that came from `parsePatchDoc`.
|
|
76
|
-
- Operations apply in array order, and the first conflict stops the batch
|
|
76
|
+
- Operations apply in array order, and the first conflict stops the batch, because a later operation was written against the state an earlier one was supposed to produce.
|
|
77
77
|
- `add_*` refuses an id that is taken; `update_*` and `remove_*` refuse an id that is absent; `update_*` writes only the fields it names.
|
|
78
78
|
- Removing a node takes its edges and flow steps with it, and drops a flow left with fewer than two participants or no steps. Removed ids are pruned out of the drill-down tree and the layout hints, and a view whose selection loses its last element is dropped rather than widened.
|
|
79
79
|
- Removing a lane that still holds nodes is a conflict, not a cascade: move its nodes first.
|
|
@@ -105,7 +105,7 @@ map:
|
|
|
105
105
|
group: broadcast-lib
|
|
106
106
|
```
|
|
107
107
|
|
|
108
|
-
A `match` beginning with `id:` addresses one node exactly; anything else is a path glob matched against a node's file paths, so a correction survives the model renaming the node between runs. Corrections are an overlay applied over fresh inference on every run
|
|
108
|
+
A `match` beginning with `id:` addresses one node exactly; anything else is a path glob matched against a node's file paths, so a correction survives the model renaming the node between runs. Corrections are an overlay applied over fresh inference on every run. Inference never writes back into this file.
|
|
109
109
|
|
|
110
110
|
## JSON Schema
|
|
111
111
|
|
|
@@ -115,7 +115,7 @@ A `match` beginning with `id:` addresses one node exactly; anything else is a pa
|
|
|
115
115
|
{ "$ref": "node_modules/@coldtea/pr-lens-schema/json-schema/graph-doc.schema.json" }
|
|
116
116
|
```
|
|
117
117
|
|
|
118
|
-
They describe **what an author may write**: a field with a default is one you may leave out. Rules are carried across wherever JSON Schema can state them
|
|
118
|
+
They describe **what an author may write**: a field with a default is one you may leave out. Rules are carried across wherever JSON Schema can state them: the supported contract versions, the repository-relative path rule, `endLine` requiring `startLine`, an asset needing a `url` or a `path`, a `selection` view having to select something.
|
|
119
119
|
|
|
120
120
|
Exactly five rules cannot be stated in JSON Schema and stay the parser's job, each of them a comparison the shape alone cannot make:
|
|
121
121
|
|
|
@@ -125,7 +125,7 @@ Exactly five rules cannot be stated in JSON Schema and stay the parser's job, ea
|
|
|
125
125
|
4. a patch whose two commits are the same,
|
|
126
126
|
5. more views than a render manifest could describe.
|
|
127
127
|
|
|
128
|
-
The tests run a table of documents through both representations and assert the same verdict, accept and reject alike
|
|
128
|
+
The tests run a table of documents through both representations and assert the same verdict, accept and reject alike, including a case per divergence above, so they stay deliberate and cannot quietly grow a fifth.
|
|
129
129
|
|
|
130
130
|
## Goldens
|
|
131
131
|
|
|
@@ -135,16 +135,16 @@ The tests run a table of documents through both representations and assert the s
|
|
|
135
135
|
import { postmarkRefactorGraph } from "@coldtea/pr-lens-schema/examples";
|
|
136
136
|
```
|
|
137
137
|
|
|
138
|
-
They tell one story
|
|
138
|
+
They tell one story: a real refactor that moved broadcast sending from one Postmark request per recipient to batches of 500:
|
|
139
139
|
|
|
140
140
|
- **`postmark-refactor.graph.json`** is the canonical document: the pull request itself, across three lanes, exercising all four delta states, a hero edge, a seven-step data flow with returns and a repeated batch step, and a nested drill-down tree. Downstream renderer goldens are measured against it.
|
|
141
|
-
- **`broadcast-baseline.graph.json`** is the stored map of that subsystem as `main` stood before the change, and **`broadcast-baseline.patch.json`** carries it to the merged state
|
|
141
|
+
- **`broadcast-baseline.graph.json`** is the stored map of that subsystem as `main` stood before the change, and **`broadcast-baseline.patch.json`** carries it to the merged state, the transition `applyPatchDoc` performs.
|
|
142
142
|
- **`postmark-refactor.render-manifest.json`** is what rendering the pull-request document produces, **`pr-lens.config.json`** a repository's corrections, and **`minimal.graph.json`** the smallest document that validates.
|
|
143
143
|
|
|
144
144
|
## Versioning
|
|
145
145
|
|
|
146
|
-
`SCHEMA_VERSION` is the contract version, and it
|
|
146
|
+
`SCHEMA_VERSION` is the contract version, and it moves independently of this package's version. A release that changes no contract, a documentation fix or another patch, ships a new package version and leaves `SCHEMA_VERSION` where it stands, so a document written against the older string keeps parsing. While the contract is below `1.0.0`, a minor bump may break: parsers accept only their exact `major.minor`. From `1.0.0` on, minor releases only add optional fields or widen an enum, and a parser accepts any minor at or below its own.
|
|
147
147
|
|
|
148
148
|
---
|
|
149
149
|
|
|
150
|
-
Part of [PR Lens](https://prlens.dev)
|
|
150
|
+
Part of [PR Lens](https://prlens.dev). Review what actually matters.
|
package/package.json
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@coldtea/pr-lens-schema",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.2",
|
|
4
4
|
"description": "The PR Lens contract: versioned schemas for architecture / data-flow graph documents, baseline patches, config and render manifests.",
|
|
5
5
|
"license": "MIT",
|
|
6
|
-
"author": "
|
|
6
|
+
"author": "Coldtea AI",
|
|
7
7
|
"repository": {
|
|
8
8
|
"type": "git",
|
|
9
9
|
"url": "git+https://github.com/coldteadotai/pr-lens.git",
|