Repository: shelfio/jest-mongodb Branch: master Commit: faeda349606c Files: 30 Total size: 25.2 KB Directory structure: gitextract_b8k417lc/ ├── .editorconfig ├── .gitattributes ├── .gitignore ├── .husky/ │ ├── _/ │ │ └── husky.sh │ ├── post-commit │ └── pre-commit ├── .npmrc ├── .nvmrc ├── CHANGELOG.md ├── eslint.config.mjs ├── jest-mongodb-config-repl.js ├── jest-mongodb-config.js ├── jest-preset.js ├── license ├── package.json ├── readme.md ├── renovate.json ├── src/ │ ├── environment.ts │ ├── helpers.ts │ ├── index.ts │ ├── setup.ts │ ├── teardown.ts │ └── types.ts ├── test/ │ ├── helpers-esm-config.test.ts │ ├── mongo-aggregate.test.ts │ ├── mongo-insert.test.ts │ ├── mongo-parallelism.test.ts │ ├── mongo-parallelism2.test.ts │ └── mongo-parallelism3.test.ts └── tsconfig.json ================================================ FILE CONTENTS ================================================ ================================================ FILE: .editorconfig ================================================ root = true [*] end_of_line = lf charset = utf-8 trim_trailing_whitespace = true insert_final_newline = true indent_style = space indent_size = 2 ================================================ FILE: .gitattributes ================================================ * text=auto *.js text eol=lf ================================================ FILE: .gitignore ================================================ .idea/ coverage/ node_modules/ lib/ temp yarn.lock *.log .DS_Store globalConfig.json !.husky/_/husky.sh ================================================ FILE: .husky/_/husky.sh ================================================ #!/bin/sh if [ -z "$husky_skip_init" ]; then debug () { if [ "$HUSKY_DEBUG" = "1" ]; then echo "husky (debug) - $1" fi } readonly hook_name="$(basename "$0")" debug "starting $hook_name..." if [ "$HUSKY" = "0" ]; then debug "HUSKY env variable is set to 0, skipping hook" exit 0 fi if [ -f ~/.huskyrc ]; then debug "sourcing ~/.huskyrc" . ~/.huskyrc fi export readonly husky_skip_init=1 sh -e "$0" "$@" exitCode="$?" if [ $exitCode != 0 ]; then echo "husky - $hook_name hook exited with code $exitCode (error)" fi exit $exitCode fi ================================================ FILE: .husky/post-commit ================================================ #!/bin/sh . "$(dirname "$0")/_/husky.sh" git update-index --again ================================================ FILE: .husky/pre-commit ================================================ #!/bin/sh . "$(dirname "$0")/_/husky.sh" pnpm exec lint-staged ================================================ FILE: .npmrc ================================================ package-lock=false node-linker=hoisted ================================================ FILE: .nvmrc ================================================ 22.15.1 ================================================ FILE: CHANGELOG.md ================================================ # Changelog ## 5.2.1 - Updated dependencies: - debug to v4.4.1 - mongodb-memory-server to v10 - Updated Node.js to v22.15.1 - Refactored isMongoMemoryReplSetOptions to helpers.ts # Breaking Changes ## 5.0.0 - Switched `node` version `18`->`22` ================================================ FILE: eslint.config.mjs ================================================ import rules from '@shelf/eslint-config/typescript.js'; export default [ ...rules, { rules: { '@typescript-eslint/no-var-requires': 'off', }, }, {files: ['**/*.js', '**/*.jsx', '**/*.ts', '**/*.tsx', '**/*.json']}, { ignores: [ '.idea/', '.pnpm-store/', 'coverage/', 'draft.js', 'lib/', 'dist/', 'node_modules/', 'packages/**/tsconfig.types.json', 'packages/**/node_modules/**', 'packages/**/lib/**', 'renovate.json', ], }, ]; ================================================ FILE: jest-mongodb-config-repl.js ================================================ /** @type {import('./src/types').Config} */ module.exports = { mongodbMemoryServerOptions: { binary: { skipMD5: true, }, autoStart: false, instance: {}, replSet: { count: 4, storageEngine: 'wiredTiger', }, }, mongoURLEnvName: 'MONGO_URL', }; ================================================ FILE: jest-mongodb-config.js ================================================ /** @type {import('./src/types').Config} */ module.exports = { mongodbMemoryServerOptions: { binary: { skipMD5: true, }, autoStart: false, instance: {}, }, mongoURLEnvName: 'MONGO_URL', }; ================================================ FILE: jest-preset.js ================================================ // eslint-disable-next-line @typescript-eslint/no-require-imports const preset = require('./lib').default; module.exports = preset; ================================================ FILE: license ================================================ MIT License Copyright (c) Gemshelf Inc. (shelf.io) Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. ================================================ FILE: package.json ================================================ { "name": "@shelf/jest-mongodb", "version": "6.0.2", "description": "Run your tests using Jest & MongoDB in Memory server", "keywords": [ "jest", "jest environment", "jest preset", "mongodb", "mongodb local" ], "repository": "shelfio/jest-mongodb", "license": "MIT", "author": { "name": "Vlad Holubiev", "email": "vlad@shelf.io", "url": "shelf.io" }, "files": [ "jest-preset.js", "lib/" ], "scripts": { "build": "rm -rf lib/ && tsc", "lint": "pnpm run lint:ci --fix", "lint:ci": "eslint . --quiet", "prepack": "pnpm run build", "test": "jest", "test:repl": "MONGO_MEMORY_SERVER_FILE=jest-mongodb-config-repl.js jest", "type-check": "tsc --noEmit", "type-check:watch": "pnpm run type-check --watch" }, "prettier": "@shelf/prettier-config", "jest": { "preset": "./jest-preset.js" }, "dependencies": { "@swc/jest": "0.2.39", "debug": "4.4.1", "mongodb-memory-server": "10.3.0" }, "devDependencies": { "@jest/environment": "30.2.0", "@shelf/eslint-config": "5.4.0", "@shelf/prettier-config": "1.0.0", "@shelf/tsconfig": "0.1.0", "@types/jest": "29.5.14", "@types/node": "22", "eslint": "9.39.1", "husky": "9.1.7", "jest": "29.7.0", "jest-environment-node": "30.2.0", "lint-staged": "16.2.7", "mongodb": "7.0.0", "prettier": "3.6.2", "typescript": "5.9.3" }, "peerDependencies": { "jest-environment-node": "28.x || 29.x || 30.x", "mongodb": "3.x.x || 4.x || 5.x || 6.x || 7.x" }, "engines": { "node": ">=22" }, "publishConfig": { "access": "public" }, "lint-staged": { "*.{html,md,yml}": [ "prettier --write" ], "*.{ts,js,json}": [ "eslint --fix" ] } } ================================================ FILE: readme.md ================================================ # jest-mongodb [![CircleCI](https://circleci.com/gh/shelfio/jest-mongodb/tree/master.svg?style=svg)](https://circleci.com/gh/shelfio/jest-mongodb/tree/master) ![](https://img.shields.io/badge/code_style-prettier-ff69b4.svg) [![npm (scoped)](https://img.shields.io/npm/v/@shelf/jest-mongodb.svg)](https://www.npmjs.com/package/@shelf/jest-mongodb) > Jest preset to run MongoDB memory server ## Usage ### 0. Install ``` $ yarn add @shelf/jest-mongodb --dev ``` Make sure `mongodb` is installed in the project as well, as it's required as a peer dependency. ### 1. Create `jest.config.js` ```js module.exports = { preset: '@shelf/jest-mongodb', }; ``` If you have a custom `jest.config.js` make sure you remove `testEnvironment` property, otherwise it will conflict with the preset. ### 2. Create `jest-mongodb-config.js` See [mongodb-memory-server](https://github.com/nodkz/mongodb-memory-server#available-options) ```js module.exports = { mongodbMemoryServerOptions: { binary: { version: '4.0.3', skipMD5: true, }, autoStart: false, instance: {}, }, }; ``` To use the same database for all tests pass the config like this: ```js module.exports = { mongodbMemoryServerOptions: { binary: { version: '4.0.3', skipMD5: true, }, instance: { dbName: 'jest', }, autoStart: false, }, }; ``` To use separate database for each jest worker pass the `useSharedDBForAllJestWorkers: false` (doesn't create `process.env` variable when using this option): ```js module.exports = { mongodbMemoryServerOptions: { binary: { skipMD5: true, }, autoStart: false, instance: {}, }, useSharedDBForAllJestWorkers: false, }; ``` To use dynamic database name you must pass empty object for instance field: ```js module.exports = { mongodbMemoryServerOptions: { binary: { version: '4.0.3', skipMD5: true, }, instance: {}, autoStart: false, }, }; ``` To use another uri environment variable name you must set mongoURLEnvName field: ```js module.exports = { mongodbMemoryServerOptions: { binary: { version: '4.0.3', skipMD5: true, }, instance: {}, autoStart: false, }, mongoURLEnvName: 'MONGODB_URI', }; ``` To use mongo as a replica set you must add the `replSet` config object and set `count` and `storageEngine` fields: ```js module.exports = { mongodbMemoryServerOptions: { binary: { skipMD5: true, }, autoStart: false, instance: {}, replSet: { count: 3, storageEngine: 'wiredTiger', }, }, }; ``` ### 3. Configure MongoDB client Library sets the `process.env.MONGO_URL` for your convenience, but using of `global.__MONGO_URI__` is preferable as it works with ` useSharedDBForAllJestWorkers: false` ```js const {MongoClient} = require('mongodb'); describe('insert', () => { let connection; let db; beforeAll(async () => { connection = await MongoClient.connect(global.__MONGO_URI__, {}); db = await connection.db(); }); afterAll(async () => { await connection.close(); }); }); ``` ### 4. PROFIT! Write tests ```js it('should insert a doc into collection', async () => { const users = db.collection('users'); const mockUser = {_id: 'some-user-id', name: 'John'}; await users.insertOne(mockUser); const insertedUser = await users.findOne({_id: 'some-user-id'}); expect(insertedUser).toEqual(mockUser); }); ``` Cache MongoDB binary in CI by putting this folder to the list of cached paths: `./node_modules/.cache/mongodb-memory-server/mongodb-binaries` You can enable debug logs by setting environment variable `DEBUG=jest-mongodb:*` #### 5. Clean collections before each test (optional) ```js beforeEach(async () => { await db.collection('COLLECTION_NAME').deleteMany({}); }); ``` See [this issue](https://github.com/shelfio/jest-mongodb/issues/173) for discussion #### 6. Jest watch mode gotcha This package creates the file `globalConfig.json` in the project root, when using jest `--watch` flag, changes to `globalConfig.json` can cause an infinite loop In order to avoid this unwanted behaviour, add `globalConfig` to ignored files in watch mode in the Jest configuation ```js // jest.config.js module.exports = { watchPathIgnorePatterns: ['globalConfig'], }; ``` ## Node 22.12+ and ESM configs Node 22.12 turned on `require()` support for ESM by default. If your config is an `.mjs` file with a default export, `@shelf/jest-mongodb` now imports it automatically (and still supports CommonJS configs). If you prefer the old behavior, you can run Jest with `--no-experimental-require-module`. ## See Also - [jest-dynamodb](https://github.com/shelfio/jest-dynamodb) ## Publish ```sh $ git checkout master $ yarn version $ yarn publish $ git push origin master --tags ``` ## License MIT © [Shelf](https://shelf.io) ================================================ FILE: renovate.json ================================================ { "extends": ["github>shelfio/renovate-config-public"], "labels": ["backend"] } ================================================ FILE: src/environment.ts ================================================ import {join as pathJoin} from 'path'; import {readFileSync} from 'fs'; import {randomUUID} from 'crypto'; import {TestEnvironment} from 'jest-environment-node'; import {MongoMemoryReplSet, MongoMemoryServer} from 'mongodb-memory-server'; import type {EnvironmentContext} from '@jest/environment'; import type {JestEnvironmentConfig} from '@jest/environment'; import {getMongodbMemoryOptions, isMongoMemoryReplSetOptions} from './helpers'; // eslint-disable-next-line @typescript-eslint/no-require-imports const debug = require('debug')('jest-mongodb:environment'); module.exports = class MongoEnvironment extends TestEnvironment { globalConfigPath: string; mongo: MongoMemoryReplSet | MongoMemoryServer; constructor(config: JestEnvironmentConfig, context: EnvironmentContext) { super(config, context); this.globalConfigPath = pathJoin(config.globalConfig.rootDir, 'globalConfig.json'); const options = getMongodbMemoryOptions(config.globalConfig.rootDir); const isReplSet = isMongoMemoryReplSetOptions(options); debug(`isReplSet`, isReplSet); this.mongo = isReplSet ? new MongoMemoryReplSet(options) : new MongoMemoryServer(options); } async setup() { debug('Setup MongoDB Test Environment'); const globalConfig = JSON.parse(readFileSync(this.globalConfigPath, 'utf-8')); if (globalConfig.mongoUri) { this.global.__MONGO_URI__ = globalConfig.mongoUri; } else { await this.mongo.start(); this.global.__MONGO_URI__ = this.mongo.getUri(); } this.global.__MONGO_DB_NAME__ = globalConfig.mongoDBName || randomUUID(); await super.setup(); } async teardown() { debug('Teardown MongoDB Test Environment'); await this.mongo.stop(); await super.teardown(); } // @ts-expect-error - runScript has incompatible type definitions runScript(script) { // @ts-expect-error - parent class method call return super.runScript(script); } }; ================================================ FILE: src/helpers.ts ================================================ import {spawnSync} from 'child_process'; import {resolve} from 'path'; import type {MongoMemoryReplSet, MongoMemoryServer} from 'mongodb-memory-server'; import type {Config} from './types'; type MongoMemoryReplSetOpts = NonNullable[0]>; type MongoMemoryServerOpts = NonNullable[0]>; export function isMongoMemoryReplSetOptions( options?: MongoMemoryReplSetOpts | MongoMemoryServerOpts ): options is MongoMemoryReplSetOpts { return Boolean((options as MongoMemoryReplSetOpts | undefined)?.replSet); } function getConfigFile() { return process.env.MONGO_MEMORY_SERVER_FILE || 'jest-mongodb-config.js'; } const configCache = new Map(); function importConfig(configPath: string): Config | undefined { try { // Node 22.12+ can let `require` load ESM by default. When Jest runs in CJS mode // and the config is `.mjs`, spawn a one-off Node process to import it as ESM // and return the plain JSON payload. const {status, stdout} = spawnSync( process.execPath, [ '--input-type=module', '--eval', [ 'import {pathToFileURL} from "node:url";', `const mod = await import(pathToFileURL(${JSON.stringify(configPath)}).href);`, 'const payload = mod.default ?? mod;', 'console.log(JSON.stringify(payload));', ].join('\n'), ], {encoding: 'utf8'} ); if (status === 0 && stdout.trim()) { return JSON.parse(stdout) as Config; } } catch { // ignore and fall through to undefined } return undefined; } function loadConfig(cwd?: string): Config | undefined { const baseDir = cwd || process.cwd(); if (configCache.has(baseDir)) { return configCache.get(baseDir) ?? undefined; } const configPath = resolve(baseDir, getConfigFile()); try { // eslint-disable-next-line @typescript-eslint/no-require-imports const loadedConfig = require(configPath) as Config | {default?: Config}; if (loadedConfig && typeof (loadedConfig as {default?: Config}).default !== 'undefined') { const config = (loadedConfig as {default?: Config}).default; configCache.set(baseDir, config ?? null); return config; } const config = loadedConfig as Config; configCache.set(baseDir, config ?? null); return config; } catch { const importedConfig = importConfig(configPath); configCache.set(baseDir, importedConfig ?? null); return importedConfig; } } export function getMongodbMemoryOptions( cwd?: string ): MongoMemoryReplSetOpts | MongoMemoryServerOpts | undefined { const config = loadConfig(cwd); if (config?.mongodbMemoryServerOptions) { return config.mongodbMemoryServerOptions; } return { binary: { checkMD5: false, }, instance: {}, }; } export function getMongoURLEnvName(cwd?: string) { const config = loadConfig(cwd); return config?.mongoURLEnvName || 'MONGO_URL'; } export function shouldUseSharedDBForAllJestWorkers(cwd?: string) { const config = loadConfig(cwd); if (typeof config?.useSharedDBForAllJestWorkers === 'undefined') { return true; } return config.useSharedDBForAllJestWorkers; } ================================================ FILE: src/index.ts ================================================ import {resolve} from 'path'; export * from './types'; export default { globalSetup: resolve(__dirname, './setup.js'), globalTeardown: resolve(__dirname, './teardown.js'), testEnvironment: resolve(__dirname, './environment.js'), transform: { '^.+\\.(t|j)sx?$': [ '@swc/jest', { jsc: { parser: { syntax: 'typescript', }, }, }, ], }, }; ================================================ FILE: src/setup.ts ================================================ /* eslint-disable multiline-ternary */ import {writeFileSync} from 'fs'; import {join} from 'path'; import {MongoMemoryReplSet, MongoMemoryServer} from 'mongodb-memory-server'; import type {JestEnvironmentConfig} from '@jest/environment'; import type {Mongo} from './types'; import { getMongoURLEnvName, getMongodbMemoryOptions, shouldUseSharedDBForAllJestWorkers, } from './helpers'; import {isMongoMemoryReplSetOptions} from './helpers'; // eslint-disable-next-line @typescript-eslint/no-require-imports const debug = require('debug')('jest-mongodb:setup'); module.exports = async (config: JestEnvironmentConfig['globalConfig']) => { const globalConfigPath = join(config.rootDir, 'globalConfig.json'); const mongoMemoryServerOptions = getMongodbMemoryOptions(config.rootDir); const isReplSet = isMongoMemoryReplSetOptions(mongoMemoryServerOptions); debug(`isReplSet ${isReplSet}`); // @ts-ignore const mongo: Mongo = isReplSet ? new MongoMemoryReplSet(mongoMemoryServerOptions) : new MongoMemoryServer(mongoMemoryServerOptions); const options = getMongodbMemoryOptions(config.rootDir); const mongoConfig: {mongoUri?: string; mongoDBName?: string} = {}; debug( `shouldUseSharedDBForAllJestWorkers: ${shouldUseSharedDBForAllJestWorkers(config.rootDir)}` ); // if we run one mongodb instance for all tests if (shouldUseSharedDBForAllJestWorkers(config.rootDir)) { if (!mongo.isRunning) { await mongo.start(); } const mongoURLEnvName = getMongoURLEnvName(config.rootDir); mongoConfig.mongoUri = await mongo.getUri(); process.env[mongoURLEnvName] = mongoConfig.mongoUri; // Set reference to mongod in order to close the server during teardown. global.__MONGOD__ = mongo; } mongoConfig.mongoDBName = isMongoMemoryReplSetOptions(options) ? '' : options?.instance?.dbName; // Write global config to disk because all tests run in different contexts. writeFileSync(globalConfigPath, JSON.stringify(mongoConfig)); debug('Config is written'); }; ================================================ FILE: src/teardown.ts ================================================ import {join} from 'path'; import {unlink} from 'fs'; import type {JestEnvironmentConfig} from '@jest/environment'; // eslint-disable-next-line @typescript-eslint/no-require-imports const debug = require('debug')('jest-mongodb:teardown'); module.exports = async function (config: JestEnvironmentConfig['globalConfig']) { const globalConfigPath = join(config.rootDir, 'globalConfig.json'); debug('Teardown mongod'); if (global.__MONGOD__) { await global.__MONGOD__.stop(); } unlink(globalConfigPath, err => { if (err) { debug('Config could not be deleted'); return; } debug('Config is deleted'); }); }; ================================================ FILE: src/types.ts ================================================ /* eslint-disable */ import { MongoMemoryReplSet, MongoMemoryServer } from "mongodb-memory-server"; declare global { var __MONGOD__: Mongo; var __MONGO_URI__: string; var __MONGO_DB_NAME__: string } export type Mongo = (MongoMemoryReplSet | MongoMemoryServer) & {isRunning: boolean} type MongoMemoryReplSetOpts = NonNullable[0]>; type MongoMemoryServerOpts = NonNullable[0]>; export interface Config { mongodbMemoryServerOptions?: MongoMemoryReplSetOpts | MongoMemoryServerOpts; /** * @default 'MONGO_URL' */ mongoURLEnvName?: string; /** * @default true */ useSharedDBForAllJestWorkers?: boolean; } ================================================ FILE: test/helpers-esm-config.test.ts ================================================ import {mkdtempSync, writeFileSync} from 'fs'; import {tmpdir} from 'os'; import {join} from 'path'; import { getMongoURLEnvName, getMongodbMemoryOptions, isMongoMemoryReplSetOptions, shouldUseSharedDBForAllJestWorkers, } from '../src/helpers'; describe('helpers with ESM default export config', () => { const originalConfigFile = process.env.MONGO_MEMORY_SERVER_FILE; const tempDir = mkdtempSync(join(tmpdir(), 'jest-mongodb-esm-config-')); const configPath = join(tempDir, 'jest-mongodb-config.mjs'); beforeAll(() => { writeFileSync( configPath, [ 'export default {', ' mongodbMemoryServerOptions: {replSet: {count: 1}},', " mongoURLEnvName: 'CUSTOM_URL',", ' useSharedDBForAllJestWorkers: false,', '};', '', ].join('\n') ); process.env.MONGO_MEMORY_SERVER_FILE = configPath; }); afterAll(() => { if (typeof originalConfigFile === 'undefined') { delete process.env.MONGO_MEMORY_SERVER_FILE; } else { process.env.MONGO_MEMORY_SERVER_FILE = originalConfigFile; } }); it('loads options from default export without throwing', () => { const options = getMongodbMemoryOptions(tempDir); expect(options).toEqual(expect.objectContaining({replSet: {count: 1}})); expect(getMongoURLEnvName(tempDir)).toBe('CUSTOM_URL'); expect(shouldUseSharedDBForAllJestWorkers(tempDir)).toBe(false); expect(isMongoMemoryReplSetOptions(options)).toBe(true); }); it('treats missing options as non-replSet', () => { expect(isMongoMemoryReplSetOptions(undefined)).toBe(false); }); }); ================================================ FILE: test/mongo-aggregate.test.ts ================================================ import {MongoClient} from 'mongodb'; import type {Db} from 'mongodb'; import '../src/types'; describe('insert', () => { const uri = global.__MONGO_URI__; let connection: MongoClient; let db: Db; beforeAll(async () => { connection = await MongoClient.connect(uri, {}); db = await connection.db(); }); afterAll(async () => { await connection.close(); }); it('should aggregate docs from collection', async () => { const files = db.collection('files'); await files.insertMany([ {type: 'Document'}, {type: 'Video'}, {type: 'Image'}, {type: 'Document'}, {type: 'Image'}, {type: 'Document'}, ]); const topFiles = await files .aggregate([{$group: {_id: '$type', count: {$sum: 1}}}, {$sort: {count: -1}}]) .toArray(); expect(topFiles).toEqual([ {_id: 'Document', count: 3}, {_id: 'Image', count: 2}, {_id: 'Video', count: 1}, ]); }); }); ================================================ FILE: test/mongo-insert.test.ts ================================================ import {MongoClient} from 'mongodb'; import type {Db} from 'mongodb'; import '../src/types'; describe('insert', () => { const uri = global.__MONGO_URI__; let connection: MongoClient; let db: Db; beforeAll(async () => { connection = await MongoClient.connect(uri, {}); db = await connection.db(); }); afterAll(async () => { await connection.close(); }); it('should insert a doc into collection', async () => { const users = db.collection('users'); const mockUser = {_id: 'some-user-id', name: 'John'}; // @ts-ignore await users.insertOne(mockUser); const insertedUser = await users.findOne({_id: 'some-user-id'}); expect(insertedUser).toEqual(mockUser); }); it('should insert many docs into collection', async () => { const users = db.collection('users'); const mockUsers = [{name: 'Alice'}, {name: 'Bob'}]; await users.insertMany(mockUsers); const insertedUsers = await users.find().toArray(); expect(insertedUsers).toEqual([ expect.objectContaining({name: 'John'}), expect.objectContaining({name: 'Alice'}), expect.objectContaining({name: 'Bob'}), ]); }); }); ================================================ FILE: test/mongo-parallelism.test.ts ================================================ import {MongoClient} from 'mongodb'; import type {Db} from 'mongodb'; import '../src/types'; import {shouldUseSharedDBForAllJestWorkers} from '../src/helpers'; describe('parallelism: first worker', () => { const uri = global.__MONGO_URI__; let connection: MongoClient; let db: Db; beforeAll(async () => { connection = await MongoClient.connect(uri, {}); db = await connection.db(); }); afterAll(async () => { await connection.close(); }); it('should have separate database', async () => { const collection = db.collection('parallelism-test'); await collection.insertOne({a: 1}); const count = await collection.count({}); if (!shouldUseSharedDBForAllJestWorkers()) { expect(count).toBe(1); } }); }); ================================================ FILE: test/mongo-parallelism2.test.ts ================================================ import {MongoClient} from 'mongodb'; import type {Db} from 'mongodb'; import '../src/types'; import {shouldUseSharedDBForAllJestWorkers} from '../src/helpers'; describe('parallelism: second worker', () => { const uri = global.__MONGO_URI__; let connection: MongoClient; let db: Db; beforeAll(async () => { connection = await MongoClient.connect(uri, {}); db = await connection.db(); }); afterAll(async () => { await connection.close(); }); it('should have separate database', async () => { const collection = db.collection('parallelism-test'); await collection.insertMany([{a: 1}, {b: 2}]); const count = await collection.count({}); if (!shouldUseSharedDBForAllJestWorkers()) { expect(count).toBe(2); } }); }); ================================================ FILE: test/mongo-parallelism3.test.ts ================================================ import {MongoClient} from 'mongodb'; import type {Db} from 'mongodb'; import '../src/types'; import {shouldUseSharedDBForAllJestWorkers} from '../src/helpers'; describe('parallelism: third worker', () => { const uri = global.__MONGO_URI__; let connection: MongoClient; let db: Db; beforeAll(async () => { connection = await MongoClient.connect(uri, {}); db = await connection.db(); }); afterAll(async () => { await connection.close(); }); it('should have separate database', async () => { const collection = db.collection('parallelism-test'); await collection.insertMany([{a: 1}, {b: 2}, {c: 3}]); const count = await collection.count({}); if (!shouldUseSharedDBForAllJestWorkers()) { expect(count).toBe(3); } }); }); ================================================ FILE: tsconfig.json ================================================ { "extends": "@shelf/tsconfig/backend", "compilerOptions": { "strict": true, "module": "commonjs", "target": "ESNext", "moduleResolution": "node", "declaration": true, "resolveJsonModule": false, "outDir": "lib" }, "exclude": ["node_modules", "**/*.test.*", "**/*.mock.ts"], "include": ["src"] }