vitest-dev/vitest · error · Error
--shard must be a positive number less then
Error message
--shard <index> must be a positive number less then <count>
What it means
After the count is validated, Vitest checks the shard index (numerator). The index must be a positive integer that does not exceed count. This fires on NaN, 0, negative, or an index greater than the total number of shards.
Solutions
- Use a 1-based index between 1 and count inclusive.
- If your CI gives 0-based indices, add 1 before passing to `--shard`.
- Double-check the matrix size equals the shard count.
Example fix
# before (0-based CI) vitest --shard 0/4 # after vitest --shard 1/4
Defensive patterns
Strategy: validation
Validate before calling
const nodeIndex = Number(process.env.CI_NODE_INDEX ?? '1') // 0-based from some CIs
const nodeTotal = Number(process.env.CI_NODE_TOTAL ?? '1')
const shardIndex = nodeIndex + 1 // convert to 1-based for vitest
if (shardIndex < 1 || shardIndex > nodeTotal) {
throw new Error(`Computed shard ${shardIndex}/${nodeTotal} is out of range`)
}
process.argv.push('--shard', `${shardIndex}/${nodeTotal}`) Type guard
function isValidShardString(raw: string): boolean {
const m = /^(\d+)\/(\d+)$/.exec(raw)
if (!m) return false
return Number(m[1]) >= 1 && Number(m[1]) <= Number(m[2])
} Prevention
- Document which CI env vars are 0-based and normalise to 1-based in a helper.
- Use a matrix where `i` runs 1..N inclusive.
When it happens
Trigger: `--shard 0/4`, `--shard 5/4` (index > count), `--shard abc/4`, or a CI 1-based vs 0-based indexing mismatch producing index 0.
Common situations: CI provider uses 0-based shard indices while Vitest expects 1-based; a matrix where `i` runs from 1..N but the off-by-one sends N+1.
Related errors
- --shard must be a positive number
- You cannot use --shard option with enabled watch
- "browser.instances" was set in the config, but the array is…
- Cannot merge reports with --watch enabled
- Invalid tags expression: expected
AI-assisted analysis of vitest-dev/vitest@1fa9837ec2 (2026-08-11).
Data as JSON: /api/errors/1326fc0225083f34.
Report an issue: GitHub.
Appendix: source
Thrown at packages/vitest/src/node/config/resolveConfig.ts:364
}
resolved.clearScreen = resolved.clearScreen ?? viteConfig.clearScreen ?? true
if (options.shard) {
if (resolved.watch) {
throw new Error('You cannot use --shard option with enabled watch')
}
const [indexString, countString] = options.shard.split('/')
const index = Math.abs(Number.parseInt(indexString, 10))
const count = Math.abs(Number.parseInt(countString, 10))
if (Number.isNaN(count) || count <= 0) {
throw new Error('--shard <count> must be a positive number')
}
if (Number.isNaN(index) || index <= 0 || index > count) {
throw new Error(
'--shard <index> must be a positive number less then <count>',
)
}
resolved.shard = { index, count }
}
if (resolved.standalone && !resolved.watch) {
throw new Error(`Vitest standalone mode requires --watch`)
}
if (resolved.mergeReports && resolved.watch) {
throw new Error(`Cannot merge reports with --watch enabled`)
}
if (resolved.maxWorkers) {
resolved.maxWorkers = resolveInlineWorkerOption(resolved.maxWorkers)
}View on GitHub (pinned to 1fa9837ec2)