Skip to content

build: migrate to ESM and bump @actions/tool-cache to 4.x#458

Merged
nanasess merged 5 commits into
masterfrom
feature/bump-tools-cache
Jun 1, 2026
Merged

build: migrate to ESM and bump @actions/tool-cache to 4.x#458
nanasess merged 5 commits into
masterfrom
feature/bump-tools-cache

Conversation

@nanasess

@nanasess nanasess commented Jun 1, 2026

Copy link
Copy Markdown
Owner

Summary

Bumps @actions/tool-cache from 2.0.2 to 4.0.0 (and @actions/core / @actions/io / @actions/exec to 3.x).

These releases are pure ESM"type": "module" with no require entry in their exports map — so a version bump alone fails at runtime with ERR_REQUIRE_ESM. Migrating the project from CommonJS to ESM is therefore a hard prerequisite, and this PR does the whole migration in one shot.

What changed

  • package.json: add "type": "module"; bump toolkit deps to 4.x/3.x; drop the unused @actions/github dependency; add @jest/globals as a devDependency (needed for type resolution under pnpm strict + NodeNext); run the test script with NODE_OPTIONS=--experimental-vm-modules.
  • tsconfig.json: module / moduleResolutionNodeNext; enable isolatedModules (silences ts-jest's hybrid-module warning).
  • src/: add .js extensions to relative imports (required by NodeNext). NodeNext also requires an explicit extension for CJS package subpaths, so typed-rest-client/HttpClient is imported as typed-rest-client/HttpClient.js.
  • Tests / Jest: ESM config (jest.config.mjs + ts-jest useESM). jest.mock hoisting does not work under ESM, so every mocking test was rewritten to import { jest } from "@jest/globals" + jest.unstable_mockModule(...) + dynamic await import() + jest.mocked(). __dirname (equivalence test) is derived from import.meta.url.
  • Artifacts: lib/ and dist/ regenerated as ESM. ncc 0.38.4 detects type: module and emits an ESM bundle, renames sourcemap-register.js.cjs, and generates dist/package.json ({"type":"module"}).
  • Formatting: prettier --write applied across all *.ts (some files were already non-conforming on master).

Parity

Behavioral parity with the shell scripts is preserved: the install locations (/usr/local/bin/chromedriver, C:\SeleniumWebDrivers\ChromeDriver) and the implicit PATH resolution are unchanged, and the legacy lib/*.sh / *.ps1 are retained as an emergency rollback option.

Verification

  • pnpm build (tsc / NodeNext) — clean.
  • pnpm test97 passed, 4 skipped (7 suites).
  • pnpm package — ncc emits an ESM dist/index.js.
  • pnpm format-check — all files conform.
  • Local end-to-end smoke test: ran node dist/index.js and confirmed @actions/tool-cache@4 downloadToolextractZip → install to /usr/local/bin works (the only failure was the local sandbox's sudo/RUNNER_TEMP constraints, not a module issue).
  • Real GitHub Actions runner verification (Ubuntu / macOS / Windows) runs via this PR's CI.

🤖 Generated with Claude Code

Summary by CodeRabbit

リリースノート

  • Refactor
    • プロジェクトをCommonJS からES Modules(ESM)に移行しました。機能の動作は変わりません。
    • 依存パッケージのバージョンを更新しました。
    • テスト環境をESM に対応させました。

nanasess and others added 2 commits June 1, 2026 15:55
@actions/tool-cache 4.0.0 および @actions/core/io/exec 3.x は pure ESM
(package.json "type":"module"、exports に require エントリなし) のため、
バージョンを上げるにはプロジェクト全体を CommonJS から ESM へ移行する
必要がある。一連の移行をまとめて行う。

- package.json: "type":"module" 化、toolkit 依存を 4.x/3.x へ更新、
  src/テストで未使用の @actions/github を削除、test を
  experimental-vm-modules で起動
- tsconfig: module/moduleResolution を NodeNext、isolatedModules を有効化
- src: 相対 import に .js 拡張子を付与。NodeNext は CJS パッケージの
  サブパスにも拡張子を要求するため typed-rest-client/HttpClient を
  明示拡張子付きで import
- jest: ESM 化 (jest.config.mjs + ts-jest useESM)。ESM では jest.mock の
  巻き上げが効かないため、テストの jest.mock を jest.unstable_mockModule
  + 動的 import へ書き換え。equivalence は __dirname を import.meta.url 由来へ
- lib/ dist/ を ESM で再生成。ncc 0.38.4 も type:module を見て ESM 出力し、
  sourcemap-register を .cjs 化、dist/package.json を生成する

download/extract から /usr/local/bin・C:\SeleniumWebDrivers への配置まで
実行パスの parity は不変。lib のレガシー shell/ps1 も従来どおり残置。

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
ESM 移行で触れたファイルに加え、master 時点で既に prettier 非準拠だった
ファイル (src/chromedriver-helper.ts, __tests__/chromedriver.ts 等) も整形し、
format-check を全面的に通過させる。整形は tsc/ncc の出力に影響しないため
lib/ dist/ の再生成差分は無し。

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

@gemini-code-assist gemini-code-assist Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Code Review

This pull request migrates the project to ES Modules (ESM), updating package.json, tsconfig.json, and jest.config.mjs to support ESM. Relative imports have been updated with .js extensions, and unit tests have been refactored to use jest.unstable_mockModule and dynamic imports. Feedback was provided to use cross-env in the test script to ensure cross-platform compatibility on Windows when setting NODE_OPTIONS.

Comment thread package.json Outdated
"format": "prettier --write **/*.ts",
"format-check": "prettier --check **/*.ts",
"test": "jest"
"test": "NODE_OPTIONS=--experimental-vm-modules jest"

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

medium

On Windows platforms (such as standard cmd.exe or PowerShell), prepending environment variables directly to a command (e.g., NODE_OPTIONS=... jest) is not supported and will result in a syntax error.

To ensure the test suite can be run locally on Windows, consider using cross-env to set the environment variable in a cross-platform manner. Remember to also add cross-env to your devDependencies.

Suggested change
"test": "NODE_OPTIONS=--experimental-vm-modules jest"
"test": "cross-env NODE_OPTIONS=--experimental-vm-modules jest"

@coderabbitai

coderabbitai Bot commented Jun 1, 2026

Copy link
Copy Markdown

Review Change Stack

Warning

Review limit reached

@nanasess, we couldn't start this review because you've reached your PR review rate limit.

More reviews will be available in 17 minutes and 48 seconds. Learn how PR review limits work.

Your organization has run out of usage credits. Purchase more in the billing tab.

⌛ How to resolve this issue?

After more reviews become available, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

We recommend that you space out your commits to avoid hitting the rate limit.

🚦 How do rate limits work?

CodeRabbit enforces hourly rate limits for each developer per organization.

Our paid plans include higher PR review limits than trial, open-source, and free plans. In all cases, reviews become available again over time. During sustained high-volume PR review activity, CodeRabbit may temporarily slow when the next review becomes available.

Please see our Fair Usage Limits Policy for further information.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 78ea7a23-733b-4313-8b28-da5d6d8ea3bf

📥 Commits

Reviewing files that changed from the base of the PR and between ba85371 and 359dcf4.

📒 Files selected for processing (1)
  • package.json
📝 Walkthrough

ウォークスルー

このPRはプロジェクト全体をCommonJSからES ModulesへMigrationさせます。パッケージ設定とtsconfig.jsonをESM対応化し、すべてのライブラリコードをexport function形式で公開し、Jestテストをjest.unstable_mockModuleによる動的モック化で対応させています。

変更内容

CommonJS から ESM への全体移行

レイヤー / ファイル 説明
構成・環境準備(ESM有効化)
package.json, tsconfig.json, jest.config.mjs
package.jsontype: "module"設定により Node.js がESMを既定値として解釈し、tsconfig.jsonmodule: NodeNextmoduleResolution: NodeNextでTypeScript側のESM出力を統一、jest.config.mjsts-jestuseESM: trueとモジュール名マッパーを設定してテスト実行環境を整えます。
コアヘルパのESM化(chromedriver-helper)
lib/chromedriver-helper.js, src/chromedriver-helper.ts
parseMajorVersionからgetInstallPathまで12個の関数をCommonJS形式のexports.*代入からESM形式のexport function宣言に統一し、ファイル先頭の"use strict"Object.definePropertyの生成コードを削除します。TypeScript側でも関数シグネチャの表記を整形します。
インストーラーモジュールのESM化
lib/installer/download.js, lib/installer/http.js, lib/installer/unix.js, lib/installer/version.js, lib/installer/windows.js, lib/setup-chromedriver.js
ダウンロード・HTTP通信・バージョン解決・Unix/Windows別インストール処理の各モジュールで、requireexportsのCommonJS型からimportexport async functionのESM形式へ移行します。相互間の参照も名前空間付き呼び出し(version_1.resolveModernDownload等)から直接import参照へ置き換わります。
TypeScript ソースの ESM互換化
src/chromedriver-helper.ts, src/installer/http.ts, src/installer/unix.ts, src/installer/version.ts, src/installer/windows.ts, src/setup-chromedriver.ts
モジュール参照に.js拡張子を明示し(../chromedriver-helper.js等)、ESM環境での Node.js モジュール解決を確実化します。
テストの ESM対応(動的モック化)
__tests__/*.test.ts
8個のテストファイルでjest.mockjest.unstable_mockModuleに置き換え、@jest/globalsからのjest取得により、dynamic import 後のモック参照をjest.mocked(...)で型付き取得する方式に統一します。あわせてモジュール参照を.js拡張子付きへ更新します。

推定レビュー労力

🎯 4 (複雑) | ⏱️ ~50分

関連するPR

  • nanasess/setup-chromedriver#437: 既存のchromedriver統合テストファイル(__tests__/chromedriver-api.test.ts__tests__/chromedriver-helper.test.ts__tests__/equivalence.test.ts)をESM化し、@jest/globals.jsサフィックス付きのchromedriver-helperインポートで同一のURL生成アサーション構造を保持します。

  • nanasess/setup-chromedriver#446: PR #446で導入されたインストーラーモジュールdownloadAndExtractZipfetchText/fetchJsoninstallOnUnix/installOnWindowsおよびヘルパーのimport/export)をESM/CommonJS移行によりコード上で直接マイグレーションし、相互参照とモック化の一貫性を確立します。

🐇 モジュールたちは新しい衣を纏い
exportの輝きで時代を映し出す
Jest の動的モック、ES の未来へ
ウサギも走る、ESM への道 🚀

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 55.17% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed PR タイトルは「build: migrate to ESM and bump @actions/tool-cache to 4.x」で、変更内容の主な目的(CommonJS から ESM への移行と @actions/tool-cache のバージョンアップ)を正確に反映しており、明確で簡潔である。
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feature/bump-tools-cache

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

nanasess and others added 3 commits June 1, 2026 16:04
CI の selenium スモークテスト (ts-node __tests__/chromedriver.ts) が
ERR_MODULE_NOT_FOUND で失敗していた。プロジェクトが "type":"module" に
なったことで ts-node が ESM モードで動作し、拡張子なしの CJS サブパス
import `selenium-webdriver/chrome` を解決できなくなったため。
`selenium-webdriver/chrome.js` と明示する。

action 本体・build・package・jest は実 runner で既に成功しており、
この E2E ステップのみの修正。test.yml と windows.yml の両方をカバーする。

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…cache

# Conflicts:
#	dist/index.js
#	dist/index.js.map
`NODE_OPTIONS=--experimental-vm-modules jest` はインライン環境変数代入で、
Windows の cmd.exe では `'NODE_OPTIONS' is not recognized` となり CI が失敗
していた (jest ESM には --experimental-vm-modules が必須)。

jest 公式ドキュメント記載の `node --experimental-vm-modules
node_modules/jest/bin/jest.js` 形式へ変更。環境変数プレフィックスが不要で
cmd.exe/pwsh/bash すべてで動作し、新規依存 (cross-env 等) も追加しない。
`pnpm test <path>` の単体指定も従来どおり機能する。

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@nanasess nanasess merged commit 38db136 into master Jun 1, 2026
79 checks passed
@nanasess nanasess deleted the feature/bump-tools-cache branch June 1, 2026 07:23
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.

1 participant