tsdown-migrate について
tsdown-migrateは、プロジェクトをtsupからtsdownへ移行するAIエージェント向けのナレッジベースです。段階的なアップグレード、オプションの対応関係、既定値の変更、非対応設定を説明します。
主な機能
- 01段階的な移行ガイド
- 02tsupオプションの対応表
- 03既定値の差分情報
- 04非対応オプションの説明
- 05パッケージとスクリプトの移行
活用シーン
- 01tsup設定の移行
- 02ビルド既定値の変更確認
- 03削除されたオプションの代替検索
- 04パッケージスクリプトと依存関係の更新
インストール
コマンドをコピーしてターミナルで実行します。
npx skills add https:/ / github.com/ rolldown/ tsdown --skill tsdown-migrateインストール後、Claude Code で/tsdown-migrateを入力して読み込まれたか確認します。
同梱ファイル
SKILL.md と一緒にインストールされる参考資料やスクリプト。
README.mdreferences/guide-differences-detailed.mdguide-option-mappings.mdguide-package-json.md詳細
tsup から tsdown への移行
tsup プロジェクトを tsdown(Rolldown を利用したライブラリバンドラー)に移行するための、AI エージェント向けナレッジベースです。
対象バージョン:2 段階での移行
tsdown v0.23 では、以前に非推奨となった tsup 互換オプション(bundle、outExtension、publicDir、removeNodeProtocol、injectStyle、skipNodeModulesBundle)がすべて削除されました。これらのオプションは TypeScript の型チェックで認識されず、実行時には警告なしで無視されるため、v0.23 以降で対応するマッピングを見落とすと、エラーが出ないまま誤った出力が生成されます。そのため、v0.23 以降へ直接移行するのは安全ではありません。これらのオプションをまだ受け付け、各オプションに非推奨の警告を表示する最後のバージョンが tsdown v0.22.14 です。安全に移行するためのチェックポイントとして、次の 2 段階で移行してください。
- ステージ 1 —
[email protected]で移行する:[email protected]をインストールし、以下の表に従って設定を移行してからビルドを実行し、警告が出た すべての tsup オプションを、対応する tsdown のオプションにマッピングして解決します。警告は移行の完全性を確認するためのものです。ビルドで警告が 0 件になるまでは、移行は完了していません。 - ステージ 2 — 最新の tsdown(
^0.23.0以降)にアップグレードする:0.22.14 で警告のないビルドができてからアップグレードしてください。設定で削除された互換オプションを使用しなくなっているため、v0.23 以降で警告なしに無視される問題は起こりません。
実行環境の要件
tsdown の実行には Node.js ^22.18.0 || ^24.11.0 || >=26.0.0 が必要です(ビルド時のみ)。つまり、Node.js 22.18 以降、24.11 以降、または 26 以降が必要です。奇数バージョンおよび EOL のリリース系列(例:Node.js 23、25)はサポートされていません。バンドルした出力は target オプションを使って、より低い Node.js バージョンを対象にできます。そのため、tsup で Node.js 18/20 をサポートしていたライブラリも、移行後に引き続きサポートできます。
Node.js 18/20 をサポートする場合の推奨ワークフロー:
- CI では Node.js 22 以降を使ってビルドし、
'node18'や'node20'などの明示的なtargetを設定します。 - ビルドした出力(またはパッケージ化した tarball)を、サポート対象とする低いバージョンの Node.js でテストします。
使用する場面
- プロジェクトを tsup から tsdown に移行する
- tsup と tsdown のオプションの違いを把握する
- 移行後の設定に関する問題を確認または修正する
- tsup から tsdown への互換性についてユーザーに案内する
移行の概要
tsup プロジェクトは、次の手順で移行してください。
- 設定ファイル名を変更する:
tsup.config.*→tsdown.config.* - インポートを更新する:
'tsup'→'tsdown' - オプションをマッピングする:以下の表に従ってオプション名を変更、または変換する
- tsup のデフォルト値を維持する:異なるオプション(format、clean、dts、target)を明示的に設定する
- package.json を更新する:依存関係(ステージ 1:
[email protected])、スクリプト、ルート設定フィールド - サポートされていないオプションを削除する:代替手段がある場合は置き換える
- 0.22.14 でビルドをテストする:
tsdownを実行し、非推奨の警告をすべて解決する。警告が 0 件であることが必須です - 最新の tsdown(
^0.23.0以降)にアップグレードし、ビルドを再度確認する
設定ファイルの移行
ファイル名の変更
| tsup | tsdown |
|---|---|
tsup.config.ts | tsdown.config.ts |
tsup.config.cts | tsdown.config.cts |
tsup.config.mts | tsdown.config.mts |
tsup.config.js | tsdown.config.js |
tsup.config.cjs | tsdown.config.cjs |
tsup.config.mjs | tsdown.config.mjs |
tsup.config.json | tsdown.config.json |
インポートと識別子の変更
// Before
import { defineConfig } from 'tsup'
// After
import { defineConfig } from 'tsdown'
すべての識別子を置き換えます:tsup → tsdown、TSUP → TSDOWN。
オプションのマッピング
プロパティ名の変更
| tsup | tsdown | 備考 |
|---|---|---|
entryPoints | entry | tsup 自体でも非推奨です |
cjsInterop | cjsDefault | CJS のデフォルトエクスポートの処理 |
esbuildPlugins | plugins | Rolldown/Unplugin プラグインを使用するようになりました |
outExtension | outExtensions | カスタム出力拡張子 |
publicDir | copy | 静的ファイルを出力先にコピーします |
bundle: true | (削除) | バンドルはデフォルトの動作です |
bundle: false | unbundle: true | ファイル構造を保持します |
removeNodeProtocol: true | nodeProtocol: 'strip' | node: プレフィックスを削除します |
injectStyle: true | css: { inject: true } | CSS の挿入 |
injectStyle: false | (削除) | デフォルトの動作です |
skipNodeModulesBundle | deps: { neverBundle: true } | すべての依存関係を外部化します |
tsdown v0.23 以降では、古い名前はどれも認識されません。常に新しい名前を出力してください。互換性オプション(outExtension、skipNodeModulesBundle、publicDir、bundle、removeNodeProtocol、injectStyle)は v0.22.14 までは非推奨の警告付きで受け入れられていましたが、v0.23 で完全に削除されました。v0.23 以降では、残っている設定はエラーにならず、警告もなく無視されるため、ビルドが意図しない動作になります。そのため、Stage 1 は v0.22.14 で実行し、残っている設定をすべて検出します。
非推奨ですが、引き続き受け入れられる設定
external と noExternal は、tsdown v0.23 で引き続き受け入れられる tsup のオプション名として唯一のものです。非推奨の警告が出力され、将来のバージョンで削除される予定です。また、置き換え後の設定と併用できません(external と deps.neverBundle、または noExternal と deps.alwaysBundle を混在させるとエラーになります)。常に置き換え後の設定を出力してください。
| tsup(非推奨) | tsdown(推奨) | 備考 |
|---|---|---|
external: [...] | deps: { neverBundle: [...] } | deps 名前空間に移動しました |
noExternal: [...] | deps: { alwaysBundle: [...] } | deps 名前空間に移動しました |
出力ファイル名の違い
IIFE ビルドでは、tsdown は [name].iife.js のような名前を出力しますが、tsup は一般的に [name].global.js を出力していました。outExtensions で拡張子やサフィックスをカスタマイズできますが、組み込みの .iife または .umd セグメントは削除できません。古い IIFE ファイル名を維持するには、outputOptions.entryFileNames: '[name].global.js' を使用してください。
依存関係の名前空間の変更
依存関係の設定は deps 名前空間に移動しました。external と noExternal の両方がある場合は、1 つの deps オブジェクトに統合してください。
// Before (tsup)
export default defineConfig({
external: ['react'],
noExternal: ['lodash-es'],
})
// After (tsdown)
export default defineConfig({
deps: {
neverBundle: ['react'],
alwaysBundle: ['lodash-es'],
},
})
tsdown には deps.onlyBundle(バンドルを許可するパッケージのホワイトリスト)も追加されています。tsup に同等の設定はありません。
tsdown v0.23 以降の依存関係の処理に関するデフォルト設定:
dependencies、peerDependencies、および**optionalDependencies**はすべて、デフォルトで外部化されます(tsup が外部化するのはdependenciesとpeerDependenciesのみのため、移行後にoptionalDependenciesがバンドル対象から外部化対象に変わる場合があります)。deps.resolveDepSubpath(exportsフィールドを持たない外部化されたパッケージのサブパスインポートを解決する設定)は、デフォルトで無効です。
プラグインのインポート変換
// Before (tsup - esbuild plugins)
import plugin from 'unplugin-example/esbuild'
// After (tsdown - Rolldown plugins)
import plugin from 'unplugin-example/rolldown'
すべての unplugin-*/esbuild インポートを unplugin-*/rolldown に変更してください。
すべての変換について、完全な変換前後の例は guide-option-mappings.md を参照してください。
デフォルト値の違い
tsdown では、tsup とはいくつかのデフォルト値が異なります。移行時は、まず tsup の動作を維持できるようにこれらを明示的に設定し、その後、新しいデフォルト値を採用するかどうかをユーザーに判断してもらいます。
| オプション | tsup のデフォルト値 | tsdown のデフォルト値 | 移行時の対応 |
|---|---|---|---|
format | 'cjs' | 'esm' | 維持するには format: 'cjs' を設定します |
clean | false | true | 維持するには clean: false を設定します |
dts | false | package.json の types/typings に基づいて自動的に有効化 | 維持するには dts: false を設定します |
target | (なし) | package.json の engines.node から自動的に読み込み | 維持するには target: false を設定します |
移行後、ユーザーにこれらの設定を見直すよう提案してください。通常、tsdown のデフォルト値のほうが適しています。
- ESM は最新の標準です
- 出力をクリーンアップすると、古いファイルが残りません
- package.json から DTS を自動設定することで、設定を減らせます
- engines.node から target を自動設定することで、一貫性を確保できます
サポートされていないオプション
以下の tsup オプションには、tsdown に直接対応する機能がありません。これらを削除し、ユーザーに知らせてください。
| tsup のオプション | 状態 | 代替手段 |
|---|---|---|
splitting | 常に有効 | 削除します。tsdown ではコード分割を無効にできません |
metafile | 利用不可 | Vite DevTools でバンドルを分析するには devtools: true を提案します |
swc | 非対応 | 削除します。tsdown は変換に oxc を標準で使用します |
experimentalDts | 非対応 | 代わりに dts オプションを使用します |
legacyOutput | 非対応 | 削除します。代替手段はありません |
plugins(tsup の実験的機能) | 互換性なし | Rolldown のプラグインに手動で移行します。tsup のプラグイン API は Rolldown のものとは異なります |
Package.json の移行
スクリプト
すべてのスクリプトコマンドで tsup と tsup-node を tsdown に置き換えます。
// Before
{
"scripts": {
"build": "tsup src/index.ts",
"dev": "tsup --watch"
}
}
// After
{
"scripts": {
"build": "tsdown src/index.ts",
"dev": "tsdown --watch"
}
}
依存関係
| 場所 | 対応 |
|---|---|
dependencies.tsup | dependencies.tsdown に名前を変更します |
devDependencies.tsup | devDependencies.tsdown に名前を変更します |
optionalDependencies.tsup | optionalDependencies.tsdown に名前を変更します |
peerDependencies.tsup | peerDependencies.tsdown に名前を変更します |
peerDependenciesMeta.tsup | peerDependenciesMeta.tsdown に名前を変更します |
ルート設定フィールド
package.json にルートレベルの tsup フィールド(インライン設定)がある場合は、tsdown に名前を変更します。
// Before
{ "tsup": { "entry": ["src/index.ts"] } }
// After
{ "tsdown": { "entry": ["src/index.ts"] } }
package.json の詳しい例については、guide-package-json.md を参照してください。
tsdown の新機能
移行後、tsdown 独自の以下の機能をユーザーに提案してください。
| 機能 | 設定 | 説明 |
|---|---|---|
| Node プロトコル | nodeProtocol: true | 'strip' | 組み込みモジュールのインポートに node: プレフィックスを追加または削除します |
| ワークスペース | workspace: 'packages/*' | モノレポ内の複数のパッケージをビルドします |
| パッケージの exports | exports: true | package.json の exports フィールドを自動生成します |
| パッケージの検証 | publint: true, attw: true | パッケージをリントし、型の正確性を確認します |
| 実行可能ファイル | exe: true | Node.js のスタンドアロン実行可能ファイル(SEA)としてバンドルします |
| DevTools | devtools: true | バンドル分析のための Vite DevTools 連携 |
| フック | hooks: { 'build:done': ... } | ライフサイクルフック:build:prepare、build:before、build:done |
| CSS モジュール | css: { modules: { ... } } | .module.css ファイルにスコープ付きクラス名を適用します |
| Glob インポート | globImport: true | import.meta.glob(Vite 形式)をサポートします |
詳しい比較については、guide-differences-detailed.md を参照してください。
参考資料
| トピック | 説明 | 参考資料 |
|---|---|---|
| オプションの対応表 | 各オプションの変換前後をすべて記載 | guide-option-mappings |
| 詳細な違い | アーキテクチャ、機能、互換性の比較 | guide-differences-detailed |
| Package.json | 依存関係、スクリプト、設定フィールドの移行 | guide-package-json |
移行チェックリスト
移行を実施する際は、次のチェックリストを使用してください。
- [ ] Rename tsup.config.* → tsdown.config.*
- [ ] Update import from 'tsup' to 'tsdown'
- [ ] Replace tsup/TSUP identifiers with tsdown/TSDOWN
- [ ] Apply property renames (cjsInterop→cjsDefault, esbuildPlugins→plugins, outExtension→outExtensions, publicDir→copy, bundle→unbundle, removeNodeProtocol→nodeProtocol, injectStyle→css.inject)
- [ ] Move external/noExternal into deps namespace, replace skipNodeModulesBundle with `deps.neverBundle: true`
- [ ] Update unplugin imports from /esbuild to /rolldown
- [ ] Set explicit defaults to preserve tsup behavior (format, clean, dts, target)
- [ ] Remove unsupported options (splitting, metafile, swc, etc.)
- [ ] Update package.json scripts (tsup→tsdown)
- [ ] Update package.json dependencies (Stage 1: [email protected])
- [ ] Rename root-level tsup config field if present
- [ ] Run tsdown on 0.22.14 and resolve every deprecation warning (zero warnings required)
- [ ] Upgrade to the latest tsdown (^0.23.0 or newer) and verify the build again
- [ ] Suggest new tsdown features to the user