vitest-dev/vitest · error · TypeError

Test attachment requires "body" or "path" to be set. Both…

Error message

Test attachment requires "body" or "path" to be set. Both are missing.

What it means

A `TestAttachment` must carry either `body` (inline content) or `path` (a file reference) — one is required so the reporter/CI consumer has something to render. This `TypeError` fires when both are missing/null. The validation runs in `manageArtifactAttachment`, which `recordArtifact` calls for every entry in `artifact.attachments`.

Solutions

  1. Set `body` (string or Uint8Array) for inline content: `attachments: [{ name: 'log', body: '...' }]`.
  2. Or set `path` to a file path: `attachments: [{ name: 'screenshot', path: '/tmp/shot.png' }]`.
  3. When building attachments dynamically, default to an empty string body if you have no path: `body: data ?? ''`.
  4. Filter out empty attachments before recording if neither field is meaningful.

Example fix

// before
recordArtifact(task, {
  type: 'report',
  attachments: [{ name: 'log' }],
})

// after
recordArtifact(task, {
  type: 'report',
  attachments: [{ name: 'log', body: logText }],
})
Defensive patterns

Strategy: validation

Validate before calling

for (const a of attachments) { if (a.body == null && !a.path) throw new TypeError(`attachment '${a.name}' needs body or path`) }

Type guard

function hasBodyOrPath(a: TestAttachment): boolean { return a.body != null || Boolean(a.path) }

Try / catch

null

Prevention

When it happens

Trigger: Passing `recordArtifact(task, { type: '...', attachments: [{ name: 'log' /* no body, no path */ }] })`; an attachment built dynamically where both fields ended up undefined; destructuring an attachment from an API response that omits both fields. The guard is `attachment.body == null && !attachment.path` at artifact.ts:171.

Common situations: Building attachments from optional/conditional data where neither branch populated a field; refactoring that renamed `content` to `body` but missed call sites; CI uploading an empty attachment stub; passing `body: ''` is allowed (only null/undefined trigger), but `body: null` is not.

Related errors


AI-assisted analysis of vitest-dev/vitest@1fa9837ec2 (2026-08-11). Data as JSON: /api/errors/b607e45c54783ebc. Report an issue: GitHub.

Appendix: source

Thrown at packages/vitest/src/runtime/runner/artifact.ts:172

    test.promises = []
  }
  test.promises.push(promise)
  return promise
}

/**
 * Validates and prepares a test attachment for serialization.
 *
 * This function ensures attachments have either `body` or `path` set (but not both), and converts `Uint8Array` bodies to base64-encoded strings for easier serialization.
 *
 * @param attachment - The attachment to validate and prepare
 *
 * @throws {TypeError} If neither `body` nor `path` is provided
 * @throws {TypeError} If both `body` and `path` are provided
 */
export function manageArtifactAttachment(attachment: TestAttachment): void {
  if (attachment.body == null && !attachment.path) {
    throw new TypeError(`Test attachment requires "body" or "path" to be set. Both are missing.`)
  }
  if (attachment.body && attachment.path) {
    throw new TypeError(`Test attachment requires only one of "body" or "path" to be set. Both are specified.`)
  }
  if (attachment.path && attachment.bodyEncoding) {
    throw new TypeError(`Test attachment with "path" should not have "bodyEncoding" specified.`)
  }
  // convert to a string so it's easier to serialise
  if (attachment.body instanceof Uint8Array) {
    attachment.body = encodeUint8Array(attachment.body)
  }
  if (attachment.body != null) {
    attachment.bodyEncoding ??= 'base64'
  }
}

View on GitHub (pinned to 1fa9837ec2)