twd-js 1.1.2 → 1.2.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.
Files changed (51) hide show
  1. package/README.md +20 -24
  2. package/dist/_commonjsHelpers-C6fGbg64.mjs +6 -0
  3. package/dist/_commonjsHelpers-DwGv2jUC.js +1 -0
  4. package/dist/index.cjs.js +39 -44
  5. package/dist/index.d.ts +433 -7
  6. package/dist/index.es.js +4670 -4917
  7. package/dist/jsx-runtime-CtyxV31n.mjs +276 -0
  8. package/dist/jsx-runtime-DN5DOl8k.js +6 -0
  9. package/dist/mock-sw.js +1 -1
  10. package/dist/runner-ci.cjs.js +1 -1
  11. package/dist/runner-ci.d.ts +28 -12
  12. package/dist/runner-ci.es.js +32 -22
  13. package/dist/runner.cjs.js +1 -1
  14. package/dist/runner.d.ts +55 -41
  15. package/dist/runner.es.js +127 -70
  16. package/dist/ui.cjs.js +1 -0
  17. package/dist/ui.d.ts +10 -0
  18. package/dist/ui.es.js +11 -0
  19. package/dist/vite-plugin.d.ts +21 -1
  20. package/package.json +15 -10
  21. package/dist/asserts/index.d.ts +0 -2
  22. package/dist/commands/mockBridge.d.ts +0 -73
  23. package/dist/commands/url.d.ts +0 -33
  24. package/dist/commands/visit.d.ts +0 -1
  25. package/dist/constants/version.d.ts +0 -1
  26. package/dist/global.d.ts +0 -8
  27. package/dist/initializers/initSidebar.d.ts +0 -22
  28. package/dist/initializers/initTests.d.ts +0 -31
  29. package/dist/plugin/removeMockServiceWorker.d.ts +0 -18
  30. package/dist/proxies/domMessage.d.ts +0 -1
  31. package/dist/proxies/eventsMessage.d.ts +0 -1
  32. package/dist/proxies/screenDom.d.ts +0 -5
  33. package/dist/proxies/userEvent.d.ts +0 -4
  34. package/dist/twd-types.d.ts +0 -106
  35. package/dist/twd.d.ts +0 -178
  36. package/dist/ui/ClosedSidebar.d.ts +0 -6
  37. package/dist/ui/Icons/BaseIcon.d.ts +0 -7
  38. package/dist/ui/Icons/ChevronDown.d.ts +0 -2
  39. package/dist/ui/Icons/ChevronRight.d.ts +0 -2
  40. package/dist/ui/Icons/Loader.d.ts +0 -2
  41. package/dist/ui/Icons/MockRequestIcon.d.ts +0 -2
  42. package/dist/ui/Icons/Play.d.ts +0 -2
  43. package/dist/ui/MockRulesButton.d.ts +0 -1
  44. package/dist/ui/TWDSidebar.d.ts +0 -16
  45. package/dist/ui/TestList.d.ts +0 -17
  46. package/dist/ui/TestListItem.d.ts +0 -39
  47. package/dist/ui/buildTreeFromHandlers.d.ts +0 -14
  48. package/dist/ui/hooks/useLayout.d.ts +0 -6
  49. package/dist/utils/assertionMessage.d.ts +0 -1
  50. package/dist/utils/log.d.ts +0 -1
  51. package/dist/utils/wait.d.ts +0 -3
package/dist/index.d.ts CHANGED
@@ -1,7 +1,433 @@
1
- export { twd } from './twd';
2
- export { TWDSidebar } from './ui/TWDSidebar';
3
- export { initTests } from './initializers/initTests';
4
- export { expect } from 'chai';
5
- export { userEvent } from './proxies/userEvent';
6
- export { screenDom, configureScreenDom } from './proxies/screenDom';
7
- export type { Chai };
1
+ import { configure } from '@testing-library/dom';
2
+ import { default as default_2 } from '@testing-library/user-event';
3
+ import { expect } from 'chai';
4
+ import { JSX } from 'react/jsx-runtime';
5
+ import { screen as screen_2 } from '@testing-library/dom';
6
+
7
+ /**
8
+ * All assertion names, including negated ones.
9
+ */
10
+ declare type AnyAssertion = Negatable_2<AssertionName>;
11
+
12
+ /**
13
+ * All assertion names, including negated ones.
14
+ */
15
+ declare type AnyURLAssertion = Negatable<URLAssertionName>;
16
+
17
+ /**
18
+ * Maps assertion name to its argument tuple.
19
+ */
20
+ declare type ArgsFor<A extends AnyAssertion> = A extends `not.${infer Base extends AssertionName}` ? AssertionArgs[Base] : A extends AssertionName ? AssertionArgs[A] : never;
21
+
22
+ /**
23
+ * Argument types for each assertion.
24
+ */
25
+ declare type AssertionArgs = {
26
+ "have.text": [expected: string];
27
+ "contain.text": [expected: string];
28
+ "be.empty": [];
29
+ "have.attr": [attr: string, value: string];
30
+ "have.value": [value: string];
31
+ "be.disabled": [];
32
+ "be.enabled": [];
33
+ "be.checked": [];
34
+ "be.selected": [];
35
+ "be.focused": [];
36
+ "be.visible": [];
37
+ "have.class": [className: string];
38
+ };
39
+
40
+ /**
41
+ * Types and interfaces for the TWD testing library.
42
+ *
43
+ * @module twd-types
44
+ */
45
+ /**
46
+ * All supported assertion names for the `should` function.
47
+ *
48
+ * @example
49
+ * api.should("have.text", "Hello");
50
+ * api.should("be.empty");
51
+ */
52
+ declare type AssertionName = "have.text" | "contain.text" | "be.empty" | "have.attr" | "have.value" | "be.disabled" | "be.enabled" | "be.checked" | "be.selected" | "be.focused" | "be.visible" | "have.class";
53
+
54
+ export declare const configureScreenDom: typeof configure;
55
+
56
+ export { expect }
57
+
58
+ /**
59
+ * Initialize Vite test loading.
60
+ * @param testModules - The test modules to load.
61
+ * @param component - The React component to render the sidebar.
62
+ * @param createRoot - Function to create a React root.
63
+ * @example
64
+ * ```ts
65
+ * if (import.meta.env.DEV) {
66
+ * const testModules = import.meta.glob("./example.twd.test.ts");
67
+ * const { initTests, TWDSidebar } = await import('twd-js');
68
+ * await initTests(testModules, <TWDSidebar open={true} position="left" />, createRoot);
69
+ * }
70
+ * ```
71
+ */
72
+ export declare const initTests: (testModules: TestModule, Component: React.ReactNode, createRoot: (el: HTMLElement) => {
73
+ render: (el: React.ReactNode) => void;
74
+ }) => Promise<void>;
75
+
76
+ /**
77
+ * Negatable assertion names (e.g., 'not.have.text').
78
+ */
79
+ declare type Negatable<T extends string> = T | `not.${T}`;
80
+
81
+ /**
82
+ * Negatable assertion names (e.g., 'not.have.text').
83
+ */
84
+ declare type Negatable_2<T extends string> = T | `not.${T}`;
85
+
86
+ declare interface Options {
87
+ method: string;
88
+ url: string | RegExp;
89
+ response: unknown;
90
+ status?: number;
91
+ responseHeaders?: Record<string, string>;
92
+ urlRegex?: boolean;
93
+ }
94
+
95
+ declare type Rule = {
96
+ method: string;
97
+ url: string | RegExp;
98
+ response: unknown;
99
+ alias: string;
100
+ executed?: boolean;
101
+ request?: any;
102
+ status?: number;
103
+ responseHeaders?: Record<string, string>;
104
+ urlRegex?: boolean;
105
+ };
106
+
107
+ declare type ScreenDom = typeof screen_2;
108
+
109
+ export declare const screenDom: ScreenDom;
110
+
111
+ /**
112
+ * Overloads for the `should` function, for best IntelliSense.
113
+ *
114
+ * @example
115
+ * twd.should("have.text", "Hello");
116
+ * twd.should("be.empty");
117
+ * twd.should("have.class", "active");
118
+ */
119
+ declare type ShouldFn = {
120
+ (name: "have.text", expected: string): TWDElemAPI;
121
+ (name: "not.have.text", expected: string): TWDElemAPI;
122
+ (name: "contain.text", expected: string): TWDElemAPI;
123
+ (name: "not.contain.text", expected: string): TWDElemAPI;
124
+ (name: "be.empty"): TWDElemAPI;
125
+ (name: "not.be.empty"): TWDElemAPI;
126
+ (name: "have.attr", attr: string, value: string): TWDElemAPI;
127
+ (name: "not.have.attr", attr: string, value: string): TWDElemAPI;
128
+ (name: "have.value", value: string): TWDElemAPI;
129
+ (name: "not.have.value", value: string): TWDElemAPI;
130
+ (name: "be.disabled"): TWDElemAPI;
131
+ (name: "not.be.disabled"): TWDElemAPI;
132
+ (name: "be.enabled"): TWDElemAPI;
133
+ (name: "not.be.enabled"): TWDElemAPI;
134
+ (name: "be.checked"): TWDElemAPI;
135
+ (name: "not.be.checked"): TWDElemAPI;
136
+ (name: "be.selected"): TWDElemAPI;
137
+ (name: "not.be.selected"): TWDElemAPI;
138
+ (name: "be.focused"): TWDElemAPI;
139
+ (name: "not.be.focused"): TWDElemAPI;
140
+ (name: "be.visible"): TWDElemAPI;
141
+ (name: "not.be.visible"): TWDElemAPI;
142
+ (name: "have.class", className: string): TWDElemAPI;
143
+ (name: "not.have.class", className: string): TWDElemAPI;
144
+ };
145
+
146
+ /**
147
+ * A record of test module paths to their loader functions.
148
+ * Each function returns a promise that resolves when the module is loaded.
149
+ * This is typically used with Vite's `import.meta.glob` to dynamically import test modules.
150
+ * @example
151
+ * ```ts
152
+ * const testModules = {
153
+ * './test1.twd.test.ts': () => import('./test1.twd.test.ts'),
154
+ * './test2.twd.test.ts': () => import('./test2.twd.test.ts'),
155
+ * };
156
+ * ```
157
+ */
158
+ declare type TestModule = Record<string, () => Promise<unknown>>;
159
+
160
+ /**
161
+ * Mini Cypress-style helpers for DOM testing.
162
+ * @namespace twd
163
+ */
164
+ export declare const twd: TWDAPI;
165
+
166
+ declare interface TWDAPI {
167
+ /**
168
+ * Finds an element by selector and returns the TWD API for it.
169
+ * @param selector CSS selector
170
+ * @returns {Promise<TWDElemAPI>} The TWD API for the element
171
+ *
172
+ * @example
173
+ * ```ts
174
+ * const btn = await twd.get("button");
175
+ *
176
+ * ```
177
+ *
178
+ */
179
+ get: (selector: string) => Promise<TWDElemAPI>;
180
+ /**
181
+ * Sets the value of an input element and dispatches an input event. We recommend using this only for range, color, time inputs.
182
+ * @param el The input element
183
+ * @param value The value to set
184
+ *
185
+ * @example
186
+ * ```ts
187
+ * const input = await twd.get("input[type='time']");
188
+ * twd.setInputValue(input.el, "13:30");
189
+ *
190
+ * ```
191
+ */
192
+ setInputValue: (el: Element, value: string) => void;
193
+ /**
194
+ * Finds multiple elements by selector and returns an array of TWD APIs for them.
195
+ * @param selector CSS selector
196
+ * @returns {Promise<TWDElemAPI[]>} Array of TWD APIs for the elements
197
+ *
198
+ * @example
199
+ * ```ts
200
+ * const items = await twd.getAll(".item");
201
+ * items.at(0).should("be.visible");
202
+ * items.at(1).should("contain.text", "Hello");
203
+ * expect(items).to.have.length(3);
204
+ * ```
205
+ */
206
+ getAll: (selector: string) => Promise<TWDElemAPI[]>;
207
+ /**
208
+ * Simulates visiting a URL (SPA navigation).
209
+ * @param url The URL to visit
210
+ * @param [reload] Whether to force a reload even if already on the URL (optional)
211
+ *
212
+ * @example
213
+ * ```ts
214
+ * twd.visit("/contact");
215
+ * // visit with reload
216
+ * twd.visit("/contact", true);
217
+ * ```
218
+ */
219
+ visit: (url: string, reload?: boolean) => Promise<void>;
220
+ /**
221
+ * Mock a network request.
222
+ *
223
+ * @param alias Identifier for the mock rule. Useful for `waitFor()`.
224
+ * @param options Options to configure the mock:
225
+ * - `method`: HTTP method ("GET", "POST", …)
226
+ * - `url`: URL string or RegExp to match
227
+ * - `response`: Body of the mocked response
228
+ * - `status`: (optional) HTTP status code (default: 200)
229
+ * - `headers`: (optional) Response headers
230
+ *
231
+ * @example
232
+ * ```ts
233
+ * mockRequest("getUser", {
234
+ * method: "GET",
235
+ * url: /\/api\/user\/\d+/,
236
+ * response: { id: 1, name: "Kevin" },
237
+ * status: 200,
238
+ * headers: { "x-mock": "true" }
239
+ * });
240
+ * ```
241
+ */
242
+ mockRequest: (alias: string, options: Options) => Promise<void>;
243
+ /**
244
+ * Wait for a mocked request to be made.
245
+ * @param alias The alias of the mock rule to wait for
246
+ * @return The matched rule (with body if applicable)
247
+ *
248
+ * @example
249
+ * ```ts
250
+ * const rule = await twd.waitFor("aliasId");
251
+ * console.log(rule.body);
252
+ *
253
+ * ```
254
+ */
255
+ waitForRequest: (alias: string) => Promise<Rule>;
256
+ /**
257
+ * wait for a list of mocked requests to be made.
258
+ * @param aliases The aliases of the mock rules to wait for
259
+ * @returns The matched rules (with body if applicable)
260
+ * @example
261
+ * ```ts
262
+ * const rules = await waitForRequests(["getUser", "postComment"]);
263
+ * ```
264
+ */
265
+ waitForRequests: (aliases: string[]) => Promise<Rule[]>;
266
+ /**
267
+ * URL-related assertions.
268
+ *
269
+ * @example
270
+ * ```ts
271
+ * twd.url().should("eq", "http://localhost:3000/contact");
272
+ * twd.url().should("contain.url", "/contact");
273
+ *
274
+ * ```
275
+ */
276
+ url: () => URLCommandAPI;
277
+ /**
278
+ * Initializes request mocking (registers the service worker).
279
+ * Must be called before using `twd.mockRequest()`.
280
+ *
281
+ * @example
282
+ * ```ts
283
+ * await twd.initRequestMocking();
284
+ *
285
+ * ```
286
+ */
287
+ initRequestMocking: () => Promise<void>;
288
+ /**
289
+ * Clears all request mock rules.
290
+ *
291
+ * @example
292
+ * ```ts
293
+ * twd.clearRequestMockRules();
294
+ *
295
+ * ```
296
+ */
297
+ clearRequestMockRules: () => void;
298
+ /**
299
+ * Gets all current request mock rules.
300
+ *
301
+ * @example
302
+ * ```ts
303
+ * const rules = twd.getRequestMockRules();
304
+ * console.log(rules);
305
+ * ```
306
+ */
307
+ getRequestMockRules: () => Rule[];
308
+ /**
309
+ * Waits for a specified time.
310
+ * @param time Time in milliseconds to wait
311
+ * @returns A promise that resolves after the specified time
312
+ * @example
313
+ * ```ts
314
+ * await twd.wait(500); // wait for 500ms
315
+ * ```
316
+ */
317
+ wait: (time: number) => Promise<void>;
318
+ /**
319
+ * Asserts something about the element.
320
+ * @param el The element to assert on
321
+ * @param name The name of the assertion.
322
+ * @param args Arguments for the assertion.
323
+ * @returns The same API for chaining.
324
+ * @example
325
+ * ```ts
326
+ * const button = await twd.get("button");
327
+ * const text = screenDom.getByText("Hello");
328
+ * twd.should(button.el, "have.text", "Hello");
329
+ * twd.should(text, "be.empty");
330
+ * twd.should(button.el, "have.class", "active");
331
+ * ```
332
+ */
333
+ should: (el: Element, name: AnyAssertion, ...args: ArgsFor<AnyAssertion>) => void;
334
+ /**
335
+ * Mock a component.
336
+ * @param name The name of the component to mock
337
+ * @param component The component to mock
338
+ * @returns The mocked component
339
+ * @example
340
+ * ```ts
341
+ * twd.mockComponent("Button", Button);
342
+ * ```
343
+ */
344
+ mockComponent: (name: string, component: React.ComponentType<any>) => void;
345
+ /**
346
+ * Clears all component mocks.
347
+ *
348
+ * @example
349
+ * ```ts
350
+ * twd.clearComponentMocks();
351
+ * ```
352
+ */
353
+ clearComponentMocks: () => void;
354
+ /**
355
+ * Asserts that an element does not exist in the DOM.
356
+ * @param selector CSS selector of the element to check
357
+ * @returns A promise that resolves if the element does not exist, or rejects if it does
358
+ *
359
+ * @example
360
+ * ```ts
361
+ * await twd.notExists(".non-existent");
362
+ * ```
363
+ */
364
+ notExists: (selector: string) => Promise<void>;
365
+ }
366
+
367
+ /**
368
+ * The main API returned by `twd.get()`.
369
+ *
370
+ * @example
371
+ * ```ts
372
+ * const btn = await twd.get("button");
373
+ * btn.should("have.text", "Clicked").click();
374
+ *
375
+ * ```
376
+ *
377
+ */
378
+ declare interface TWDElemAPI {
379
+ /** The underlying DOM element. */
380
+ el: Element;
381
+ /**
382
+ * Asserts something about the element.
383
+ * @param name The name of the assertion.
384
+ * @param args Arguments for the assertion.
385
+ * @returns The same API for chaining.
386
+ *
387
+ * @example
388
+ * ```ts
389
+ * const btn = await twd.get("button");
390
+ * btn.should("have.text", "Click me").should("not.be.disabled");
391
+ *
392
+ * ```
393
+ *
394
+ */
395
+ should: ShouldFn;
396
+ }
397
+
398
+ export declare const TWDSidebar: ({ open, position }: TWDSidebarProps) => JSX.Element;
399
+
400
+ declare interface TWDSidebarProps {
401
+ /**
402
+ * Whether the sidebar is open by default
403
+ */
404
+ open: boolean;
405
+ /**
406
+ * Sidebar position
407
+ * - left: Sidebar on the left side (default)
408
+ * - right: Sidebar on the right side
409
+ *
410
+ * @default "left"
411
+ */
412
+ position?: "left" | "right";
413
+ }
414
+
415
+ /**
416
+ * All supported assertion names for the `should` function in url command
417
+ *
418
+ * @example
419
+ * twd.url().should("contain.url", "/new-page");
420
+ * twd.url().should("eq", "http://localhost:3000/new-page");
421
+ */
422
+ declare type URLAssertionName = "eq" | "contain.url";
423
+
424
+ declare type URLCommandAPI = {
425
+ location: Location;
426
+ should: (name: AnyURLAssertion, value: string) => URLCommandAPI | string;
427
+ };
428
+
429
+ declare type UserEvent = typeof default_2;
430
+
431
+ export declare const userEvent: UserEvent;
432
+
433
+ export { }