@restormel/testing-core 0.1.0 → 0.1.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/LICENSE +1 -1
- package/dist/assertion.d.ts +6 -2
- package/dist/assertion.d.ts.map +1 -1
- package/dist/goal.d.ts +5 -0
- package/dist/goal.d.ts.map +1 -1
- package/dist/index.d.ts +2 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1 -0
- package/dist/index.js.map +1 -1
- package/dist/normalize.d.ts.map +1 -1
- package/dist/normalize.js +4 -0
- package/dist/normalize.js.map +1 -1
- package/dist/safe-path.d.ts +19 -0
- package/dist/safe-path.d.ts.map +1 -0
- package/dist/safe-path.js +34 -0
- package/dist/safe-path.js.map +1 -0
- package/dist/success-criteria.d.ts +5 -0
- package/dist/success-criteria.d.ts.map +1 -1
- package/package.json +5 -5
package/LICENSE
CHANGED
package/dist/assertion.d.ts
CHANGED
|
@@ -1,9 +1,13 @@
|
|
|
1
|
-
import type { JudgeRubric, StructuredCheck } from "./success-criteria.js";
|
|
1
|
+
import type { JudgeRubric, StructuredCheck, SuccessCriteria } from "./success-criteria.js";
|
|
2
2
|
/**
|
|
3
3
|
* One atomic expectation (for traces, reports, or normalised criteria).
|
|
4
4
|
* Config YAML may use the flatter `SuccessCriteria` shape instead.
|
|
5
5
|
*/
|
|
6
|
-
export type Assertion = UrlAssertion | DomAssertion | TextPresentAssertion | TextAbsentAssertion | StructuredAssertion | JudgeAssertion;
|
|
6
|
+
export type Assertion = AnyOfAssertion | UrlAssertion | DomAssertion | TextPresentAssertion | TextAbsentAssertion | StructuredAssertion | JudgeAssertion;
|
|
7
|
+
export interface AnyOfAssertion {
|
|
8
|
+
kind: "any_of";
|
|
9
|
+
branches: SuccessCriteria[];
|
|
10
|
+
}
|
|
7
11
|
export interface UrlAssertion {
|
|
8
12
|
kind: "url";
|
|
9
13
|
patterns: string[];
|
package/dist/assertion.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"assertion.d.ts","sourceRoot":"","sources":["../src/assertion.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAC;
|
|
1
|
+
{"version":3,"file":"assertion.d.ts","sourceRoot":"","sources":["../src/assertion.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,eAAe,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAC;AAE3F;;;GAGG;AACH,MAAM,MAAM,SAAS,GACjB,cAAc,GACd,YAAY,GACZ,YAAY,GACZ,oBAAoB,GACpB,mBAAmB,GACnB,mBAAmB,GACnB,cAAc,CAAC;AAEnB,MAAM,WAAW,cAAc;IAC7B,IAAI,EAAE,QAAQ,CAAC;IACf,QAAQ,EAAE,eAAe,EAAE,CAAC;CAC7B;AAED,MAAM,WAAW,YAAY;IAC3B,IAAI,EAAE,KAAK,CAAC;IACZ,QAAQ,EAAE,MAAM,EAAE,CAAC;CACpB;AAED,MAAM,WAAW,YAAY;IAC3B,IAAI,EAAE,KAAK,CAAC;IACZ,SAAS,EAAE,MAAM,EAAE,CAAC;CACrB;AAED,MAAM,WAAW,oBAAoB;IACnC,IAAI,EAAE,cAAc,CAAC;IACrB,UAAU,EAAE,MAAM,EAAE,CAAC;CACtB;AAED,MAAM,WAAW,mBAAmB;IAClC,IAAI,EAAE,aAAa,CAAC;IACpB,UAAU,EAAE,MAAM,EAAE,CAAC;CACtB;AAED,MAAM,WAAW,mBAAmB;IAClC,IAAI,EAAE,YAAY,CAAC;IACnB,KAAK,EAAE,eAAe,CAAC;CACxB;AAED,MAAM,WAAW,cAAc;IAC7B,IAAI,EAAE,OAAO,CAAC;IACd,MAAM,EAAE,WAAW,CAAC;CACrB"}
|
package/dist/goal.d.ts
CHANGED
|
@@ -7,6 +7,11 @@ export interface TestGoal {
|
|
|
7
7
|
type: GoalType;
|
|
8
8
|
description: string;
|
|
9
9
|
successCriteria: SuccessCriteria;
|
|
10
|
+
/**
|
|
11
|
+
* Path relative to environment `base_url` for the initial navigation (e.g. `/login`, `dashboard/`).
|
|
12
|
+
* Resolved with `new URL(startPath, baseUrl)`.
|
|
13
|
+
*/
|
|
14
|
+
startPath?: string;
|
|
10
15
|
preconditions?: HookRef[];
|
|
11
16
|
cleanup?: HookRef[];
|
|
12
17
|
exclusiveWith?: string[];
|
package/dist/goal.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"goal.d.ts","sourceRoot":"","sources":["../src/goal.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAC;AAE7D,MAAM,MAAM,QAAQ,GAAG,SAAS,GAAG,aAAa,GAAG,QAAQ,CAAC;AAE5D,iEAAiE;AACjE,MAAM,MAAM,OAAO,GAAG,MAAM,CAAC;AAE7B,MAAM,WAAW,QAAQ;IACvB,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,QAAQ,CAAC;IACf,WAAW,EAAE,MAAM,CAAC;IACpB,eAAe,EAAE,eAAe,CAAC;IACjC,aAAa,CAAC,EAAE,OAAO,EAAE,CAAC;IAC1B,OAAO,CAAC,EAAE,OAAO,EAAE,CAAC;IACpB,aAAa,CAAC,EAAE,MAAM,EAAE,CAAC;IACzB,IAAI,CAAC,EAAE,MAAM,EAAE,CAAC;CACjB"}
|
|
1
|
+
{"version":3,"file":"goal.d.ts","sourceRoot":"","sources":["../src/goal.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAC;AAE7D,MAAM,MAAM,QAAQ,GAAG,SAAS,GAAG,aAAa,GAAG,QAAQ,CAAC;AAE5D,iEAAiE;AACjE,MAAM,MAAM,OAAO,GAAG,MAAM,CAAC;AAE7B,MAAM,WAAW,QAAQ;IACvB,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,QAAQ,CAAC;IACf,WAAW,EAAE,MAAM,CAAC;IACpB,eAAe,EAAE,eAAe,CAAC;IACjC;;;OAGG;IACH,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,aAAa,CAAC,EAAE,OAAO,EAAE,CAAC;IAC1B,OAAO,CAAC,EAAE,OAAO,EAAE,CAAC;IACpB,aAAa,CAAC,EAAE,MAAM,EAAE,CAAC;IACzB,IAAI,CAAC,EAAE,MAAM,EAAE,CAAC;CACjB"}
|
package/dist/index.d.ts
CHANGED
|
@@ -15,6 +15,8 @@ export type { CostEstimate, GoalRunRecord, KeysModelMeta, RunRecord, RunRequest,
|
|
|
15
15
|
export type { JudgeRubric, StructuredCheck, SuccessCriteria } from "./success-criteria.js";
|
|
16
16
|
export type { TestSuite } from "./suite.js";
|
|
17
17
|
export type { Verdict } from "./verdict.js";
|
|
18
|
+
export { isPathContainedInRoot, resolvePathUnderRoot, sanitizePathSegment, } from "./safe-path.js";
|
|
19
|
+
export type { ResolvePathUnderRootResult } from "./safe-path.js";
|
|
18
20
|
/** Doc-aligned alias for `RunRecord`. */
|
|
19
21
|
export type TestRun = import("./run.js").RunRecord;
|
|
20
22
|
//# sourceMappingURL=index.d.ts.map
|
package/dist/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,eAAO,MAAM,kBAAkB,EAAG,yBAAkC,CAAC;AAErE,OAAO,EACL,eAAe,EACf,QAAQ,EACR,WAAW,EACX,YAAY,GACb,MAAM,aAAa,CAAC;AACrB,OAAO,EAAE,SAAS,EAAE,QAAQ,EAAE,MAAM,cAAc,CAAC;AACnD,OAAO,EAAE,2BAA2B,EAAE,MAAM,gBAAgB,CAAC;AAE7D,YAAY,EAAE,SAAS,EAAE,MAAM,gBAAgB,CAAC;AAChD,YAAY,EACV,YAAY,EACZ,cAAc,EACd,mBAAmB,EACnB,mBAAmB,EACnB,oBAAoB,EACpB,YAAY,GACb,MAAM,gBAAgB,CAAC;AACxB,YAAY,EAAE,kBAAkB,EAAE,MAAM,kBAAkB,CAAC;AAC3D,YAAY,EAAE,QAAQ,EAAE,OAAO,EAAE,QAAQ,EAAE,MAAM,WAAW,CAAC;AAC7D,YAAY,EAAE,cAAc,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AACjE,YAAY,EACV,WAAW,EACX,gBAAgB,EAChB,MAAM,EACN,SAAS,GACV,MAAM,aAAa,CAAC;AACrB,YAAY,EACV,YAAY,EACZ,aAAa,EACb,aAAa,EACb,SAAS,EACT,UAAU,EACV,UAAU,EACV,gBAAgB,EAChB,UAAU,EACV,cAAc,GACf,MAAM,UAAU,CAAC;AAClB,YAAY,EAAE,WAAW,EAAE,eAAe,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAC;AAC3F,YAAY,EAAE,SAAS,EAAE,MAAM,YAAY,CAAC;AAC5C,YAAY,EAAE,OAAO,EAAE,MAAM,cAAc,CAAC;AAE5C,yCAAyC;AACzC,MAAM,MAAM,OAAO,GAAG,OAAO,UAAU,EAAE,SAAS,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,eAAO,MAAM,kBAAkB,EAAG,yBAAkC,CAAC;AAErE,OAAO,EACL,eAAe,EACf,QAAQ,EACR,WAAW,EACX,YAAY,GACb,MAAM,aAAa,CAAC;AACrB,OAAO,EAAE,SAAS,EAAE,QAAQ,EAAE,MAAM,cAAc,CAAC;AACnD,OAAO,EAAE,2BAA2B,EAAE,MAAM,gBAAgB,CAAC;AAE7D,YAAY,EAAE,SAAS,EAAE,MAAM,gBAAgB,CAAC;AAChD,YAAY,EACV,YAAY,EACZ,cAAc,EACd,mBAAmB,EACnB,mBAAmB,EACnB,oBAAoB,EACpB,YAAY,GACb,MAAM,gBAAgB,CAAC;AACxB,YAAY,EAAE,kBAAkB,EAAE,MAAM,kBAAkB,CAAC;AAC3D,YAAY,EAAE,QAAQ,EAAE,OAAO,EAAE,QAAQ,EAAE,MAAM,WAAW,CAAC;AAC7D,YAAY,EAAE,cAAc,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AACjE,YAAY,EACV,WAAW,EACX,gBAAgB,EAChB,MAAM,EACN,SAAS,GACV,MAAM,aAAa,CAAC;AACrB,YAAY,EACV,YAAY,EACZ,aAAa,EACb,aAAa,EACb,SAAS,EACT,UAAU,EACV,UAAU,EACV,gBAAgB,EAChB,UAAU,EACV,cAAc,GACf,MAAM,UAAU,CAAC;AAClB,YAAY,EAAE,WAAW,EAAE,eAAe,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAC;AAC3F,YAAY,EAAE,SAAS,EAAE,MAAM,YAAY,CAAC;AAC5C,YAAY,EAAE,OAAO,EAAE,MAAM,cAAc,CAAC;AAE5C,OAAO,EACL,qBAAqB,EACrB,oBAAoB,EACpB,mBAAmB,GACpB,MAAM,gBAAgB,CAAC;AACxB,YAAY,EAAE,0BAA0B,EAAE,MAAM,gBAAgB,CAAC;AAEjE,yCAAyC;AACzC,MAAM,MAAM,OAAO,GAAG,OAAO,UAAU,EAAE,SAAS,CAAC"}
|
package/dist/index.js
CHANGED
|
@@ -5,4 +5,5 @@ export const testingCorePackage = "@restormel/testing-core";
|
|
|
5
5
|
export { isGoalRunRecord, isReport, isRunRecord, isTraceEvent, } from "./guards.js";
|
|
6
6
|
export { isVerdict, VERDICTS } from "./verdict.js";
|
|
7
7
|
export { successCriteriaToAssertions } from "./normalize.js";
|
|
8
|
+
export { isPathContainedInRoot, resolvePathUnderRoot, sanitizePathSegment, } from "./safe-path.js";
|
|
8
9
|
//# sourceMappingURL=index.js.map
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,MAAM,CAAC,MAAM,kBAAkB,GAAG,yBAAkC,CAAC;AAErE,OAAO,EACL,eAAe,EACf,QAAQ,EACR,WAAW,EACX,YAAY,GACb,MAAM,aAAa,CAAC;AACrB,OAAO,EAAE,SAAS,EAAE,QAAQ,EAAE,MAAM,cAAc,CAAC;AACnD,OAAO,EAAE,2BAA2B,EAAE,MAAM,gBAAgB,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,MAAM,CAAC,MAAM,kBAAkB,GAAG,yBAAkC,CAAC;AAErE,OAAO,EACL,eAAe,EACf,QAAQ,EACR,WAAW,EACX,YAAY,GACb,MAAM,aAAa,CAAC;AACrB,OAAO,EAAE,SAAS,EAAE,QAAQ,EAAE,MAAM,cAAc,CAAC;AACnD,OAAO,EAAE,2BAA2B,EAAE,MAAM,gBAAgB,CAAC;AAmC7D,OAAO,EACL,qBAAqB,EACrB,oBAAoB,EACpB,mBAAmB,GACpB,MAAM,gBAAgB,CAAC"}
|
package/dist/normalize.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"normalize.d.ts","sourceRoot":"","sources":["../src/normalize.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,gBAAgB,CAAC;AAChD,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAC;AAE7D,6FAA6F;AAC7F,wBAAgB,2BAA2B,CAAC,QAAQ,EAAE,eAAe,GAAG,SAAS,EAAE,
|
|
1
|
+
{"version":3,"file":"normalize.d.ts","sourceRoot":"","sources":["../src/normalize.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,gBAAgB,CAAC;AAChD,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAC;AAE7D,6FAA6F;AAC7F,wBAAgB,2BAA2B,CAAC,QAAQ,EAAE,eAAe,GAAG,SAAS,EAAE,CA8BlF"}
|
package/dist/normalize.js
CHANGED
|
@@ -1,6 +1,10 @@
|
|
|
1
1
|
/** Flattens repo-config `SuccessCriteria` into discrete assertions for runners or traces. */
|
|
2
2
|
export function successCriteriaToAssertions(criteria) {
|
|
3
3
|
const out = [];
|
|
4
|
+
if (criteria.anyOf !== undefined && criteria.anyOf.length > 0) {
|
|
5
|
+
out.push({ kind: "any_of", branches: [...criteria.anyOf] });
|
|
6
|
+
return out;
|
|
7
|
+
}
|
|
4
8
|
if (criteria.urlMatches != null) {
|
|
5
9
|
const patterns = Array.isArray(criteria.urlMatches)
|
|
6
10
|
? criteria.urlMatches
|
package/dist/normalize.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"normalize.js","sourceRoot":"","sources":["../src/normalize.ts"],"names":[],"mappings":"AAGA,6FAA6F;AAC7F,MAAM,UAAU,2BAA2B,CAAC,QAAyB;IACnE,MAAM,GAAG,GAAgB,EAAE,CAAC;IAC5B,IAAI,QAAQ,CAAC,UAAU,IAAI,IAAI,EAAE,CAAC;QAChC,MAAM,QAAQ,GAAG,KAAK,CAAC,OAAO,CAAC,QAAQ,CAAC,UAAU,CAAC;YACjD,CAAC,CAAC,QAAQ,CAAC,UAAU;YACrB,CAAC,CAAC,CAAC,QAAQ,CAAC,UAAU,CAAC,CAAC;QAC1B,IAAI,QAAQ,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;YACxB,GAAG,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,KAAK,EAAE,QAAQ,EAAE,CAAC,GAAG,QAAQ,CAAC,EAAE,CAAC,CAAC;QACrD,CAAC;IACH,CAAC;IACD,IAAI,QAAQ,CAAC,UAAU,IAAI,IAAI,IAAI,QAAQ,CAAC,UAAU,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;QAClE,GAAG,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,KAAK,EAAE,SAAS,EAAE,CAAC,GAAG,QAAQ,CAAC,UAAU,CAAC,EAAE,CAAC,CAAC;IACjE,CAAC;IACD,IAAI,QAAQ,CAAC,WAAW,IAAI,IAAI,IAAI,QAAQ,CAAC,WAAW,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;QACpE,GAAG,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,cAAc,EAAE,UAAU,EAAE,CAAC,GAAG,QAAQ,CAAC,WAAW,CAAC,EAAE,CAAC,CAAC;IAC5E,CAAC;IACD,IAAI,QAAQ,CAAC,UAAU,IAAI,IAAI,IAAI,QAAQ,CAAC,UAAU,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;QAClE,GAAG,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,aAAa,EAAE,UAAU,EAAE,CAAC,GAAG,QAAQ,CAAC,UAAU,CAAC,EAAE,CAAC,CAAC;IAC1E,CAAC;IACD,KAAK,MAAM,KAAK,IAAI,QAAQ,CAAC,gBAAgB,IAAI,EAAE,EAAE,CAAC;QACpD,GAAG,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,YAAY,EAAE,KAAK,EAAE,CAAC,CAAC;IAC1C,CAAC;IACD,IAAI,QAAQ,CAAC,WAAW,IAAI,IAAI,EAAE,CAAC;QACjC,GAAG,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,EAAE,QAAQ,CAAC,WAAW,EAAE,CAAC,CAAC;IAC5D,CAAC;IACD,OAAO,GAAG,CAAC;AACb,CAAC"}
|
|
1
|
+
{"version":3,"file":"normalize.js","sourceRoot":"","sources":["../src/normalize.ts"],"names":[],"mappings":"AAGA,6FAA6F;AAC7F,MAAM,UAAU,2BAA2B,CAAC,QAAyB;IACnE,MAAM,GAAG,GAAgB,EAAE,CAAC;IAC5B,IAAI,QAAQ,CAAC,KAAK,KAAK,SAAS,IAAI,QAAQ,CAAC,KAAK,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;QAC9D,GAAG,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,QAAQ,EAAE,QAAQ,EAAE,CAAC,GAAG,QAAQ,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC;QAC5D,OAAO,GAAG,CAAC;IACb,CAAC;IACD,IAAI,QAAQ,CAAC,UAAU,IAAI,IAAI,EAAE,CAAC;QAChC,MAAM,QAAQ,GAAG,KAAK,CAAC,OAAO,CAAC,QAAQ,CAAC,UAAU,CAAC;YACjD,CAAC,CAAC,QAAQ,CAAC,UAAU;YACrB,CAAC,CAAC,CAAC,QAAQ,CAAC,UAAU,CAAC,CAAC;QAC1B,IAAI,QAAQ,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;YACxB,GAAG,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,KAAK,EAAE,QAAQ,EAAE,CAAC,GAAG,QAAQ,CAAC,EAAE,CAAC,CAAC;QACrD,CAAC;IACH,CAAC;IACD,IAAI,QAAQ,CAAC,UAAU,IAAI,IAAI,IAAI,QAAQ,CAAC,UAAU,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;QAClE,GAAG,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,KAAK,EAAE,SAAS,EAAE,CAAC,GAAG,QAAQ,CAAC,UAAU,CAAC,EAAE,CAAC,CAAC;IACjE,CAAC;IACD,IAAI,QAAQ,CAAC,WAAW,IAAI,IAAI,IAAI,QAAQ,CAAC,WAAW,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;QACpE,GAAG,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,cAAc,EAAE,UAAU,EAAE,CAAC,GAAG,QAAQ,CAAC,WAAW,CAAC,EAAE,CAAC,CAAC;IAC5E,CAAC;IACD,IAAI,QAAQ,CAAC,UAAU,IAAI,IAAI,IAAI,QAAQ,CAAC,UAAU,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;QAClE,GAAG,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,aAAa,EAAE,UAAU,EAAE,CAAC,GAAG,QAAQ,CAAC,UAAU,CAAC,EAAE,CAAC,CAAC;IAC1E,CAAC;IACD,KAAK,MAAM,KAAK,IAAI,QAAQ,CAAC,gBAAgB,IAAI,EAAE,EAAE,CAAC;QACpD,GAAG,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,YAAY,EAAE,KAAK,EAAE,CAAC,CAAC;IAC1C,CAAC;IACD,IAAI,QAAQ,CAAC,WAAW,IAAI,IAAI,EAAE,CAAC;QACjC,GAAG,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,EAAE,QAAQ,CAAC,WAAW,EAAE,CAAC,CAAC;IAC5D,CAAC;IACD,OAAO,GAAG,CAAC;AACb,CAAC"}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* True if `candidateAbs` is the same path or strictly inside `rootAbs` (no `..` escape).
|
|
3
|
+
* Both paths should be absolute (e.g. from `path.resolve`).
|
|
4
|
+
*/
|
|
5
|
+
export declare function isPathContainedInRoot(rootAbs: string, candidateAbs: string): boolean;
|
|
6
|
+
export type ResolvePathUnderRootResult = {
|
|
7
|
+
ok: true;
|
|
8
|
+
path: string;
|
|
9
|
+
} | {
|
|
10
|
+
ok: false;
|
|
11
|
+
reason: string;
|
|
12
|
+
};
|
|
13
|
+
/**
|
|
14
|
+
* Resolve a user-supplied path against `root` and reject directory traversal outside `root`.
|
|
15
|
+
*/
|
|
16
|
+
export declare function resolvePathUnderRoot(root: string, userPath: string): ResolvePathUnderRootResult;
|
|
17
|
+
/** Single path segment safe for directory names (goal ids, etc.). */
|
|
18
|
+
export declare function sanitizePathSegment(segment: string, maxLen?: number): string;
|
|
19
|
+
//# sourceMappingURL=safe-path.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"safe-path.d.ts","sourceRoot":"","sources":["../src/safe-path.ts"],"names":[],"mappings":"AAEA;;;GAGG;AACH,wBAAgB,qBAAqB,CAAC,OAAO,EAAE,MAAM,EAAE,YAAY,EAAE,MAAM,GAAG,OAAO,CAGpF;AAED,MAAM,MAAM,0BAA0B,GAClC;IAAE,EAAE,EAAE,IAAI,CAAC;IAAC,IAAI,EAAE,MAAM,CAAA;CAAE,GAC1B;IAAE,EAAE,EAAE,KAAK,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,CAAC;AAElC;;GAEG;AACH,wBAAgB,oBAAoB,CAAC,IAAI,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,0BAA0B,CAO/F;AAED,qEAAqE;AACrE,wBAAgB,mBAAmB,CAAC,OAAO,EAAE,MAAM,EAAE,MAAM,SAAM,GAAG,MAAM,CASzE"}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import { isAbsolute, relative, resolve } from "node:path";
|
|
2
|
+
/**
|
|
3
|
+
* True if `candidateAbs` is the same path or strictly inside `rootAbs` (no `..` escape).
|
|
4
|
+
* Both paths should be absolute (e.g. from `path.resolve`).
|
|
5
|
+
*/
|
|
6
|
+
export function isPathContainedInRoot(rootAbs, candidateAbs) {
|
|
7
|
+
const rel = relative(rootAbs, candidateAbs);
|
|
8
|
+
return rel === "" || (!rel.startsWith("..") && !isAbsolute(rel));
|
|
9
|
+
}
|
|
10
|
+
/**
|
|
11
|
+
* Resolve a user-supplied path against `root` and reject directory traversal outside `root`.
|
|
12
|
+
*/
|
|
13
|
+
export function resolvePathUnderRoot(root, userPath) {
|
|
14
|
+
const rootAbs = resolve(root);
|
|
15
|
+
const candidateAbs = isAbsolute(userPath) ? resolve(userPath) : resolve(rootAbs, userPath);
|
|
16
|
+
if (!isPathContainedInRoot(rootAbs, candidateAbs)) {
|
|
17
|
+
return { ok: false, reason: `Path escapes allowed root (${rootAbs}): ${userPath}` };
|
|
18
|
+
}
|
|
19
|
+
return { ok: true, path: candidateAbs };
|
|
20
|
+
}
|
|
21
|
+
/** Single path segment safe for directory names (goal ids, etc.). */
|
|
22
|
+
export function sanitizePathSegment(segment, maxLen = 128) {
|
|
23
|
+
const s = segment.trim();
|
|
24
|
+
if (s.length === 0)
|
|
25
|
+
return "unnamed";
|
|
26
|
+
if (/^[a-zA-Z0-9._-]+$/.test(s) && s.length <= maxLen)
|
|
27
|
+
return s;
|
|
28
|
+
const folded = s
|
|
29
|
+
.replace(/[^a-zA-Z0-9._-]/g, "_")
|
|
30
|
+
.slice(0, maxLen)
|
|
31
|
+
.replace(/^_+|_+$/g, "");
|
|
32
|
+
return folded.length > 0 ? folded : "segment";
|
|
33
|
+
}
|
|
34
|
+
//# sourceMappingURL=safe-path.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"safe-path.js","sourceRoot":"","sources":["../src/safe-path.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,QAAQ,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAE1D;;;GAGG;AACH,MAAM,UAAU,qBAAqB,CAAC,OAAe,EAAE,YAAoB;IACzE,MAAM,GAAG,GAAG,QAAQ,CAAC,OAAO,EAAE,YAAY,CAAC,CAAC;IAC5C,OAAO,GAAG,KAAK,EAAE,IAAI,CAAC,CAAC,GAAG,CAAC,UAAU,CAAC,IAAI,CAAC,IAAI,CAAC,UAAU,CAAC,GAAG,CAAC,CAAC,CAAC;AACnE,CAAC;AAMD;;GAEG;AACH,MAAM,UAAU,oBAAoB,CAAC,IAAY,EAAE,QAAgB;IACjE,MAAM,OAAO,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IAC9B,MAAM,YAAY,GAAG,UAAU,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC,OAAO,EAAE,QAAQ,CAAC,CAAC;IAC3F,IAAI,CAAC,qBAAqB,CAAC,OAAO,EAAE,YAAY,CAAC,EAAE,CAAC;QAClD,OAAO,EAAE,EAAE,EAAE,KAAK,EAAE,MAAM,EAAE,8BAA8B,OAAO,MAAM,QAAQ,EAAE,EAAE,CAAC;IACtF,CAAC;IACD,OAAO,EAAE,EAAE,EAAE,IAAI,EAAE,IAAI,EAAE,YAAY,EAAE,CAAC;AAC1C,CAAC;AAED,qEAAqE;AACrE,MAAM,UAAU,mBAAmB,CAAC,OAAe,EAAE,MAAM,GAAG,GAAG;IAC/D,MAAM,CAAC,GAAG,OAAO,CAAC,IAAI,EAAE,CAAC;IACzB,IAAI,CAAC,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,SAAS,CAAC;IACrC,IAAI,mBAAmB,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,MAAM,IAAI,MAAM;QAAE,OAAO,CAAC,CAAC;IAChE,MAAM,MAAM,GAAG,CAAC;SACb,OAAO,CAAC,kBAAkB,EAAE,GAAG,CAAC;SAChC,KAAK,CAAC,CAAC,EAAE,MAAM,CAAC;SAChB,OAAO,CAAC,UAAU,EAAE,EAAE,CAAC,CAAC;IAC3B,OAAO,MAAM,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,SAAS,CAAC;AAChD,CAAC"}
|
|
@@ -23,6 +23,11 @@ export interface JudgeRubric {
|
|
|
23
23
|
* See `successCriteriaToAssertions` to normalise to `Assertion[]`.
|
|
24
24
|
*/
|
|
25
25
|
export interface SuccessCriteria {
|
|
26
|
+
/**
|
|
27
|
+
* At least two alternative criteria bundles; the goal passes if **any** branch passes.
|
|
28
|
+
* When set, no other keys may appear at this level (use nested objects inside each branch).
|
|
29
|
+
*/
|
|
30
|
+
anyOf?: SuccessCriteria[];
|
|
26
31
|
urlMatches?: string | string[];
|
|
27
32
|
domSignals?: string[];
|
|
28
33
|
textPresent?: string[];
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"success-criteria.d.ts","sourceRoot":"","sources":["../src/success-criteria.ts"],"names":[],"mappings":"AAAA,oFAAoF;AACpF,MAAM,WAAW,eAAe;IAC9B,EAAE,CAAC,EAAE,MAAM,CAAC;IACZ,+EAA+E;IAC/E,IAAI,EAAE,MAAM,CAAC;IACb,MAAM,CAAC,EAAE,OAAO,CAAC;CAClB;AAED,qEAAqE;AACrE,MAAM,WAAW,WAAW;IAC1B,EAAE,EAAE,MAAM,CAAC;IACX,qFAAqF;IACrF,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,uEAAuE;IACvE,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB;;;OAGG;IACH,eAAe,CAAC,EAAE,MAAM,CAAC;CAC1B;AAED;;;GAGG;AACH,MAAM,WAAW,eAAe;IAC9B,UAAU,CAAC,EAAE,MAAM,GAAG,MAAM,EAAE,CAAC;IAC/B,UAAU,CAAC,EAAE,MAAM,EAAE,CAAC;IACtB,WAAW,CAAC,EAAE,MAAM,EAAE,CAAC;IACvB,UAAU,CAAC,EAAE,MAAM,EAAE,CAAC;IACtB,gBAAgB,CAAC,EAAE,eAAe,EAAE,CAAC;IACrC,WAAW,CAAC,EAAE,WAAW,CAAC;CAC3B"}
|
|
1
|
+
{"version":3,"file":"success-criteria.d.ts","sourceRoot":"","sources":["../src/success-criteria.ts"],"names":[],"mappings":"AAAA,oFAAoF;AACpF,MAAM,WAAW,eAAe;IAC9B,EAAE,CAAC,EAAE,MAAM,CAAC;IACZ,+EAA+E;IAC/E,IAAI,EAAE,MAAM,CAAC;IACb,MAAM,CAAC,EAAE,OAAO,CAAC;CAClB;AAED,qEAAqE;AACrE,MAAM,WAAW,WAAW;IAC1B,EAAE,EAAE,MAAM,CAAC;IACX,qFAAqF;IACrF,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,uEAAuE;IACvE,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB;;;OAGG;IACH,eAAe,CAAC,EAAE,MAAM,CAAC;CAC1B;AAED;;;GAGG;AACH,MAAM,WAAW,eAAe;IAC9B;;;OAGG;IACH,KAAK,CAAC,EAAE,eAAe,EAAE,CAAC;IAC1B,UAAU,CAAC,EAAE,MAAM,GAAG,MAAM,EAAE,CAAC;IAC/B,UAAU,CAAC,EAAE,MAAM,EAAE,CAAC;IACtB,WAAW,CAAC,EAAE,MAAM,EAAE,CAAC;IACvB,UAAU,CAAC,EAAE,MAAM,EAAE,CAAC;IACtB,gBAAgB,CAAC,EAAE,eAAe,EAAE,CAAC;IACrC,WAAW,CAAC,EAAE,WAAW,CAAC;CAC3B"}
|
package/package.json
CHANGED
|
@@ -1,17 +1,17 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@restormel/testing-core",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.1",
|
|
4
4
|
"description": "Contracts, run/verdict types, and shared primitives (scaffold).",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"repository": {
|
|
7
7
|
"type": "git",
|
|
8
|
-
"url": "https://github.com/Allotment-Technology-Ltd/restormel-
|
|
9
|
-
"directory": "packages/core"
|
|
8
|
+
"url": "https://github.com/Allotment-Technology-Ltd/restormel-keys.git",
|
|
9
|
+
"directory": "packages/testing-core"
|
|
10
10
|
},
|
|
11
11
|
"bugs": {
|
|
12
|
-
"url": "https://github.com/Allotment-Technology-Ltd/restormel-
|
|
12
|
+
"url": "https://github.com/Allotment-Technology-Ltd/restormel-keys/issues"
|
|
13
13
|
},
|
|
14
|
-
"homepage": "https://github.com/Allotment-Technology-Ltd/restormel-testing/tree/main/packages/core#readme",
|
|
14
|
+
"homepage": "https://github.com/Allotment-Technology-Ltd/restormel-testing/tree/main/packages/testing-core#readme",
|
|
15
15
|
"publishConfig": {
|
|
16
16
|
"access": "public"
|
|
17
17
|
},
|