@ripplo/testing 0.6.1 → 0.7.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.
Files changed (44) hide show
  1. package/DSL.md +355 -0
  2. package/LICENSE.md +1 -0
  3. package/README.md +47 -273
  4. package/dist/engine-BT7hUouB.d.ts +1095 -0
  5. package/dist/express.d.ts +7 -9
  6. package/dist/express.js +422 -48
  7. package/dist/index.d.ts +122 -59
  8. package/dist/index.js +1630 -1126
  9. package/package.json +31 -113
  10. package/dist/actions.d.ts +0 -260
  11. package/dist/actions.js +0 -177
  12. package/dist/assert.d.ts +0 -188
  13. package/dist/assert.js +0 -111
  14. package/dist/builder-SsgqYqSC.d.ts +0 -156
  15. package/dist/chunk-2YLI7VD4.js +0 -65
  16. package/dist/chunk-4MGIQFAJ.js +0 -16
  17. package/dist/chunk-DCJBLS2U.js +0 -26
  18. package/dist/chunk-MGATMMCZ.js +0 -16
  19. package/dist/chunk-XO36IU66.js +0 -88
  20. package/dist/chunk-YFOTJIVF.js +0 -134
  21. package/dist/chunk-YQAEOH5W.js +0 -111
  22. package/dist/compiler.d.ts +0 -32
  23. package/dist/compiler.js +0 -8
  24. package/dist/control.d.ts +0 -45
  25. package/dist/control.js +0 -17
  26. package/dist/elysia.d.ts +0 -78
  27. package/dist/elysia.js +0 -114
  28. package/dist/engine-BOqzK_go.d.ts +0 -61
  29. package/dist/fastify.d.ts +0 -14
  30. package/dist/fastify.js +0 -79
  31. package/dist/hono.d.ts +0 -19
  32. package/dist/hono.js +0 -89
  33. package/dist/koa.d.ts +0 -14
  34. package/dist/koa.js +0 -135
  35. package/dist/locators.d.ts +0 -40
  36. package/dist/locators.js +0 -11
  37. package/dist/lockfile.d.ts +0 -722
  38. package/dist/lockfile.js +0 -707
  39. package/dist/nestjs.d.ts +0 -17
  40. package/dist/nestjs.js +0 -139
  41. package/dist/nextjs.d.ts +0 -14
  42. package/dist/nextjs.js +0 -137
  43. package/dist/step-De52hTLd.d.ts +0 -19
  44. package/dist/types-BzZrl65Z.d.ts +0 -115
package/package.json CHANGED
@@ -1,10 +1,13 @@
1
1
  {
2
2
  "name": "@ripplo/testing",
3
- "description": "TypeScript DSL for defining and running Ripplo e2e workflow tests",
4
- "version": "0.6.1",
3
+ "version": "0.7.0",
4
+ "description": "Typed test DSL for Ripplo — declare entities and user flows, compile to a lockfile",
5
+ "homepage": "https://ripplo.ai",
6
+ "license": "SEE LICENSE IN LICENSE.md",
5
7
  "type": "module",
6
8
  "files": [
7
- "dist"
9
+ "dist",
10
+ "DSL.md"
8
11
  ],
9
12
  "exports": {
10
13
  ".": {
@@ -12,136 +15,51 @@
12
15
  "import": "./dist/index.js",
13
16
  "default": "./dist/index.js"
14
17
  },
15
- "./actions": {
16
- "types": "./dist/actions.d.ts",
17
- "import": "./dist/actions.js",
18
- "default": "./dist/actions.js"
19
- },
20
- "./assert": {
21
- "types": "./dist/assert.d.ts",
22
- "import": "./dist/assert.js",
23
- "default": "./dist/assert.js"
24
- },
25
- "./control": {
26
- "types": "./dist/control.d.ts",
27
- "import": "./dist/control.js",
28
- "default": "./dist/control.js"
29
- },
30
- "./locators": {
31
- "types": "./dist/locators.d.ts",
32
- "import": "./dist/locators.js",
33
- "default": "./dist/locators.js"
34
- },
35
- "./compiler": {
36
- "types": "./dist/compiler.d.ts",
37
- "import": "./dist/compiler.js",
38
- "default": "./dist/compiler.js"
39
- },
40
- "./lockfile": {
41
- "types": "./dist/lockfile.d.ts",
42
- "import": "./dist/lockfile.js",
43
- "default": "./dist/lockfile.js"
44
- },
45
- "./elysia": {
46
- "types": "./dist/elysia.d.ts",
47
- "import": "./dist/elysia.js",
48
- "default": "./dist/elysia.js"
49
- },
50
18
  "./express": {
51
19
  "types": "./dist/express.d.ts",
52
20
  "import": "./dist/express.js",
53
21
  "default": "./dist/express.js"
54
- },
55
- "./fastify": {
56
- "types": "./dist/fastify.d.ts",
57
- "import": "./dist/fastify.js",
58
- "default": "./dist/fastify.js"
59
- },
60
- "./hono": {
61
- "types": "./dist/hono.d.ts",
62
- "import": "./dist/hono.js",
63
- "default": "./dist/hono.js"
64
- },
65
- "./koa": {
66
- "types": "./dist/koa.d.ts",
67
- "import": "./dist/koa.js",
68
- "default": "./dist/koa.js"
69
- },
70
- "./nestjs": {
71
- "types": "./dist/nestjs.d.ts",
72
- "import": "./dist/nestjs.js",
73
- "default": "./dist/nestjs.js"
74
- },
75
- "./nextjs": {
76
- "types": "./dist/nextjs.d.ts",
77
- "import": "./dist/nextjs.js",
78
- "default": "./dist/nextjs.js"
79
22
  }
80
23
  },
81
24
  "dependencies": {
25
+ "neverthrow": "^8.2.0",
82
26
  "standardwebhooks": "^1.0.0",
83
- "zod": "^4.3.6"
84
- },
85
- "devDependencies": {
86
- "@nestjs/common": "^10.0.0",
87
- "@nestjs/core": "^10.0.0",
88
- "@types/express": "^5.0.2",
89
- "@types/koa": "^2.15.0",
90
- "@types/node": "catalog:",
91
- "elysia": "^1.0.0",
92
- "eslint": "catalog:",
93
- "express": "^5.1.0",
94
- "fastify": "^5.3.3",
95
- "hono": "^4.0.0",
96
- "koa": "^2.15.0",
97
- "reflect-metadata": "^0.2.0",
98
- "rxjs": "^7.8.0",
99
- "tsup": "^8.5.1",
100
- "typescript": "catalog:",
101
- "vitest": "^4.1.4",
102
- "@ripplo/eslint-config": "0.0.0",
103
- "@ripplo/spec": "^0.0.0"
27
+ "zod": "4.3.6"
104
28
  },
105
29
  "peerDependencies": {
106
- "@nestjs/common": "^10.0.0 || ^11.0.0",
107
- "@nestjs/core": "^10.0.0 || ^11.0.0",
108
- "dotenv": "^16.0.0 || ^17.0.0",
109
- "elysia": "^1.0.0",
110
- "express": "^4.0.0 || ^5.0.0",
111
- "fastify": "^5.0.0",
112
- "hono": "^4.0.0",
113
- "koa": "^2.0.0 || ^3.0.0"
30
+ "express": "^4.0.0 || ^5.0.0"
114
31
  },
115
32
  "peerDependenciesMeta": {
116
- "@nestjs/common": {
117
- "optional": true
118
- },
119
- "@nestjs/core": {
120
- "optional": true
121
- },
122
- "dotenv": {
123
- "optional": true
124
- },
125
- "elysia": {
126
- "optional": true
127
- },
128
33
  "express": {
129
34
  "optional": true
130
- },
131
- "fastify": {
132
- "optional": true
133
- },
134
- "hono": {
135
- "optional": true
136
- },
137
- "koa": {
138
- "optional": true
139
35
  }
140
36
  },
37
+ "devDependencies": {
38
+ "@types/express": "^5.0.0",
39
+ "@types/node": "^22.15.3",
40
+ "eslint": "^9.39.1",
41
+ "eslint-plugin-neverthrow": "^1.1.4",
42
+ "express": "^5.1.0",
43
+ "tsup": "^8.5.1",
44
+ "typescript": "^5.9.3",
45
+ "vitest": "^4.1.4",
46
+ "@ripplo/eslint-config": "0.0.0",
47
+ "@ripplo/spec": "^0.0.0"
48
+ },
141
49
  "scripts": {
142
50
  "build": "tsup",
143
51
  "check-types": "tsc --noEmit",
144
52
  "lint": "eslint src",
145
53
  "test": "vitest run"
54
+ },
55
+ "main": "./dist/index.js",
56
+ "module": "./dist/index.js",
57
+ "types": "./dist/index.d.ts",
58
+ "typesVersions": {
59
+ "*": {
60
+ "express": [
61
+ "./dist/express.d.ts"
62
+ ]
63
+ }
146
64
  }
147
65
  }
package/dist/actions.d.ts DELETED
@@ -1,260 +0,0 @@
1
- import { Variable, StaticStringRef, VariableRef } from './control.js';
2
- import { U as UnlabeledStep } from './step-De52hTLd.js';
3
- import { CheckLocator, InputLocator, AnyLocator, SelectLocator } from './locators.js';
4
- import '@ripplo/spec';
5
-
6
- declare class Fixture {
7
- readonly kind: "fixture";
8
- readonly name: string;
9
- constructor(name: string);
10
- }
11
- declare function fixture(name: string): Fixture;
12
- declare function isFixture(value: unknown): value is Fixture;
13
-
14
- type StringOrVariable = string | Variable<string>;
15
- declare function navigate(url: string): UnlabeledStep<{
16
- type: "goto";
17
- url: {
18
- type: "static";
19
- value: string;
20
- };
21
- }>;
22
- interface StepOptions {
23
- readonly modifier?: "Alt" | "Control" | "Meta" | "Shift";
24
- readonly uiOnly?: boolean;
25
- }
26
- declare function click(locator: AnyLocator, options?: StepOptions): UnlabeledStep<{
27
- locator: {
28
- by: "testId";
29
- value: string;
30
- } | {
31
- by: "role";
32
- role: string;
33
- name?: string | undefined;
34
- };
35
- modifier: "Alt" | "Control" | "Meta" | "Shift" | undefined;
36
- type: "click";
37
- uiOnly: boolean | undefined;
38
- }>;
39
- declare function fill(locator: InputLocator, value: StringOrVariable): UnlabeledStep<{
40
- locator: {
41
- by: "testId";
42
- value: string;
43
- } | {
44
- by: "role";
45
- role: string;
46
- name?: string | undefined;
47
- };
48
- type: "fill";
49
- value: StaticStringRef | VariableRef;
50
- }>;
51
- declare function select(locator: SelectLocator, value: StringOrVariable): UnlabeledStep<{
52
- locator: {
53
- by: "testId";
54
- value: string;
55
- } | {
56
- by: "role";
57
- role: string;
58
- name?: string | undefined;
59
- };
60
- type: "select";
61
- value: StaticStringRef | VariableRef;
62
- }>;
63
- declare function check(locator: CheckLocator): UnlabeledStep<{
64
- locator: {
65
- by: "testId";
66
- value: string;
67
- } | {
68
- by: "role";
69
- role: string;
70
- name?: string | undefined;
71
- };
72
- type: "check";
73
- }>;
74
- declare function uncheck(locator: CheckLocator): UnlabeledStep<{
75
- locator: {
76
- by: "testId";
77
- value: string;
78
- } | {
79
- by: "role";
80
- role: string;
81
- name?: string | undefined;
82
- };
83
- type: "uncheck";
84
- }>;
85
- declare function hover(locator: AnyLocator): UnlabeledStep<{
86
- locator: {
87
- by: "testId";
88
- value: string;
89
- } | {
90
- by: "role";
91
- role: string;
92
- name?: string | undefined;
93
- };
94
- type: "hover";
95
- }>;
96
- declare function press(key: string): UnlabeledStep<{
97
- key: string;
98
- type: "press";
99
- }>;
100
- declare function upload(locator: AnyLocator, files: Fixture | ReadonlyArray<Fixture>, options?: StepOptions): UnlabeledStep<{
101
- files: string[];
102
- locator: {
103
- by: "testId";
104
- value: string;
105
- } | {
106
- by: "role";
107
- role: string;
108
- name?: string | undefined;
109
- };
110
- type: "upload";
111
- uiOnly: boolean | undefined;
112
- }>;
113
- declare function dblclick(locator: AnyLocator): UnlabeledStep<{
114
- locator: {
115
- by: "testId";
116
- value: string;
117
- } | {
118
- by: "role";
119
- role: string;
120
- name?: string | undefined;
121
- };
122
- type: "dblclick";
123
- }>;
124
- declare function focus(locator: AnyLocator): UnlabeledStep<{
125
- locator: {
126
- by: "testId";
127
- value: string;
128
- } | {
129
- by: "role";
130
- role: string;
131
- name?: string | undefined;
132
- };
133
- type: "focus";
134
- }>;
135
- declare function clear(locator: InputLocator): UnlabeledStep<{
136
- locator: {
137
- by: "testId";
138
- value: string;
139
- } | {
140
- by: "role";
141
- role: string;
142
- name?: string | undefined;
143
- };
144
- type: "clear";
145
- }>;
146
- declare function typeText(locator: InputLocator, value: StringOrVariable): UnlabeledStep<{
147
- locator: {
148
- by: "testId";
149
- value: string;
150
- } | {
151
- by: "role";
152
- role: string;
153
- name?: string | undefined;
154
- };
155
- type: "type";
156
- value: StaticStringRef | VariableRef;
157
- }>;
158
- declare function rightClick(locator: AnyLocator): UnlabeledStep<{
159
- locator: {
160
- by: "testId";
161
- value: string;
162
- } | {
163
- by: "role";
164
- role: string;
165
- name?: string | undefined;
166
- };
167
- type: "rightClick";
168
- }>;
169
- declare function scrollIntoView(locator: AnyLocator): UnlabeledStep<{
170
- locator: {
171
- by: "testId";
172
- value: string;
173
- } | {
174
- by: "role";
175
- role: string;
176
- name?: string | undefined;
177
- };
178
- type: "scrollIntoView";
179
- }>;
180
- declare function drag(source: AnyLocator, target: AnyLocator): UnlabeledStep<{
181
- source: {
182
- by: "testId";
183
- value: string;
184
- } | {
185
- by: "role";
186
- role: string;
187
- name?: string | undefined;
188
- };
189
- target: {
190
- by: "testId";
191
- value: string;
192
- } | {
193
- by: "role";
194
- role: string;
195
- name?: string | undefined;
196
- };
197
- type: "drag";
198
- }>;
199
- interface HandleDialogOptions {
200
- readonly action: "accept" | "dismiss";
201
- readonly promptText: string | undefined;
202
- readonly uiOnly?: boolean;
203
- }
204
- /**
205
- * Register a one-shot listener for the next native dialog (`alert`, `confirm`,
206
- * `prompt`). Pure client-side — the backend mutation, if any, comes from the
207
- * triggering action; observer assertions belong on that step, not here.
208
- */
209
- declare function handleDialog({ action, promptText, uiOnly }: HandleDialogOptions): UnlabeledStep<{
210
- action: "accept" | "dismiss";
211
- promptText: string | undefined;
212
- type: "handleDialog";
213
- uiOnly: boolean | undefined;
214
- }>;
215
- interface ClipboardOptions {
216
- readonly action: "read" | "write";
217
- readonly target: Variable<string> | undefined;
218
- readonly value: StringOrVariable | undefined;
219
- }
220
- /**
221
- * Read from or write to the browser clipboard. Use when a flow depends on
222
- * copy/paste (share links, invite tokens) — pair `write` to seed the
223
- * clipboard before a paste action, or `read` into a `variable()` to assert
224
- * what the app copied.
225
- */
226
- declare function clipboard({ action, target, value }: ClipboardOptions): UnlabeledStep<{
227
- action: "read" | "write";
228
- type: "clipboard";
229
- value: StaticStringRef | VariableRef | undefined;
230
- variable: string | undefined;
231
- }>;
232
- interface SetPermissionOptions {
233
- readonly permission: string;
234
- readonly state: "granted" | "prompt";
235
- }
236
- /**
237
- * Pre-answer a browser permission prompt (geolocation, camera, notifications,
238
- * clipboard-read, etc.) so the test doesn't stall on the native dialog.
239
- */
240
- declare function setPermission({ permission, state }: SetPermissionOptions): UnlabeledStep<{
241
- permission: string;
242
- state: "granted" | "prompt";
243
- type: "setPermission";
244
- }>;
245
- interface SetViewportOptions {
246
- readonly height: number;
247
- readonly width: number;
248
- }
249
- /**
250
- * Resize the browser viewport mid-test. Use to cover responsive breakpoints
251
- * (mobile nav, collapsed sidebars) within the same flow rather than
252
- * duplicating the test per size.
253
- */
254
- declare function setViewport({ height, width }: SetViewportOptions): UnlabeledStep<{
255
- height: number;
256
- type: "setViewport";
257
- width: number;
258
- }>;
259
-
260
- export { Fixture, check, clear, click, clipboard, dblclick, drag, fill, fixture, focus, handleDialog, hover, isFixture, navigate, press, rightClick, scrollIntoView, select, setPermission, setViewport, typeText, uncheck, upload };
package/dist/actions.js DELETED
@@ -1,177 +0,0 @@
1
- import {
2
- readVariable,
3
- toSpecLocator,
4
- toStringValueRef
5
- } from "./chunk-2YLI7VD4.js";
6
- import "./chunk-DCJBLS2U.js";
7
- import {
8
- createStep
9
- } from "./chunk-MGATMMCZ.js";
10
- import "./chunk-4MGIQFAJ.js";
11
-
12
- // src/steps/fixture.ts
13
- var Fixture = class {
14
- kind = "fixture";
15
- name;
16
- constructor(name) {
17
- const raw = name;
18
- if (typeof raw !== "string") {
19
- throw new TypeError(
20
- `fixture(name) requires a string name \u2014 got ${raw == null ? String(raw) : typeof raw}`
21
- );
22
- }
23
- if (raw.length === 0) {
24
- throw new Error("fixture(name) requires a non-empty name");
25
- }
26
- this.name = raw;
27
- }
28
- };
29
- function fixture(name) {
30
- return new Fixture(name);
31
- }
32
- function isFixture(value) {
33
- return value instanceof Fixture;
34
- }
35
-
36
- // src/steps/actions.ts
37
- function navigate(url) {
38
- return createStep({ type: "goto", url: { type: "static", value: url } });
39
- }
40
- function click(locator, options) {
41
- return createStep({
42
- locator: toSpecLocator(locator),
43
- modifier: options?.modifier,
44
- type: "click",
45
- uiOnly: options?.uiOnly
46
- });
47
- }
48
- function fill(locator, value) {
49
- return createStep({
50
- locator: toSpecLocator(locator),
51
- type: "fill",
52
- value: toStringValueRef(value)
53
- });
54
- }
55
- function select(locator, value) {
56
- return createStep({
57
- locator: toSpecLocator(locator),
58
- type: "select",
59
- value: toStringValueRef(value)
60
- });
61
- }
62
- function check(locator) {
63
- return createStep({ locator: toSpecLocator(locator), type: "check" });
64
- }
65
- function uncheck(locator) {
66
- return createStep({ locator: toSpecLocator(locator), type: "uncheck" });
67
- }
68
- function hover(locator) {
69
- return createStep({ locator: toSpecLocator(locator), type: "hover" });
70
- }
71
- function press(key) {
72
- return createStep({ key, type: "press" });
73
- }
74
- function describeFilesArg(files) {
75
- if (typeof files === "string") {
76
- return `string "${files}"`;
77
- }
78
- return typeof files;
79
- }
80
- function normalizeUploadFiles(files) {
81
- if (files instanceof Fixture) {
82
- return [files];
83
- }
84
- if (!Array.isArray(files)) {
85
- throw new TypeError(
86
- `upload() expected a Fixture or an array of Fixtures \u2014 got ${describeFilesArg(files)}. Wrap the filename with fixture(): upload(loc, fixture("file.png"))`
87
- );
88
- }
89
- return files.map((f, i) => {
90
- if (!(f instanceof Fixture)) {
91
- throw new TypeError(
92
- `upload() files[${String(i)}] is not a Fixture \u2014 wrap it with fixture(): upload(loc, fixture("file.png"))`
93
- );
94
- }
95
- return f;
96
- });
97
- }
98
- function upload(locator, files, options) {
99
- const list = normalizeUploadFiles(files);
100
- return createStep({
101
- files: list.map((f) => f.name),
102
- locator: toSpecLocator(locator),
103
- type: "upload",
104
- uiOnly: options?.uiOnly
105
- });
106
- }
107
- function dblclick(locator) {
108
- return createStep({ locator: toSpecLocator(locator), type: "dblclick" });
109
- }
110
- function focus(locator) {
111
- return createStep({ locator: toSpecLocator(locator), type: "focus" });
112
- }
113
- function clear(locator) {
114
- return createStep({ locator: toSpecLocator(locator), type: "clear" });
115
- }
116
- function typeText(locator, value) {
117
- return createStep({
118
- locator: toSpecLocator(locator),
119
- type: "type",
120
- value: toStringValueRef(value)
121
- });
122
- }
123
- function rightClick(locator) {
124
- return createStep({ locator: toSpecLocator(locator), type: "rightClick" });
125
- }
126
- function scrollIntoView(locator) {
127
- return createStep({ locator: toSpecLocator(locator), type: "scrollIntoView" });
128
- }
129
- function drag(source, target) {
130
- return createStep({
131
- source: toSpecLocator(source),
132
- target: toSpecLocator(target),
133
- type: "drag"
134
- });
135
- }
136
- function handleDialog({ action, promptText, uiOnly }) {
137
- return createStep({ action, promptText, type: "handleDialog", uiOnly });
138
- }
139
- function clipboard({ action, target, value }) {
140
- return createStep({
141
- action,
142
- type: "clipboard",
143
- value: value == null ? void 0 : toStringValueRef(value),
144
- variable: target == null ? void 0 : readVariable(target)
145
- });
146
- }
147
- function setPermission({ permission, state }) {
148
- return createStep({ permission, state, type: "setPermission" });
149
- }
150
- function setViewport({ height, width }) {
151
- return createStep({ height, type: "setViewport", width });
152
- }
153
- export {
154
- Fixture,
155
- check,
156
- clear,
157
- click,
158
- clipboard,
159
- dblclick,
160
- drag,
161
- fill,
162
- fixture,
163
- focus,
164
- handleDialog,
165
- hover,
166
- isFixture,
167
- navigate,
168
- press,
169
- rightClick,
170
- scrollIntoView,
171
- select,
172
- setPermission,
173
- setViewport,
174
- typeText,
175
- uncheck,
176
- upload
177
- };