@cfxlabsinc/nx-bun-testInfers a test target for every package, running bun test.
Replaces the test target @nx/vitest used to contribute. Nx's
targetDefaults can only augment a target that already exists, so without an
inference plugin every package would need to declare "test": {} by hand.
tools/test/bun.sh test ./<projectRoot>/ --pass-with-no-tests --timeout 600000 [--preload ./<projectRoot>/<preload>]
tools/test/bun.sh runs bun as the .bun-version release. On CI, PATH
bun already is that release and the script just execs it. Locally PATH often
holds a canary, whose bun test differs from CI's (module mocks, bare-specifier
onResolve, --isolate=modules), so the script runs bunx bun@<version>
and puts it first on PATH for any bun a test spawns. It compares
bun --revision, because a canary reports the same --version../<projectRoot>/, not <projectRoot>/: bun reads a bare argument as a
substring filter, which also matched copies of a package under tmp/.plus lcov coverage into coverage/<projectRoot> whenever BUN_COVERAGE holds
bun's coverage flags — pr.yml's test step sets it, and the coverage
configuration sets it to --coverage --coverage-reporter=lcov. BUN_COVERAGE
is a target input, so a cached run without coverage is never replayed for one
with it.
--pass-with-no-tests — the target is inferred for every package, the
same way the vitest one was; a package with no tests is not a failure.--parallel / --isolate by default. bun runs one package's files
sequentially in a single process, which is what the surfpool and Temporal
suites need — they previously spelled it pool: "forks" +
fileParallelism: false in their vite configs.test:parallel opts a package in. A project whose project.json tags it
gets --parallel=4, run under bun tools/test/with-postgres.ts, which
passes on an inherited TEST_DATABASE_URL or boots one Postgres for the run.
--parallel implies --isolate, so the preload runs in every file, and
without one shared server each file would boot a container of its own.inputs: default
^production
{workspaceRoot}/bunfig.toml
{workspaceRoot}/tools/test/**/*
{workspaceRoot}/.bun-version
env: BUN_COVERAGE
outputs: {workspaceRoot}/coverage/{projectRoot}
default, not production — production drops *.test.ts, which is the
one thing this target exists to run. ^production on the dependency side is
right, though: an upstream package's own tests can't change this one's result.{workspaceRoot} entries. The command runs with cwd = workspace
root, so the root bunfig.toml is the only one bun reads, and it decides both
what gets collected (pathIgnorePatterns) and what runs before every file
([test].preload → tools/test/). Neither is reachable from default —
that's {projectRoot}/**/* plus sharedGlobals, and sharedGlobals is only
tsconfig.base.json. Without them, dropping the global timeout or changing an
ignore pattern leaves every test cache warm and wrong.outputs is always declared because only a coverage run writes it and Nx
configurations carry executor options alone — outputs is target-level and
can't be narrowed per configuration. A plain test run captures nothing.A project nested inside another (tools/ci and tools/visual-snapshots inside
tools) runs its own tests, so the outer one's command passes
--path-ignore-patterns for each. The flag replaces bunfig's
pathIgnorePatterns rather than adding to them, so **/e2e/** is restated.
Not covered: the root package.json / bun.lock. A dependency bump doesn't
invalidate any test cache — that's a workspace-wide gap (build has it too) and
belongs in sharedGlobals, not here.
A package opts in by having the file; there is no per-package project.json
wiring.
| File | Used by |
|---|---|
test/preload.ts |
surfpool / Temporal packages — the module body replaces vitest's globalSetup |
test/setup.ts |
packages/ui — happy-dom's GlobalRegistrator must run before anything touches document |
A preload's module body executes once per bun test invocation, and a
top-level afterAll fires after the final test file — the same
once-per-package-with-teardown contract globalSetup provided.
The command passes --timeout 600000. tools/test/preload.ts calls
setDefaultTimeout with the same number for a bare bun test. That call can
lapse partway through a package's files, so the flag is the one that holds.
BUN_TEST_JUNIT_DIR adds a JUnit report at
$BUN_TEST_JUNIT_DIR/{projectName}.xml.