Skip to content

refactor!: replace loupe.inspect with pretty-format#9609

Draft
hi-ogawa wants to merge 34 commits intovitest-dev:mainfrom
hi-ogawa:02-08-refactor_replace_loupe.inspect_with_pretty-format
Draft

refactor!: replace loupe.inspect with pretty-format#9609
hi-ogawa wants to merge 34 commits intovitest-dev:mainfrom
hi-ogawa:02-08-refactor_replace_loupe.inspect_with_pretty-format

Conversation

@hi-ogawa
Copy link
Copy Markdown
Collaborator

@hi-ogawa hi-ogawa commented Feb 8, 2026

Description

Summary

  • Replace loupe dependency in @vitest/utils with @vitest/pretty-format for all value inspection (test titles, error display, assertion messages (only toHaveProperty was using objDisplay directly))
  • Consolidate inspect(), objDisplay(), baseFormat(), format(), and browserFormat() into two clean exports: inspect() and format()

@vitest/pretty-format:

  • To aim for node/loupe inspect style formatting, new options are added, but there are still some discrepeancy.
  • unit tests pretty-format.test.ts should show almost full coverage including how three inspects (vitest, node, loupe) differ each other.
    @vitest/utils/display exports:
Before After
inspect(obj, loupeOptions) inspect(obj, { truncate?, multiline? ... })
objDisplay(obj, loupeOptions) removed (use inspect with truncate)
format(...args) format(args, options?) — signature changed from rest params to array
browserFormat(...args) removed (use format(args, { multiline: true }))
baseFormat(args, options) removed (merged into format)

Breaking changes

Since this changes test.for/each title formatting, this is considered a breaking change.

Question: truncation config

For test.for/each title object formatting, the old behavior supported configuring truncation through chaiConfig.truncateThreshold with default truncate: 40. This PR inherits the same behavior, but I think we should introduce a separate option since we now own the formatting and relevant to chai nor loupe. Perhaps, this can be follow-up.

Please don't delete this checklist! Before submitting the PR, please make sure you do the following:

  • It's really useful if your PR references an issue where it is discussed ahead of time. If the feature is substantial or introduces breaking changes without a discussion, PR might be closed.
  • Ideally, include a test that fails without this PR but passes with it.
  • Please, don't make changes to pnpm-lock.yaml unless you introduce a new test example.
  • Please check Allow edits by maintainers to make review process faster. Note that this option is not available for repositories that are owned by Github organizations.

Tests

  • Run the tests with pnpm test:ci.

Documentation

  • If you introduce new functionality, document it. You can run documentation with pnpm run docs command.

Changesets

  • Changes in changelog are generated from PR name. Please, make sure that it explains your changes in an understandable manner. Please, prefix changeset messages with feat:, fix:, perf:, docs:, or chore:.

@hi-ogawa hi-ogawa changed the title refactor: replace loupe.inspect with pretty-format refactor!: replace loupe.inspect with pretty-format Feb 8, 2026
@hi-ogawa hi-ogawa self-assigned this Feb 10, 2026
@netlify
Copy link
Copy Markdown

netlify bot commented Mar 1, 2026

Deploy Preview for vitest-dev ready!

Built without sensitive environment variables

Name Link
🔨 Latest commit b0f1577
🔍 Latest deploy log https://app.netlify.com/projects/vitest-dev/deploys/69aa406def37f00008652c19
😎 Deploy Preview https://deploy-preview-9609--vitest-dev.netlify.app
📱 Preview on mobile
Toggle QR Code...

QR Code

Use your smartphone camera to open QR code link.

To edit notification comments on pull requests, go to your Netlify project configuration.

hi-ogawa and others added 21 commits March 5, 2026 16:21
Cover value types (primitives, collections, built-ins), existing options
(indent, maxDepth, maxWidth, min, compareKeys, callToJSON, escapeString,
escapeRegex, printBasicPrototype, printFunctionName), new PR options
(singleQuote, quoteKeys, spacingInner, spacingOuter), ErrorPlugin, and
custom plugin API.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add INSPECT_OPTIONS and prettyInspect() as the unified replacement for
inspect() and objDisplay(). Uses stringify with inspect-like options
(singleQuote, quoteKeys: false, min, spaced) and surface-level
truncation (structural summaries for containers, ellipsis for scalars).

Refactor conformance tests to use prettyInspect from @vitest/utils/display
instead of a local wrapper with duplicated options.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
@hi-ogawa hi-ogawa marked this pull request as ready for review March 6, 2026 05:07
@hi-ogawa hi-ogawa added the p2-to-be-discussed Enhancement under consideration (priority) label Mar 6, 2026
@hi-ogawa hi-ogawa moved this to P2 - 2 in Team Board Mar 6, 2026
Comment on lines -282 to -294
describe('objDisplay', () => {
test.each`
value | expected
${'a'.repeat(100)} | ${`'${'a'.repeat(37)}…'`}
${'🐱'.repeat(100)} | ${`'${'🐱'.repeat(18)}…'`}
${`a${'🐱'.repeat(100)}…`} | ${`'a${'🐱'.repeat(18)}…'`}
`('Do not truncate strings anywhere but produce valid unicode strings for $value', ({ value, expected }) => {
// encodeURI can be used to detect invalid strings including invalid code-points
// note: our code should not split surrogate pairs, but may split graphemes
expect(() => encodeURI(objDisplay(value))).not.toThrow()
expect(objDisplay(value)).toEqual(expected)
})
})
Copy link
Copy Markdown
Collaborator Author

@hi-ogawa hi-ogawa Mar 6, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Similar test exists in pretty-format.test.ts, so removed from here.

Comment on lines +236 to +238
// if stringify's adaptive maxDepth (down to 1) fails to truncate enough,
// - for known types (e.g. string, object), do something reasonable.
// - for other values, fallback to maxDepth = 0 which should show minimal output (though it can technically exeed the threshold for some cases)
Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Truncation implementation is very poor compared to loupe, but I think this should get quite far in practice.

Comment on lines +1031 to +1032
// TODO: introduce new option
return inspect(value, { truncate: runner?.config?.chaiConfig?.truncateThreshold ?? 40 })
Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The same option is reused for our inspect for now.

@hi-ogawa hi-ogawa marked this pull request as draft March 27, 2026 08:20
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

p2-to-be-discussed Enhancement under consideration (priority)

Projects

Status: P2 - 2

Development

Successfully merging this pull request may close these issues.

1 participant