/// import type { AnyExtensionTarget, ApiForTarget, EventMapForTarget } from './targets'; import { type Navigation } from './navigation'; export type { AnyExtensionTarget, ApiForTarget } from './targets'; export { createNavigationHistoryEntry } from './navigation'; export type { Navigation, NavigationHistoryEntry, NavigationNavigateOptions, } from './navigation'; /** * Makes all properties in the API deeply mutable so tests can * override any value through the `extension.shopify` proxy: * * extension.shopify.cart.current.value = createPosCart({lineItems: [...]}); * extension.shopify.i18n.translate = (key) => myTranslations[key]; */ type Mutable = T extends (...args: any[]) => any ? T : T extends object ? { -readonly [K in keyof T]: Mutable; } : T; /** * `Symbol.dispose` for runtimes that support it, with a polyfill * fallback so the library works on older Node versions too. */ export declare const SymbolDispose: typeof Symbol.dispose; /** * Members shared by both {@link ExtensionHarness} (returned by * `getExtension`) and {@link DisposableExtensionHarness} (returned * by `setUpExtension`). */ interface BaseExtensionHarness { /** * Imports and executes the extension module's default export, * rendering the extension into `document.body`. */ render(): Promise; /** * A mock `shopify` global, typed correctly for the target under test. * * You can mutate any property. Example: * * ```ts * extension.shopify.cart.current.value = { lineItems: [...] }; * ``` */ shopify: Mutable>; /** * A mock `fetch()` function installed as `globalThis.fetch` during * `setUp()`. * * Override it with a mock to control responses: * * ```ts * extension.fetch = vi.fn().mockResolvedValue( * new Response(JSON.stringify({ ok: true })), * ); * ``` */ fetch: typeof globalThis.fetch; /** * A mock `navigation` object installed as `globalThis.navigation` * during `setUp()`. * * Override its methods with mocks to control navigation behaviour: * * ```ts * import { createNavigationHistoryEntry } from '@shopify/ui-extensions-tester'; * extension.navigation.navigate = vi.fn(); * extension.navigation.currentEntry = * createNavigationHistoryEntry({ url: '/cart' }); * ``` */ navigation: Navigation; /** * Fires a host event at every listener registered via * `shopify.addEventListener(name, listener)`. * * Matches the `shopify.addEventListener` contract: listener return values * are ignored, and thrown errors are caught per-listener so one bad * listener doesn't block the others. * * Pass the same payload shape that the host dispatches at runtime: * * ```ts * shopify.addEventListener('transactioncomplete', (event) => { ... }); * * extension.dispatch('transactioncomplete', { * transactionType: 'Sale', * orderId: 1, * grandTotal: { amount: 10, currency: 'USD' }, * // ... * }); * ``` */ dispatch>(type: K, event: EventMapForTarget[K]): void; } /** * Returned by `getExtension`. The caller is responsible for calling * `setUp()` before each test and `tearDown()` after. */ interface ExtensionHarness extends BaseExtensionHarness { /** * Sets up an extension environment for testing. * * For example, it creates a mock `shopify` global with some defaults. */ setUp(): void; /** * Tears down the extension environment. * * For example, it resets the `shopify` global and clears `document.body`. */ tearDown(): void; } /** * Returned by `setUpExtension`. Already set up — tears down * automatically via `Symbol.dispose` (the `using` keyword): * * ```ts * using extension = setUpExtension('purchase.checkout.block.render'); * ``` */ interface DisposableExtensionHarness extends BaseExtensionHarness { [Symbol.dispose](): void; } /** * Returns an extension test harness for the given target. * * It reads `shopify.extension.toml`, finds the module for the given target, * and provides helpers to mock the environment and render the extension. * * It locates `shopify.extension.toml` by walking up from the calling * test file's directory, and falls back to searching `extensions/` * under the current working directory. * * @param target - The extension target to mock. * @param options - Optional configuration. * @param options.configSearchDir - Directory containing (or a parent of) * `shopify.extension.toml`. Defaults to the calling test file's directory. */ export declare function getExtension(target: T, options?: { configSearchDir?: string; }): ExtensionHarness; /** * Sets up an extension for testing and returns a disposable object * that supports automatic teardown with the `using` keyword: * * ```ts * test('rendering the extension', async () => { * using extension = setUpExtension( * 'purchase.checkout.block.render', * ); * await extension.render(); * // tearDown() is called automatically at the end of the block * }); * ``` * * @param target - The extension target to mock. * @param options - Optional configuration (same as {@link getExtension}). */ export declare function setUpExtension(target: T, options?: { configSearchDir?: string; }): DisposableExtensionHarness; //# sourceMappingURL=index.d.ts.map