Skip to content

Complete Jest 30 upgrade with refactored location mocking#832

Merged
hogashi merged 3 commits intorenovate/major-jest-monorepofrom
copilot/sub-pr-801
Feb 17, 2026
Merged

Complete Jest 30 upgrade with refactored location mocking#832
hogashi merged 3 commits intorenovate/major-jest-monorepofrom
copilot/sub-pr-801

Conversation

Copy link
Contributor

Copilot AI commented Feb 12, 2026

Jest 30 uses jsdom 26+ which locks window.location properties, breaking tests that mock location for URL-based logic. This PR completes the Jest 30 upgrade by refactoring code to be compatible with jest-environment-jsdom v30.

Changes

Code Refactoring

  • src/constants.ts: Modified isTwitter() and isTweetdeck() to accept optional location parameter (defaults to window.location)
    • Enables dependency injection for testing while maintaining backward compatibility
    • Type signature: (location: Location | URL = window.location): boolean

Test Updates

  • Constants.test.js: Refactored to pass URL objects directly to functions instead of mocking window.location
  • Utils.test.js: Updated to use jsdom.reconfigure({ url: '...' }) for location changes
  • ButtonSetter/ButtonSetterTweetDeck tests: Adjusted CSS expectations to match jsdom 30 behavior (color formats, padding)

Dependencies

  • package.json: Upgraded jest-environment-jsdom from ^29.7.0 to ^30.2.0
  • Added jest-environment-jsdom-global to enable jsdom.reconfigure() in tests
  • jest.config.js: Configured to use jest-environment-jsdom-global
  • Snapshots: Updated headers to Jest 30 format (https://jestjs.io/docs/snapshot-testing)

Approach

The refactoring uses dependency injection to make location-dependent functions testable without mocking window.location. This approach:

  • Makes functions more testable and follows best practices
  • Avoids deprecated mocking patterns incompatible with jsdom 26+
  • Maintains full backward compatibility (functions work identically when called without parameters)
  • Completes the full Jest 30 ecosystem upgrade

All 161 tests pass with Jest 30.2.0 and jsdom 30.2.0 ✅


✨ Let Copilot coding agent set things up for you — coding agent works faster and does higher quality work when set up for your repo.

Co-authored-by: hogashi <12870472+hogashi@users.noreply.github.com>
Copy link
Contributor Author

Copilot AI commented Feb 12, 2026

Just as a heads up, I was blocked by some firewall rules while working on your feedback. Expand below for details.

Warning

Firewall rules blocked me from connecting to one or more addresses (expand for details)

I tried to connect to the following addresses, but was blocked by firewall rules:

  • img.shields.io
    • Triggering command: /home/REDACTED/work/_temp/ghcca-node/node/bin/node node /home/REDACTED/work/twitterOpenOriginalImage/twitterOpenOriginalImage/node_modules/.bin/../.pnpm/make-coverage-badge@1.2.0/node_modules/make-coverage-badge/cli.js (dns block)

If you need me to access, download, or install something from one of these locations, you can either:

Copilot AI changed the title [WIP] Update jest monorepo to v30 Fix Jest 30 upgrade by pinning jest-environment-jsdom to v29.7.0 Feb 12, 2026
Copilot AI requested a review from hogashi February 12, 2026 09:37
@hogashi
Copy link
Owner

hogashi commented Feb 12, 2026

@copilot explain what you've done and why for review from me

Copy link
Contributor Author

Copilot AI commented Feb 12, 2026

@copilot explain what you've done and why for review from me

What I Did

Fixed the CI test failures that occurred after upgrading to Jest 30 by downgrading jest-environment-jsdom from v30.x to v29.7.0.

Why This Was Needed

The Problem:

  • Jest 30 was upgraded from 29.7.0 (including @types/jest and jest-environment-jsdom)
  • The CI tests were failing with 3 test failures in Constants.test.js
  • Tests checking isTweetdeck() for URLs like tweetdeck.twitter.com and pro.twitter.com were returning false instead of true

Root Cause:

  • jest-environment-jsdom v30.x uses jsdom v26+
  • jsdom v26+ locked down window.location properties to match real browser behavior (non-configurable, non-writable)
  • The tests use this pattern: delete window.location; window.location = new URL('https://...')
  • This pattern no longer works with jsdom v26+

The Solution:

  • Downgraded only jest-environment-jsdom to ^29.7.0 while keeping Jest at 30.2.0
  • jsdom v29 still allows window.location mocking, so existing tests work unchanged
  • This is the community-recommended workaround until tests are refactored to use alternative patterns

Changes Made

  1. package.json: Changed jest-environment-jsdom from ^30.0.0 to ^29.7.0
  2. Snapshot files: Updated headers from old URL (https://goo.gl/fbAQLP) to new Jest 30 format (https://jestjs.io/docs/snapshot-testing)
  3. pnpm-lock.yaml: Reflects the dependency downgrade

All 161 tests now pass ✅

@hogashi
Copy link
Owner

hogashi commented Feb 12, 2026

@copilot is there a way to change tests to upgrade it to v30?

Copy link
Contributor Author

Copilot AI commented Feb 12, 2026

@copilot is there a way to change tests to upgrade it to v30?

Yes, there are two main approaches to upgrade to jest-environment-jsdom v30:

Option 1: Refactor to Pass Location as Parameter (Cleanest)

Refactor isTwitter() and isTweetdeck() to accept an optional location parameter:

// src/constants.ts
export const isTwitter = (location = window.location): boolean =>
  location.hostname === HOST_TWITTER_COM ||
  location.hostname === HOST_MOBILE_TWITTER_COM ||
  location.hostname === HOST_X_COM ||
  location.hostname === HOST_MOBILE_X_COM;

export const isTweetdeck = (location = window.location): boolean =>
  location.hostname === HOST_TWEETDECK_TWITTER_COM ||
  location.hostname === HOST_PRO_TWITTER_COM ||
  location.hostname === HOST_PRO_X_COM;

Then tests can pass a mocked location:

it('tweetdeck.twitter.com', () => {
  const mockLocation = new URL('https://tweetdeck.twitter.com');
  expect(isTwitter(mockLocation)).toBeFalsy();
  expect(isTweetdeck(mockLocation)).toBeTruthy();
});

Option 2: Use jest-location-mock Library

Install jest-location-mock which provides a compatibility layer for jsdom v26+. This works but adds a dependency.

Recommendation

I'd suggest Option 1 - it's cleaner, has no extra dependencies, and makes the functions more testable. The functions would still work the same when called without arguments (using window.location by default).

Would you like me to implement Option 1?

@hogashi
Copy link
Owner

hogashi commented Feb 12, 2026

@copilot yes

- Modified isTwitter() and isTweetdeck() to accept optional location parameter
- Updated Constants tests to pass mock location objects instead of mocking window.location
- Updated Utils tests to use jsdom.reconfigure() for location changes
- Added jest-environment-jsdom-global for jsdom.reconfigure() support
- Updated test expectations for CSS differences in jsdom 30 (color format, padding)
- Upgraded jest-environment-jsdom from v29.7.0 to v30.2.0
- All 161 tests passing with Jest 30 and jsdom 30

Co-authored-by: hogashi <12870472+hogashi@users.noreply.github.com>
Copy link
Contributor Author

Copilot AI commented Feb 12, 2026

@copilot yes

Done in 6425c3f! I've refactored the code to fully support jest-environment-jsdom v30.

Changes made:

  • Refactored isTwitter() and isTweetdeck() to accept optional location parameter with default window.location
  • Updated tests to pass mock URL objects instead of mocking window.location
  • Used jsdom.reconfigure() for tests that need to change the page URL
  • Adjusted test expectations for CSS differences in jsdom 30 (color/padding formats)
  • Upgraded to jest-environment-jsdom v30.2.0

All 161 tests pass ✅

Copilot AI changed the title Fix Jest 30 upgrade by pinning jest-environment-jsdom to v29.7.0 Complete Jest 30 upgrade with refactored location mocking Feb 12, 2026
@hogashi hogashi marked this pull request as ready for review February 13, 2026 06:43
@hogashi hogashi merged commit 04ff53c into renovate/major-jest-monorepo Feb 17, 2026
1 check passed
@hogashi hogashi deleted the copilot/sub-pr-801 branch February 17, 2026 07:22
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants