Contributing to fast-check
Relevant source files
The following files were used as context for generating this wiki page:- CONTRIBUTING.md
- packages/fast-check/package.json
- website/blog/2023-09-04-dual-packages-or-supporting-both-cjs-and-esm/index.md
- packages/fast-check/test/e2e/documentation/Docs.md.spec.ts
- website/blog/2023-05-16-fast-check-loves-docusaurus/index.md
- website/blog/2025-03-10-whats-new-in-fast-check-4-0-0/index.md
This guide provides a comprehensive overview for developers looking to contribute to the fast-check project. It covers everything from setting up the local environment and understanding the project's architecture to following the coding standards and pull request process. Contributions can range from asking questions and reporting bugs to submitting pull requests for new features or fixes.
Sources: CONTRIBUTING.md:3-8
Getting Started
To begin contributing, you need to set up the development environment locally. The project uses pnpm for dependency management. The initial setup involves cloning the repository, installing dependencies, and building the main fast-check package.
Sources: CONTRIBUTING.md:30-34, website/blog/2025-03-10-whats-new-in-fast-check-4-0-0/index.md:143
Initial Setup Flow
The following diagram illustrates the commands required to prepare your local environment for development.
Sources: CONTRIBUTING.md:31-34
Key Development Commands
The table below summarizes the essential commands for local development.
| Command | Description |
|---|---|
pnpm install | Installs all project dependencies. |
pnpm --filter fast-check build | Compiles the TypeScript source in packages/fast-check/src and outputs the build to packages/fast-check/lib. |
pnpm format:check | Checks if the code adheres to the Prettier style standard. |
pnpm format | Automatically fixes code style issues using Prettier. |
pnpm lint:check | Checks for linting errors. |
pnpm lint | Automatically fixes linting problems. |
pnpm -w run bump | A script to determine the semantic versioning impact of your changes on the packages. |
Sources: CONTRIBUTING.md:32-54
Project Architecture
The fast-check repository is a monorepo that has transitioned to using pnpm for managing its packages. A key architectural feature is its support for both CommonJS (CJS) and ES Modules (ESM), ensuring broad compatibility across different JavaScript environments.
Sources: website/blog/2025-03-10-whats-new-in-fast-check-4-0-0/index.md:143, website/blog/2023-09-04-dual-packages-or-supporting-both-cjs-and-esm/index.md:10-14
Dual CJS/ESM Package Support
To support both module systems, fast-check employs a specific project structure and package.json configuration. The root package.json declares the project as an ES Module ("type": "module"), but it generates separate output directories for CJS and ESM builds.
The exports field in packages/fast-check/package.json is crucial for directing Node.js and bundlers to the correct file based on the import method (require vs. import).
// packages/fast-check/package.json
{
"type": "module",
"main": "lib/fast-check.js",
"exports": {
"./package.json": "./package.json",
".": {
"require": {
"types@<5.7": "./lib/cjs/types57/fast-check.d.ts",
"types": "./lib/cjs/types/fast-check.d.ts",
"default": "./lib/cjs/fast-check.js"
},
"import": {
"types@<5.7": "./lib/types57/fast-check.d.ts",
"types": "./lib/types/fast-check.d.ts",
"default": "./lib/fast-check.js"
}
}
},
"module": "lib/fast-check.js",
"types": "lib/types/fast-check.d.ts"
}
Sources: packages/fast-check/package.json:4-24, website/blog/2023-09-04-dual-packages-or-supporting-both-cjs-and-esm/index.md:73-95
The build process, defined in packages/fast-check/package.json, uses tsc to compile TypeScript into two separate targets: one for CJS and one for ESM. This includes generating distinct type definition files for each module system.
// packages/fast-check/package.json
"scripts": {
"build": "pnpm run build:publish-cjs && pnpm run build:publish-esm && pnpm run build:publish-types && node postbuild/main.mjs",
"build:publish-types": "tsc -p tsconfig.publish.types.json && tsc -p tsconfig.publish.types.json --outDir lib/cjs/types",
"build:publish-cjs": "tsc -p tsconfig.publish.json --outDir lib/cjs && cp package.cjs-template.json lib/cjs/package.json",
"build:publish-esm": "tsc -p tsconfig.publish.json --module es2015 --moduleResolution node",
// ...
}
Sources: packages/fast-check/package.json:28-32
The following diagram shows the directory structure used to isolate CJS modules. A nested package.json inside the CJS output directory overrides the module type.
This diagram illustrates the strategy of using a nested package.json to declare a subdirectory as CommonJS within a larger ESM project, a slight variation of the strategy described in the blog post.
Sources: website/blog/2023-09-04-dual-packages-or-supporting-both-cjs-and-esm/index.md:63-71, packages/fast-check/package.json:31
Pull Request Process
All contributions are submitted via pull requests. The process is designed to be smooth and maintain high code quality through automation and clear guidelines.
PR Lifecycle
The diagram below outlines the typical workflow for submitting a pull request.
Sources: CONTRIBUTING.md:44-73
Semantic Versioning
Before opening a PR, contributors should run pnpm -w run bump. This script helps classify the impact of the change according to semantic versioning (patch, minor, or major), which streamlines the release process. Internal or private packages should always be marked as 'decline'.
Sources: CONTRIBUTING.md:48-57
Testing Strategy
fast-check has a comprehensive testing strategy to ensure correctness, prevent regressions, and maintain compatibility.
Types of Tests
| Test Type | File Location / Command | Purpose |
|---|---|---|
| Unit & Integration | test/unit/arbitrary/ | Tests new arbitraries in isolation and in integration with a real random generator. Uses helpers like assertProduceCorrectValues. |
| No Regression | test/e2e/NoRegression.spec.ts | Prevents unintended breaking changes by snapshotting the output of arbitraries. Update with pnpm --filter fast-check e2e -- -u. |
| Legacy Support | packages/test-minimal-support/main.js | Ensures arbitraries work correctly on older supported versions of Node.js. |
| Typing | packages/test-types/main.ts | Verifies that TypeScript typings are correct and do not break with future TypeScript releases. |
| Documentation Snippets | test/e2e/documentation/Docs.md.spec.ts | Automatically validates and updates code snippets and generated examples within the documentation files. |
Sources: CONTRIBUTING.md:83-145, packages/fast-check/test/e2e/documentation/Docs.md.spec.ts
Adding a New Arbitrary
When adding a new arbitrary, contributors must:
- Create a feature request to justify its need.
- Code the arbitrary in a new file under
src/arbitrary/. - Add comprehensive tests, including unit, integration, no-regression, legacy, and typing tests as described in the table above.
- Document the arbitrary with JSDoc comments and add it to the website's list of built-in arbitraries.
Sources: CONTRIBUTING.md:78-152
Documentation Contributions
Documentation is a vital part of the project and is managed using Docusaurus.
Sources: website/blog/2023-05-16-fast-check-loves-docusaurus/index.md:81-83
Automated Snippet Verification
A unique aspect of the documentation process is the automated testing and generation of code examples. A test suite located at packages/fast-check/test/e2e/documentation/Docs.md.spec.ts parses all markdown documentation files, executes the JavaScript code blocks, and verifies or regenerates the "Examples of generated values" sections.
This ensures all examples in the documentation are correct and up-to-date. If a contributor runs the tests with the UPDATE_CODE_SNIPPETS environment variable set, the script will automatically update the markdown files with fresh examples.
The following diagram shows how this process works.