@cueloop/schema 0.1.0-alpha.69 → 0.1.0-alpha.70
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/package.json +2 -2
- package/src/anchor.test.ts +4 -4
- package/src/feedback.ts +2 -2
- package/src/history.ts +2 -2
- package/src/participants.test.ts +2 -2
- package/src/participants.ts +2 -6
- package/src/path-view.test.ts +4 -4
- package/src/path-view.ts +4 -4
- package/src/types.ts +5 -2
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@cueloop/schema",
|
|
3
|
-
"version": "0.1.0-alpha.
|
|
4
|
-
"description": "The
|
|
3
|
+
"version": "0.1.0-alpha.70",
|
|
4
|
+
"description": "The Thread primitive: types, markdown block model, quote-primary anchors, feedback serialization",
|
|
5
5
|
"homepage": "https://github.com/mmurakaru/cueloop#readme",
|
|
6
6
|
"bugs": {
|
|
7
7
|
"url": "https://github.com/mmurakaru/cueloop/issues"
|
package/src/anchor.test.ts
CHANGED
|
@@ -218,7 +218,7 @@ describe("anchors spanning blocks", () => {
|
|
|
218
218
|
All persistence lives in a new module,
|
|
219
219
|
so a crash can never leave a torn file on disk.
|
|
220
220
|
|
|
221
|
-
- server/storage/store.ts - the
|
|
221
|
+
- server/storage/store.ts - the ThreadStore class
|
|
222
222
|
- server/storage/schema.ts - the on-disk record shape
|
|
223
223
|
|
|
224
224
|
## Phase 2
|
|
@@ -235,7 +235,7 @@ so a crash can never leave a torn file on disk.
|
|
|
235
235
|
expect(anchor.quote).toBe(
|
|
236
236
|
[
|
|
237
237
|
"so a crash can never leave a torn file on disk.",
|
|
238
|
-
"server/storage/store.ts - the
|
|
238
|
+
"server/storage/store.ts - the ThreadStore class",
|
|
239
239
|
"server/storage/schema.ts",
|
|
240
240
|
].join(BLOCK_SEPARATOR),
|
|
241
241
|
);
|
|
@@ -282,7 +282,7 @@ so a crash can never leave a torn file on disk.
|
|
|
282
282
|
|
|
283
283
|
test("re-binds fuzzily after a light edit inside the span", () => {
|
|
284
284
|
// Arrange
|
|
285
|
-
const edited = parseBlocks(SPANNING_DOC.replace("
|
|
285
|
+
const edited = parseBlocks(SPANNING_DOC.replace("ThreadStore class", "ThreadStore type"));
|
|
286
286
|
|
|
287
287
|
// Act
|
|
288
288
|
const resolved = resolveAnchor(anchor, edited);
|
|
@@ -308,7 +308,7 @@ so a crash can never leave a torn file on disk.
|
|
|
308
308
|
// simulate the stale case directly
|
|
309
309
|
const staleAnchor = {
|
|
310
310
|
...anchor,
|
|
311
|
-
quote: `${BLOCK_SEPARATOR}server/storage/store.ts - the
|
|
311
|
+
quote: `${BLOCK_SEPARATOR}server/storage/store.ts - the ThreadStore class`,
|
|
312
312
|
};
|
|
313
313
|
|
|
314
314
|
// Act
|
package/src/feedback.ts
CHANGED
|
@@ -11,7 +11,7 @@ import {
|
|
|
11
11
|
isAgentNote,
|
|
12
12
|
type Annotation,
|
|
13
13
|
type ArtifactType,
|
|
14
|
-
type
|
|
14
|
+
type Thread,
|
|
15
15
|
type VerdictKind,
|
|
16
16
|
} from "./types";
|
|
17
17
|
import { parseBlocks, sectionOf, type Block } from "./markdown";
|
|
@@ -246,7 +246,7 @@ function annotationSectionLines(
|
|
|
246
246
|
}
|
|
247
247
|
|
|
248
248
|
export function feedbackForSession(
|
|
249
|
-
session:
|
|
249
|
+
session: Thread,
|
|
250
250
|
verdictKind: VerdictKind,
|
|
251
251
|
summary: string,
|
|
252
252
|
actionBodies?: Record<string, string>,
|
package/src/history.ts
CHANGED
|
@@ -10,7 +10,7 @@
|
|
|
10
10
|
* feedback document read what this module derives.
|
|
11
11
|
*/
|
|
12
12
|
|
|
13
|
-
import type { Annotation,
|
|
13
|
+
import type { Annotation, Thread, Verdict } from "./types";
|
|
14
14
|
|
|
15
15
|
export type EntryAuthor = "agent" | "reviewer";
|
|
16
16
|
|
|
@@ -361,7 +361,7 @@ export function removalEntries(
|
|
|
361
361
|
* Deterministic: the same record migrates to the same ids.
|
|
362
362
|
*/
|
|
363
363
|
export function historyFromLinear(
|
|
364
|
-
session: Pick<
|
|
364
|
+
session: Pick<Thread, "id" | "revisions" | "annotations" | "verdict" | "createdAt">,
|
|
365
365
|
): SessionHistory {
|
|
366
366
|
const entries: SessionEntry[] = [];
|
|
367
367
|
let parentId: string | null = null;
|
package/src/participants.test.ts
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import { describe, expect, test } from "bun:test";
|
|
2
2
|
import { registerParticipant } from "./participants";
|
|
3
|
-
import { SCHEMA_VERSION, type
|
|
3
|
+
import { SCHEMA_VERSION, type Thread } from "./types";
|
|
4
4
|
|
|
5
|
-
function emptySession():
|
|
5
|
+
function emptySession(): Thread {
|
|
6
6
|
return {
|
|
7
7
|
schemaVersion: SCHEMA_VERSION,
|
|
8
8
|
id: "ses_1",
|
package/src/participants.ts
CHANGED
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
* "author name" lands here.
|
|
6
6
|
*/
|
|
7
7
|
|
|
8
|
-
import type { Identity,
|
|
8
|
+
import type { Identity, Thread } from "./types";
|
|
9
9
|
|
|
10
10
|
/**
|
|
11
11
|
* Return the session with `author` present in the participant registry, setting
|
|
@@ -13,11 +13,7 @@ import type { Identity, ReviewSession } from "./types";
|
|
|
13
13
|
* rail renders anonymous) and never erases a name a past visit set. Immutable:
|
|
14
14
|
* the input session is not mutated.
|
|
15
15
|
*/
|
|
16
|
-
export function registerParticipant(
|
|
17
|
-
session: ReviewSession,
|
|
18
|
-
author: string,
|
|
19
|
-
name?: string,
|
|
20
|
-
): ReviewSession {
|
|
16
|
+
export function registerParticipant(session: Thread, author: string, name?: string): Thread {
|
|
21
17
|
const participants = session.participants ?? [];
|
|
22
18
|
const existing = participants.find((participant) => participant.id === author);
|
|
23
19
|
const trimmed = name?.trim();
|
package/src/path-view.test.ts
CHANGED
|
@@ -8,7 +8,7 @@ import {
|
|
|
8
8
|
type SessionHistory,
|
|
9
9
|
} from "./history";
|
|
10
10
|
import { applyPathView, viewFollowing, viewOfPath } from "./path-view";
|
|
11
|
-
import type { Annotation,
|
|
11
|
+
import type { Annotation, Thread } from "./types";
|
|
12
12
|
|
|
13
13
|
const AT = "2026-09-01T10:00:00.000Z";
|
|
14
14
|
|
|
@@ -101,7 +101,7 @@ describe("viewOfPath", () => {
|
|
|
101
101
|
describe("applyPathView", () => {
|
|
102
102
|
test("writes the view into the record and removes the fields the view leaves empty", () => {
|
|
103
103
|
// Arrange
|
|
104
|
-
const session:
|
|
104
|
+
const session: Thread = {
|
|
105
105
|
schemaVersion: "1",
|
|
106
106
|
id: "ses_1",
|
|
107
107
|
workspace: { repoRoot: "/repo", branch: "main" },
|
|
@@ -139,7 +139,7 @@ describe("viewFollowing", () => {
|
|
|
139
139
|
history = navigateTo(history, history.entries[1]!.id);
|
|
140
140
|
history = createBranch(history, "alt");
|
|
141
141
|
history = appendEntry(history, { type: "comment", annotationId: "b1", createdAt: AT }).history;
|
|
142
|
-
const session:
|
|
142
|
+
const session: Thread = {
|
|
143
143
|
schemaVersion: "1",
|
|
144
144
|
id: "ses_1",
|
|
145
145
|
workspace: { repoRoot: "/repo", branch: "main" },
|
|
@@ -177,7 +177,7 @@ describe("viewFollowing", () => {
|
|
|
177
177
|
verdict: null,
|
|
178
178
|
createdAt: AT,
|
|
179
179
|
});
|
|
180
|
-
const session:
|
|
180
|
+
const session: Thread = {
|
|
181
181
|
schemaVersion: "1",
|
|
182
182
|
id: "ses_1",
|
|
183
183
|
workspace: { repoRoot: "/repo", branch: "main" },
|
package/src/path-view.ts
CHANGED
|
@@ -7,7 +7,7 @@
|
|
|
7
7
|
*/
|
|
8
8
|
|
|
9
9
|
import { derivePath, followBranch, MAIN_BRANCH, pathOf, type SessionHistory } from "./history";
|
|
10
|
-
import type { Annotation,
|
|
10
|
+
import type { Annotation, Thread } from "./types";
|
|
11
11
|
|
|
12
12
|
export interface PathView {
|
|
13
13
|
/** The last agent revision on the path: what the artifact shows. */
|
|
@@ -51,7 +51,7 @@ export function viewOfPath(history: SessionHistory, known: Annotation[]): PathVi
|
|
|
51
51
|
}
|
|
52
52
|
|
|
53
53
|
/** Write a path view back into a record, in place; absent fields are removed. */
|
|
54
|
-
export function applyPathView(session:
|
|
54
|
+
export function applyPathView(session: Thread, view: PathView): void {
|
|
55
55
|
session.artifact = { ...session.artifact, content: view.content };
|
|
56
56
|
session.annotations = view.annotations;
|
|
57
57
|
if (view.workingCopy === undefined) delete session.workingCopy;
|
|
@@ -66,12 +66,12 @@ export function applyPathView(session: ReviewSession, view: PathView): void {
|
|
|
66
66
|
* owner's. A followed branch that no longer exists falls back to main. A record
|
|
67
67
|
* without a history travels as it is.
|
|
68
68
|
*/
|
|
69
|
-
export function viewFollowing(session:
|
|
69
|
+
export function viewFollowing(session: Thread, branch?: string): Thread {
|
|
70
70
|
const asked = branch ?? session.shareBranch ?? MAIN_BRANCH;
|
|
71
71
|
// a branch that no longer exists falls back to main, matching the daemon
|
|
72
72
|
const followed =
|
|
73
73
|
session.history && session.history.tips[asked] === undefined ? MAIN_BRANCH : asked;
|
|
74
|
-
const shared:
|
|
74
|
+
const shared: Thread = { ...session, shareBranch: followed };
|
|
75
75
|
|
|
76
76
|
if (!session.history) return shared;
|
|
77
77
|
const history = followBranch(session.history, followed);
|
package/src/types.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* The
|
|
2
|
+
* The Thread primitive. Everything in cueloop renders, annotates, or
|
|
3
3
|
* resolves this one noun. This module is pure data shapes - no IO, no
|
|
4
4
|
* dependencies beyond the history shapes.
|
|
5
5
|
*/
|
|
@@ -230,7 +230,7 @@ export interface Identity {
|
|
|
230
230
|
handle?: string;
|
|
231
231
|
}
|
|
232
232
|
|
|
233
|
-
export interface
|
|
233
|
+
export interface Thread {
|
|
234
234
|
schemaVersion: string;
|
|
235
235
|
id: string;
|
|
236
236
|
workspace: WorkspaceKey;
|
|
@@ -284,6 +284,9 @@ export interface ReviewSession {
|
|
|
284
284
|
participants?: Identity[];
|
|
285
285
|
}
|
|
286
286
|
|
|
287
|
+
/** @deprecated use Thread */
|
|
288
|
+
export type ReviewSession = Thread;
|
|
289
|
+
|
|
287
290
|
/** comment and request_changes both map to deny in agent-native contracts. */
|
|
288
291
|
export function verdictAllows(kind: VerdictKind): boolean {
|
|
289
292
|
return kind === "approve";
|