@-xun/test-mock-import
Version:
A generic testing utility that wraps require to ensure imports are performed without caching
57 lines • 2.31 kB
TypeScript
import type { AbsolutePath } from '@-xun/fs';
/**
* A helper type that reduces an object type to its `default` property, if such
* a property exists, or returns it as-is if it does not.
*/
export type AsDefault<T> = T extends {
default: unknown;
} ? T['default'] : T;
/**
* @see {@link isolatedImport}
*/
export type IsolatedImportOptions = {
/**
* By default, if `module.__esModule === true` and the only other property of
* `module.exports` is `"default"`, then said `"default"` export will be
* returned instead of a module object. Use `reduceToDefault` to override this
* behavior in either direction.
*
* @default undefined
*/
reduceToDefault?: boolean | undefined;
};
/**
* Performs a CJS module import (via `require`) as if it were being imported for
* the first time.
*
* Note that this function breaks the "require caching" expectation of Node.js
* modules. Problems can arise, for example, when closing an app-wide database
* connection in your test cleanup phase and expecting it to close for the
* isolated module too. In this case, the isolated module has its own isolated
* "app-wide" connection that would not actually be closed and could cause your
* test to hang unexpectedly, even when all tests pass.
*/
export declare function isolatedImport<Module>(
/**
* Specifier or absolute path to the module under test. Module resolution is
* handled by `require`, therefore the specifier, if a filesystem path, should
* never be relative and must always use unix-style separators (i.e. `/`).
*/
specifier: AbsolutePath | string, options?: IsolatedImportOptions): Module;
/**
* Returns a function that, when invoked, performs a CJS module import (via
* `require`) as if it were being imported for the first time. Also awaits the
* import result and protects the caller from any calls to `process.exit` from
* the imported module.
*
* Use `expectedExitCode` when the import is expected to terminate with a
* specific exit code.
*
* @see {@link isolatedImport}
*/
export declare function protectedImportFactory<Module>(...[specifier, factoryOptions]: Parameters<typeof isolatedImport<Module>>): <LocalModule = Module>({
expectedExitCode,
reduceToDefault
}?: IsolatedImportOptions & {
expectedExitCode?: number;
}) => Promise<LocalModule>;