@jitsusama/agentic-harness.core 0.1.0 → 0.2.0
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/dist/bin/cli.js +7 -0
- package/dist/bin/web.d.ts +30 -0
- package/dist/bin/web.js +97 -0
- package/dist/web/audit/index.d.ts +1 -0
- package/dist/web/audit/index.js +1 -0
- package/dist/web/audit/motion.d.ts +87 -0
- package/dist/web/audit/motion.js +239 -0
- package/dist/web/design/index.d.ts +1 -0
- package/dist/web/design/index.js +1 -0
- package/dist/web/design/typography.d.ts +71 -0
- package/dist/web/design/typography.js +221 -0
- package/dist/web/hydration/capture.d.ts +37 -0
- package/dist/web/hydration/capture.js +96 -0
- package/dist/web/hydration/index.d.ts +10 -0
- package/dist/web/hydration/index.js +10 -0
- package/dist/web/hydration/judge.d.ts +56 -0
- package/dist/web/hydration/judge.js +191 -0
- package/dist/web/index.d.ts +1 -0
- package/dist/web/index.js +1 -0
- package/dist/web/perf/index.d.ts +1 -1
- package/dist/web/perf/index.js +1 -1
- package/dist/web/perf/view.js +19 -1
- package/dist/web/perf/vitals.d.ts +29 -0
- package/dist/web/perf/vitals.js +70 -0
- package/dist/web/session.d.ts +31 -2
- package/dist/web/session.js +75 -2
- package/package.json +144 -144
- package/dist/memory/db.d.ts +0 -15
- package/dist/memory/db.js +0 -25
package/dist/web/perf/view.js
CHANGED
|
@@ -47,12 +47,26 @@ export function renderVitals(vitals, measures) {
|
|
|
47
47
|
// person to interact: nothing here observes event timing, so a
|
|
48
48
|
// reader told only that four were measured has no way to know
|
|
49
49
|
// responsiveness was never among them, and assumes it passed.
|
|
50
|
+
const sampled = Math.max(...measures.map((one) => one.spread?.samples ?? 1));
|
|
51
|
+
// A rating that changed between loads is the finding, not the
|
|
52
|
+
// median beside it: the median alone reads as settled.
|
|
53
|
+
const unstable = measures.filter((one) => one.spread?.straddles);
|
|
50
54
|
const caveat = ` Interaction to next paint is not among them: it needs an ` +
|
|
51
55
|
`interaction, and this measures a load.` +
|
|
56
|
+
(sampled <= 1 ? "" : ` Each value is the median of ${sampled} loads.`) +
|
|
57
|
+
(unstable.length === 0
|
|
58
|
+
? ""
|
|
59
|
+
: ` Rated differently between loads: ${unstable
|
|
60
|
+
.map((one) => one.name)
|
|
61
|
+
.join(", ")}.`) +
|
|
52
62
|
(missing.length === 0 ? "" : ` Not observed: ${missing.join("; ")}.`);
|
|
53
63
|
const width = Math.max(...measures.map((one) => one.name.length));
|
|
54
64
|
const lines = measures.map((one) => ` ${one.name.padEnd(width)} ${MARK[one.rating].padEnd(4)} ` +
|
|
55
65
|
`${say(one.value, one.unit).padStart(9)}` +
|
|
66
|
+
`${one.spread && one.spread.samples > 1
|
|
67
|
+
? ` ${say(one.spread.low, one.unit)}-${say(one.spread.high, one.unit)}` +
|
|
68
|
+
` over ${one.spread.samples}`
|
|
69
|
+
: ""}` +
|
|
56
70
|
`${one.detail ? ` ${one.detail}` : ""}`);
|
|
57
71
|
const blame = worstShiftSources(vitals.shifts);
|
|
58
72
|
if (blame.length > 0) {
|
|
@@ -71,7 +85,11 @@ export function renderVitals(vitals, measures) {
|
|
|
71
85
|
// A partial capture cannot pass: an observer that never
|
|
72
86
|
// installed reports nothing, which reads the same as a page
|
|
73
87
|
// with nothing wrong.
|
|
74
|
-
|
|
88
|
+
// A pass that only holds on the median is not a pass: a
|
|
89
|
+
// metric that rated poor on any load is worth a look even
|
|
90
|
+
// when the middle run was fine.
|
|
91
|
+
standing: (missing.length > 0 || unstable.length > 0) &&
|
|
92
|
+
overall(measures) === "pass"
|
|
75
93
|
? "warn"
|
|
76
94
|
: overall(measures),
|
|
77
95
|
headline: failing.length === 0
|
|
@@ -128,6 +128,15 @@ export declare function worstShiftSources(shifts: readonly Shift[], limit?: numb
|
|
|
128
128
|
readonly node: string;
|
|
129
129
|
readonly moved: number;
|
|
130
130
|
}[];
|
|
131
|
+
/** How a metric varied across repeated loads. */
|
|
132
|
+
export interface Spread {
|
|
133
|
+
readonly low: number;
|
|
134
|
+
readonly high: number;
|
|
135
|
+
/** How many loads actually reported this metric. */
|
|
136
|
+
readonly samples: number;
|
|
137
|
+
/** Whether the rating differed between loads. */
|
|
138
|
+
readonly straddles: boolean;
|
|
139
|
+
}
|
|
131
140
|
/** One metric, rated. */
|
|
132
141
|
export interface Measure {
|
|
133
142
|
readonly name: string;
|
|
@@ -136,6 +145,26 @@ export interface Measure {
|
|
|
136
145
|
readonly rating: Rating;
|
|
137
146
|
/** What the value points at, when the browser said. */
|
|
138
147
|
readonly detail?: string;
|
|
148
|
+
/** Present when the value is a median over several loads. */
|
|
149
|
+
readonly spread?: Spread;
|
|
139
150
|
}
|
|
140
151
|
/** Read the vitals into rated measures. */
|
|
141
152
|
export declare function measure(vitals: Vitals): readonly Measure[];
|
|
153
|
+
/**
|
|
154
|
+
* Read several captures of the same page into rated measures,
|
|
155
|
+
* one per metric, each the median over the loads that reported
|
|
156
|
+
* it.
|
|
157
|
+
*
|
|
158
|
+
* A single headless load drifts: the same page can rate good on
|
|
159
|
+
* one run and poor on the next without anything changing. The
|
|
160
|
+
* median is the defensible middle, and the spread is reported
|
|
161
|
+
* beside it because a rating that straddles the runs is the
|
|
162
|
+
* finding, not the number.
|
|
163
|
+
*
|
|
164
|
+
* The rating is taken from the sample nearest the median rather
|
|
165
|
+
* than re-derived, so a metric keeps exactly the thresholds
|
|
166
|
+
* `measure` gave it. For an even count the worse of the two
|
|
167
|
+
* middle samples decides, which errs toward the reading a
|
|
168
|
+
* person would want to hear about.
|
|
169
|
+
*/
|
|
170
|
+
export declare function measureSamples(samples: readonly Vitals[]): readonly Measure[];
|
package/dist/web/perf/vitals.js
CHANGED
|
@@ -173,3 +173,73 @@ export function measure(vitals) {
|
|
|
173
173
|
}
|
|
174
174
|
return measures;
|
|
175
175
|
}
|
|
176
|
+
/**
|
|
177
|
+
* Read several captures of the same page into rated measures,
|
|
178
|
+
* one per metric, each the median over the loads that reported
|
|
179
|
+
* it.
|
|
180
|
+
*
|
|
181
|
+
* A single headless load drifts: the same page can rate good on
|
|
182
|
+
* one run and poor on the next without anything changing. The
|
|
183
|
+
* median is the defensible middle, and the spread is reported
|
|
184
|
+
* beside it because a rating that straddles the runs is the
|
|
185
|
+
* finding, not the number.
|
|
186
|
+
*
|
|
187
|
+
* The rating is taken from the sample nearest the median rather
|
|
188
|
+
* than re-derived, so a metric keeps exactly the thresholds
|
|
189
|
+
* `measure` gave it. For an even count the worse of the two
|
|
190
|
+
* middle samples decides, which errs toward the reading a
|
|
191
|
+
* person would want to hear about.
|
|
192
|
+
*/
|
|
193
|
+
export function measureSamples(samples) {
|
|
194
|
+
const first = samples[0];
|
|
195
|
+
if (first === undefined)
|
|
196
|
+
return [];
|
|
197
|
+
if (samples.length === 1)
|
|
198
|
+
return measure(first);
|
|
199
|
+
const order = [];
|
|
200
|
+
const byName = new Map();
|
|
201
|
+
for (const capture of samples) {
|
|
202
|
+
for (const one of measure(capture)) {
|
|
203
|
+
const group = byName.get(one.name);
|
|
204
|
+
if (group === undefined) {
|
|
205
|
+
byName.set(one.name, [one]);
|
|
206
|
+
order.push(one.name);
|
|
207
|
+
}
|
|
208
|
+
else {
|
|
209
|
+
group.push(one);
|
|
210
|
+
}
|
|
211
|
+
}
|
|
212
|
+
}
|
|
213
|
+
return order.map((name) => {
|
|
214
|
+
// Set above for every name in order; the map cannot miss.
|
|
215
|
+
const group = byName.get(name);
|
|
216
|
+
const sorted = [...group].sort((a, b) => a.value - b.value);
|
|
217
|
+
const mid = Math.floor(sorted.length / 2);
|
|
218
|
+
const upper = sorted[mid];
|
|
219
|
+
const lower = sorted[Math.max(0, mid - 1)];
|
|
220
|
+
const odd = sorted.length % 2 === 1;
|
|
221
|
+
const median = odd ? upper.value : (lower.value + upper.value) / 2;
|
|
222
|
+
const worseMiddle = SEVERITY_ORDER.indexOf(lower.rating) >=
|
|
223
|
+
SEVERITY_ORDER.indexOf(upper.rating)
|
|
224
|
+
? lower
|
|
225
|
+
: upper;
|
|
226
|
+
const nearest = odd ? upper : worseMiddle;
|
|
227
|
+
const low = sorted[0].value;
|
|
228
|
+
const high = sorted[sorted.length - 1].value;
|
|
229
|
+
return {
|
|
230
|
+
name,
|
|
231
|
+
value: median,
|
|
232
|
+
unit: nearest.unit,
|
|
233
|
+
rating: nearest.rating,
|
|
234
|
+
...(nearest.detail === undefined ? {} : { detail: nearest.detail }),
|
|
235
|
+
spread: {
|
|
236
|
+
low,
|
|
237
|
+
high,
|
|
238
|
+
samples: group.length,
|
|
239
|
+
straddles: new Set(group.map((one) => one.rating)).size > 1,
|
|
240
|
+
},
|
|
241
|
+
};
|
|
242
|
+
});
|
|
243
|
+
}
|
|
244
|
+
/** Mildest to worst, for choosing the reading to stand on. */
|
|
245
|
+
const SEVERITY_ORDER = ["good", "needs-improvement", "poor"];
|
package/dist/web/session.d.ts
CHANGED
|
@@ -18,9 +18,10 @@ import { type Animation, type BoxModel, type DelegatedListeners, type HoverRepor
|
|
|
18
18
|
import { type Divergence, type EmulationState, type NetworkRule, type ObservedEnvironment, type SavedState, type SessionStatus, type StorageSnapshot, type TabRecord, type ThrottleConditions } from "./environment/index.js";
|
|
19
19
|
import { type ChordRefusal, type Point, type PointerEventStep, type TouchStep } from "./input/index.js";
|
|
20
20
|
import { type Settled, type WaitCondition, type WaitOutcome } from "./wait/index.js";
|
|
21
|
-
import { type A11yFinding, type BehindReport, type CapturedTarget, type ConformanceBar, type ContrastLevel, type PageBox, type PairReport, type StructureNode, type VisualNode } from "./audit/index.js";
|
|
22
|
-
import { type StyleSample } from "./design/index.js";
|
|
21
|
+
import { type A11yFinding, type BehindReport, type CapturedTarget, type ConformanceBar, type ContrastLevel, type MotionCapture, type PageBox, type PairReport, type StructureNode, type VisualNode } from "./audit/index.js";
|
|
22
|
+
import { type StyleSample, type TextBlock } from "./design/index.js";
|
|
23
23
|
import { type EvalFrame, type EvalOutcome } from "./evaluate/index.js";
|
|
24
|
+
import { type HydrationCapture } from "./hydration/index.js";
|
|
24
25
|
import { type HeapComparison, type Hotspots, type LayerReport, type TraceCapture, type TraceProfile, type Vitals } from "./perf/index.js";
|
|
25
26
|
import { type IndexedNode } from "./snapshot/index.js";
|
|
26
27
|
import { type PropertyTrace, type StyleGroup } from "./styles/index.js";
|
|
@@ -810,6 +811,18 @@ export declare class BrowserSession {
|
|
|
810
811
|
* a click or a navigation without disturbing what it reports.
|
|
811
812
|
*/
|
|
812
813
|
focusHolder(): Promise<FocusHolder | undefined>;
|
|
814
|
+
/**
|
|
815
|
+
* What the page keeps doing when asked to hold still.
|
|
816
|
+
*
|
|
817
|
+
* Emulates prefers-reduced-motion: reduce, reloads so the page
|
|
818
|
+
* decides its motion under the preference rather than being
|
|
819
|
+
* caught mid-flight, reads what is still moving, then puts the
|
|
820
|
+
* emulation back exactly as it was. The reload matters: a page
|
|
821
|
+
* picks most of its motion at load, so flipping the preference
|
|
822
|
+
* on a settled page measures its reaction to a change, not its
|
|
823
|
+
* behaviour for a visitor who arrived with the preference set.
|
|
824
|
+
*/
|
|
825
|
+
motionUnderReduce(): Promise<MotionCapture>;
|
|
813
826
|
structure(): Promise<readonly StructureNode[]>;
|
|
814
827
|
/**
|
|
815
828
|
* What the layout actually did, as the browser measured it.
|
|
@@ -828,6 +841,22 @@ export declare class BrowserSession {
|
|
|
828
841
|
* criterion turns on.
|
|
829
842
|
*/
|
|
830
843
|
targets(): Promise<readonly CapturedTarget[]>;
|
|
844
|
+
/**
|
|
845
|
+
* Both renders of the current page: what the server sends and
|
|
846
|
+
* what hydration made of it.
|
|
847
|
+
*
|
|
848
|
+
* The server render is fetched from inside the page, so it
|
|
849
|
+
* travels with the session's cookies, and parsed without
|
|
850
|
+
* running a script. Judging the capture is the hydration
|
|
851
|
+
* subdomain's job; pair it with logs() so the framework's own
|
|
852
|
+
* complaints are read beside the comparison.
|
|
853
|
+
*/
|
|
854
|
+
hydration(): Promise<HydrationCapture>;
|
|
855
|
+
/**
|
|
856
|
+
* How the page's text blocks wrap, measured from real line
|
|
857
|
+
* boxes rather than estimated from fonts.
|
|
858
|
+
*/
|
|
859
|
+
typography(): Promise<readonly TextBlock[]>;
|
|
831
860
|
layout(): Promise<{
|
|
832
861
|
readonly nodes: readonly VisualNode[];
|
|
833
862
|
readonly viewport: PageBox;
|
package/dist/web/session.js
CHANGED
|
@@ -82,9 +82,10 @@ const WAIT_POLL_MS = 100;
|
|
|
82
82
|
const KNOWN_KEYS = new Set(Object.keys(_keyDefinitions));
|
|
83
83
|
import { readFile } from "node:fs/promises";
|
|
84
84
|
import { createRequire } from "node:module";
|
|
85
|
-
import { buildStructure, enabledRules, foldBehind, foldPair, parseRgb, readAxeRun, TARGET_CAPTURE, visualCaptureSource, } from "./audit/index.js";
|
|
86
|
-
import { inventorySource } from "./design/index.js";
|
|
85
|
+
import { buildStructure, enabledRules, foldBehind, foldPair, MOTION_CAPTURE, parseRgb, readAxeRun, TARGET_CAPTURE, visualCaptureSource, } from "./audit/index.js";
|
|
86
|
+
import { inventorySource, TYPOGRAPHY_CAPTURE, } from "./design/index.js";
|
|
87
87
|
import { describeThrow, evaluationSource, } from "./evaluate/index.js";
|
|
88
|
+
import { HYDRATION_CAPTURE } from "./hydration/index.js";
|
|
88
89
|
import { categoriesFor, compareHeap, foldLayers, foldProfile, foldTrace, LAYER_SETTLE_MS, nameNode, observerBootstrap, readVitalsSource, } from "./perf/index.js";
|
|
89
90
|
import { captureTiles } from "./screenshot.js";
|
|
90
91
|
import { ArtifactLedger } from "./session/artifacts.js";
|
|
@@ -1874,6 +1875,39 @@ export class BrowserSession {
|
|
|
1874
1875
|
});
|
|
1875
1876
|
return result.value;
|
|
1876
1877
|
}
|
|
1878
|
+
/**
|
|
1879
|
+
* What the page keeps doing when asked to hold still.
|
|
1880
|
+
*
|
|
1881
|
+
* Emulates prefers-reduced-motion: reduce, reloads so the page
|
|
1882
|
+
* decides its motion under the preference rather than being
|
|
1883
|
+
* caught mid-flight, reads what is still moving, then puts the
|
|
1884
|
+
* emulation back exactly as it was. The reload matters: a page
|
|
1885
|
+
* picks most of its motion at load, so flipping the preference
|
|
1886
|
+
* on a settled page measures its reaction to a change, not its
|
|
1887
|
+
* behaviour for a visitor who arrived with the preference set.
|
|
1888
|
+
*/
|
|
1889
|
+
async motionUnderReduce() {
|
|
1890
|
+
await this.ready();
|
|
1891
|
+
const before = this.emulation.asked;
|
|
1892
|
+
try {
|
|
1893
|
+
await this.emulation.change({ reducedMotion: true });
|
|
1894
|
+
await this.reload();
|
|
1895
|
+
const response = await this.cdp.send("Runtime.evaluate", {
|
|
1896
|
+
expression: MOTION_CAPTURE,
|
|
1897
|
+
returnByValue: true,
|
|
1898
|
+
});
|
|
1899
|
+
if (response.exceptionDetails) {
|
|
1900
|
+
const threw = describeThrow(response.exceptionDetails);
|
|
1901
|
+
throw new Error(`Could not read the motion: ${threw.message}`);
|
|
1902
|
+
}
|
|
1903
|
+
return response.result.value;
|
|
1904
|
+
}
|
|
1905
|
+
finally {
|
|
1906
|
+
// Wholesale, not merged: a merge cannot clear the reduce
|
|
1907
|
+
// this added when the session had no opinion before.
|
|
1908
|
+
await this.emulation.restore(before);
|
|
1909
|
+
}
|
|
1910
|
+
}
|
|
1877
1911
|
async structure() {
|
|
1878
1912
|
// Every sibling read waits out a crash recovery first, and
|
|
1879
1913
|
// this one did not. Promise.all evaluates this.cdp.send when
|
|
@@ -1937,6 +1971,45 @@ export class BrowserSession {
|
|
|
1937
1971
|
}
|
|
1938
1972
|
return response.result.value;
|
|
1939
1973
|
}
|
|
1974
|
+
/**
|
|
1975
|
+
* Both renders of the current page: what the server sends and
|
|
1976
|
+
* what hydration made of it.
|
|
1977
|
+
*
|
|
1978
|
+
* The server render is fetched from inside the page, so it
|
|
1979
|
+
* travels with the session's cookies, and parsed without
|
|
1980
|
+
* running a script. Judging the capture is the hydration
|
|
1981
|
+
* subdomain's job; pair it with logs() so the framework's own
|
|
1982
|
+
* complaints are read beside the comparison.
|
|
1983
|
+
*/
|
|
1984
|
+
async hydration() {
|
|
1985
|
+
await this.ready();
|
|
1986
|
+
const response = await this.cdp.send("Runtime.evaluate", {
|
|
1987
|
+
expression: HYDRATION_CAPTURE,
|
|
1988
|
+
awaitPromise: true,
|
|
1989
|
+
returnByValue: true,
|
|
1990
|
+
});
|
|
1991
|
+
if (response.exceptionDetails) {
|
|
1992
|
+
const threw = describeThrow(response.exceptionDetails);
|
|
1993
|
+
throw new Error(`Could not read the renders: ${threw.message}`);
|
|
1994
|
+
}
|
|
1995
|
+
return response.result.value;
|
|
1996
|
+
}
|
|
1997
|
+
/**
|
|
1998
|
+
* How the page's text blocks wrap, measured from real line
|
|
1999
|
+
* boxes rather than estimated from fonts.
|
|
2000
|
+
*/
|
|
2001
|
+
async typography() {
|
|
2002
|
+
await this.ready();
|
|
2003
|
+
const response = await this.cdp.send("Runtime.evaluate", {
|
|
2004
|
+
expression: TYPOGRAPHY_CAPTURE,
|
|
2005
|
+
returnByValue: true,
|
|
2006
|
+
});
|
|
2007
|
+
if (response.exceptionDetails) {
|
|
2008
|
+
const threw = describeThrow(response.exceptionDetails);
|
|
2009
|
+
throw new Error(`Could not measure the text: ${threw.message}`);
|
|
2010
|
+
}
|
|
2011
|
+
return response.result.value;
|
|
2012
|
+
}
|
|
1940
2013
|
async layout() {
|
|
1941
2014
|
await this.ready();
|
|
1942
2015
|
const response = await this.cdp.send("Runtime.evaluate", {
|
package/package.json
CHANGED
|
@@ -1,145 +1,145 @@
|
|
|
1
1
|
{
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
}
|
|
2
|
+
"name": "@jitsusama/agentic-harness.core",
|
|
3
|
+
"version": "0.2.0",
|
|
4
|
+
"description": "Pi-agnostic business logic for agentic-harness: state machines, guardian decisions, quest/TDD domain model.",
|
|
5
|
+
"license": "MIT",
|
|
6
|
+
"type": "module",
|
|
7
|
+
"overrides": {
|
|
8
|
+
"google-auth-library": "$google-auth-library"
|
|
9
|
+
},
|
|
10
|
+
"exports": {
|
|
11
|
+
"./tdd": "./dist/tdd/index.js",
|
|
12
|
+
"./tdd/presentation": "./dist/tdd/presentation.js",
|
|
13
|
+
"./shell": "./dist/shell/index.js",
|
|
14
|
+
"./command": "./dist/command/index.js",
|
|
15
|
+
"./git-cli": "./dist/git-cli/index.js",
|
|
16
|
+
"./github-cli": "./dist/github-cli/index.js",
|
|
17
|
+
"./attribution": "./dist/attribution/index.js",
|
|
18
|
+
"./verify": "./dist/verify/index.js",
|
|
19
|
+
"./memory": "./dist/memory/index.js",
|
|
20
|
+
"./governance": "./dist/governance/index.js",
|
|
21
|
+
"./observability": "./dist/observability/index.js",
|
|
22
|
+
"./completion": "./dist/completion/index.js",
|
|
23
|
+
"./advisor": "./dist/advisor/index.js",
|
|
24
|
+
"./quest": "./dist/quest/index.js",
|
|
25
|
+
"./quest/lifecycle": "./dist/quest/lifecycle.js",
|
|
26
|
+
"./quest/lookup": "./dist/quest/lookup.js",
|
|
27
|
+
"./quest/state": "./dist/quest/state.js",
|
|
28
|
+
"./quest/machine": "./dist/quest/machine.js",
|
|
29
|
+
"./quest/actions": "./dist/quest/actions.js",
|
|
30
|
+
"./quest/config": "./dist/quest/config.js",
|
|
31
|
+
"./quest/render-rows": "./dist/quest/render-rows.js",
|
|
32
|
+
"./quest/verbs/shared": "./dist/quest/verbs/shared.js",
|
|
33
|
+
"./quest/verbs/alias": "./dist/quest/verbs/alias.js",
|
|
34
|
+
"./quest/verbs/reorder": "./dist/quest/verbs/reorder.js",
|
|
35
|
+
"./quest/verbs/structural": "./dist/quest/verbs/structural.js",
|
|
36
|
+
"./quest/verbs/stage": "./dist/quest/verbs/stage.js",
|
|
37
|
+
"./quest/verbs/queries": "./dist/quest/verbs/queries.js",
|
|
38
|
+
"./quest/verbs/lifecycle": "./dist/quest/verbs/lifecycle.js",
|
|
39
|
+
"./quest/verbs/tree-ops": "./dist/quest/verbs/tree-ops.js",
|
|
40
|
+
"./tree": "./dist/tree/index.js",
|
|
41
|
+
"./lsp": "./dist/lsp/index.js",
|
|
42
|
+
"./result": "./dist/result/index.js",
|
|
43
|
+
"./refs": "./dist/refs/index.js",
|
|
44
|
+
"./prose": "./dist/prose/index.js",
|
|
45
|
+
"./gate": "./dist/gate/index.js",
|
|
46
|
+
"./sections": "./dist/sections/index.js",
|
|
47
|
+
"./title": "./dist/title/index.js",
|
|
48
|
+
"./guardian": "./dist/guardian/index.js",
|
|
49
|
+
"./guardian/prose-gate": "./dist/internal/guardian/prose-gate.js",
|
|
50
|
+
"./guardian/section-gate": "./dist/internal/guardian/section-gate.js",
|
|
51
|
+
"./guardian/title-gate": "./dist/internal/guardian/title-gate.js",
|
|
52
|
+
"./guardian/redirect-gate": "./dist/internal/guardian/redirect-gate.js",
|
|
53
|
+
"./guardian/history-gate": "./dist/internal/guardian/history-gate.js",
|
|
54
|
+
"./guardian/commit-shell": "./dist/internal/guardian/commit-shell.js",
|
|
55
|
+
"./guardian/commit-format": "./dist/internal/guardian/commit-format.js",
|
|
56
|
+
"./guardian/commit-file": "./dist/internal/guardian/commit-file.js",
|
|
57
|
+
"./github/cli": "./dist/internal/github/cli.js",
|
|
58
|
+
"./clock": "./dist/clock/index.js",
|
|
59
|
+
"./exec": "./dist/exec/index.js",
|
|
60
|
+
"./remote": "./dist/remote/index.js",
|
|
61
|
+
"./process": "./dist/process/index.js",
|
|
62
|
+
"./work": "./dist/work/index.js",
|
|
63
|
+
"./review": "./dist/review/index.js",
|
|
64
|
+
"./web": "./dist/web/index.js",
|
|
65
|
+
"./web/a11y": "./dist/web/a11y/index.js",
|
|
66
|
+
"./web/audit": "./dist/web/audit/index.js",
|
|
67
|
+
"./web/audit/verdict": "./dist/web/audit/verdict.js",
|
|
68
|
+
"./web/browser": "./dist/web/browser.js",
|
|
69
|
+
"./web/compare": "./dist/web/compare/index.js",
|
|
70
|
+
"./web/cookies": "./dist/web/cookies/index.js",
|
|
71
|
+
"./web/design": "./dist/web/design/index.js",
|
|
72
|
+
"./web/element": "./dist/web/element/index.js",
|
|
73
|
+
"./web/environment": "./dist/web/environment/index.js",
|
|
74
|
+
"./web/environment/devices": "./dist/web/environment/devices.js",
|
|
75
|
+
"./web/evaluate": "./dist/web/evaluate/index.js",
|
|
76
|
+
"./web/hydration": "./dist/web/hydration/index.js",
|
|
77
|
+
"./web/input": "./dist/web/input/index.js",
|
|
78
|
+
"./web/mermaid": "./dist/web/mermaid.js",
|
|
79
|
+
"./web/perf": "./dist/web/perf/index.js",
|
|
80
|
+
"./web/reader": "./dist/web/reader.js",
|
|
81
|
+
"./web/search": "./dist/web/search.js",
|
|
82
|
+
"./web/session": "./dist/web/session.js",
|
|
83
|
+
"./web/snapshot": "./dist/web/snapshot/index.js",
|
|
84
|
+
"./web/target": "./dist/web/target/index.js",
|
|
85
|
+
"./web/telemetry": "./dist/web/telemetry/index.js",
|
|
86
|
+
"./web/wait": "./dist/web/wait/index.js",
|
|
87
|
+
"./slack": "./dist/slack/index.js",
|
|
88
|
+
"./slack/auth/browser": "./dist/slack/auth/browser.js",
|
|
89
|
+
"./slack/auth/browser-extract": "./dist/slack/auth/browser-extract.js",
|
|
90
|
+
"./slack/auth/extract": "./dist/slack/auth/extract.js",
|
|
91
|
+
"./slack/auth/oauth": "./dist/slack/auth/oauth.js",
|
|
92
|
+
"./slack/auth/server": "./dist/slack/auth/server.js",
|
|
93
|
+
"./slack/types": "./dist/slack/types.js",
|
|
94
|
+
"./google": "./dist/google/index.js",
|
|
95
|
+
"./google/auth/browser": "./dist/google/auth/browser.js",
|
|
96
|
+
"./google/auth/oauth": "./dist/google/auth/oauth.js",
|
|
97
|
+
"./google/auth/server": "./dist/google/auth/server.js",
|
|
98
|
+
"./google/auth/setup-instructions": "./dist/google/auth/setup-instructions.js",
|
|
99
|
+
"./google/types": "./dist/google/types.js"
|
|
100
|
+
},
|
|
101
|
+
"bin": {
|
|
102
|
+
"agentic-harness-core": "./dist/bin/cli.js"
|
|
103
|
+
},
|
|
104
|
+
"files": [
|
|
105
|
+
"dist"
|
|
106
|
+
],
|
|
107
|
+
"engines": {
|
|
108
|
+
"node": ">=22.19.0"
|
|
109
|
+
},
|
|
110
|
+
"dependencies": {
|
|
111
|
+
"axe-core": "^4.12.1",
|
|
112
|
+
"defuddle": "^0.19.1",
|
|
113
|
+
"google-auth-library": "^10.9.0",
|
|
114
|
+
"googleapis": "^173.0.0",
|
|
115
|
+
"jsdom": "^29.1.1",
|
|
116
|
+
"jsonpath-plus": "^10.4.0",
|
|
117
|
+
"pixelmatch": "^7.2.0",
|
|
118
|
+
"pngjs": "^7.0.0",
|
|
119
|
+
"puppeteer-core": "^25.3.0",
|
|
120
|
+
"sqlite3": "^6.0.1",
|
|
121
|
+
"vscode-jsonrpc": "^9.0.1",
|
|
122
|
+
"vscode-languageserver-protocol": "^3.18.2",
|
|
123
|
+
"yaml": "^2.9.0"
|
|
124
|
+
},
|
|
125
|
+
"devDependencies": {
|
|
126
|
+
"@biomejs/biome": "^2.5.9",
|
|
127
|
+
"@types/jsdom": "^28.0.3",
|
|
128
|
+
"@types/node": "^26.1.1",
|
|
129
|
+
"@types/pngjs": "^6.0.5",
|
|
130
|
+
"@types/ws": "^8.18.1",
|
|
131
|
+
"typescript": "^7.0.2",
|
|
132
|
+
"vitest": "^4.1.11",
|
|
133
|
+
"ws": "^8.21.1"
|
|
134
|
+
},
|
|
135
|
+
"scripts": {
|
|
136
|
+
"build": "tsc -p tsconfig.build.json",
|
|
137
|
+
"lint": "biome check .",
|
|
138
|
+
"lint:fix": "biome check --write .",
|
|
139
|
+
"typecheck": "tsc --noEmit",
|
|
140
|
+
"pretest": "tsc -p tsconfig.build.json",
|
|
141
|
+
"test": "vitest run",
|
|
142
|
+
"test:watch": "vitest",
|
|
143
|
+
"test:browser": "vitest run --config vitest.browser.config.ts"
|
|
144
|
+
}
|
|
145
|
+
}
|
package/dist/memory/db.d.ts
DELETED
|
@@ -1,15 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Thin promise wrapper over the callback-based sqlite3 driver.
|
|
3
|
-
* sqlite3 is a native module, so it is lazy-imported on first
|
|
4
|
-
* open; callers speak promises and never touch the driver
|
|
5
|
-
* directly.
|
|
6
|
-
*/
|
|
7
|
-
/** A promise-speaking handle to a SQLite database. */
|
|
8
|
-
export interface Db {
|
|
9
|
-
run(sql: string, params?: readonly unknown[]): Promise<void>;
|
|
10
|
-
all<T>(sql: string, params?: readonly unknown[]): Promise<T[]>;
|
|
11
|
-
exec(sql: string): Promise<void>;
|
|
12
|
-
close(): Promise<void>;
|
|
13
|
-
}
|
|
14
|
-
/** Open a SQLite database at the given path (`:memory:` for tests). */
|
|
15
|
-
export declare function openDb(dbPath: string): Promise<Db>;
|