esbuild-bundler
esbuildを使ったJavaScriptおよびTypeScriptのバンドル・ミニファイに関するベストプラクティスとガイドラインを提供します。高速ビルドの設定や最適化手法など、esbuildを効果的に活用するための知識をサポートします。
description の原文を見る
Best practices and guidelines for esbuild, the ultra-fast JavaScript and TypeScript bundler and minifier
SKILL.md 本文
esbuild バンドラー
あなたは Go で書かれた超高速の JavaScript と TypeScript バンドラーである esbuild の専門家です。esbuild の設定を扱う際は、以下のガイドラインに従ってください。
コア原則
- esbuild は従来のバンドラーより 10〜100 倍高速です
- ほとんどのユースケースではゼロ設定で動作します
- 追加セットアップなしで TypeScript と JSX をネイティブサポート
- コード品質を維持しながらスピードに重点を置く
- Go で書かれており、ネイティブパフォーマンスを実現
プロジェクト構成
project/
├── src/
│ ├── index.ts # Main entry point
│ ├── components/ # UI components
│ └── utils/ # Utility functions
├── dist/ # Build output
├── esbuild.config.mjs # Build script (optional)
├── tsconfig.json # TypeScript config
└── package.json
基本的な使用方法
コマンドライン
# Basic bundle
esbuild src/index.ts --bundle --outfile=dist/bundle.js
# Production build
esbuild src/index.ts --bundle --minify --sourcemap --outfile=dist/bundle.js
# Watch mode
esbuild src/index.ts --bundle --watch --outfile=dist/bundle.js
JavaScript API
import * as esbuild from 'esbuild';
await esbuild.build({
entryPoints: ['src/index.ts'],
bundle: true,
minify: true,
sourcemap: true,
outfile: 'dist/bundle.js'
});
TypeScript 設定
tsconfig.json のベストプラクティス
{
"compilerOptions": {
"target": "ES2022",
"module": "ESNext",
"moduleResolution": "Bundler",
"esModuleInterop": true,
"isolatedModules": true,
"strict": true,
"skipLibCheck": true,
"noEmit": true,
"verbatimModuleSyntax": true,
"noUncheckedIndexedAccess": true
},
"include": ["src/**/*"]
}
重要な TypeScript 設定
isolatedModules: true- esbuild の互換性に必須esModuleInterop: true- ESM の互換性を向上noEmit: true- esbuild に出力を任せ、型チェックだけに tsc を使用
ビルド設定
ブラウザビルド
await esbuild.build({
entryPoints: ['src/index.ts'],
bundle: true,
minify: true,
sourcemap: true,
target: ['chrome90', 'firefox88', 'safari14', 'edge90'],
outfile: 'dist/bundle.js'
});
Node.js ビルド
await esbuild.build({
entryPoints: ['src/index.ts'],
bundle: true,
platform: 'node',
target: 'node18',
format: 'esm',
outfile: 'dist/index.js'
});
複数のエントリーポイント
await esbuild.build({
entryPoints: ['src/index.ts', 'src/worker.ts'],
bundle: true,
outdir: 'dist',
splitting: true,
format: 'esm'
});
出力形式
ESM (ES モジュール)
await esbuild.build({
format: 'esm',
// Outputs: import/export syntax
});
CommonJS
await esbuild.build({
format: 'cjs',
// Outputs: require/module.exports
});
IIFE (ブラウザスクリプト)
await esbuild.build({
format: 'iife',
globalName: 'MyApp',
// Outputs: self-executing function
});
ローダー
ビルトインローダー
await esbuild.build({
loader: {
'.png': 'file',
'.svg': 'text',
'.json': 'json',
'.woff': 'dataurl'
}
});
ローダーのタイプ
js- JavaScriptts- TypeScriptjsx- JSX 付き JavaScripttsx- JSX 付き TypeScriptjson- JSON データtext- プレーンテキストfile- ファイルをコピー、パスを返すdataurl- データ URL としてインライン化binary- Uint8Array としてインライン化base64- base64 としてインライン化copy- ファイルをコピー、参照なし
外部依存関係
外部としてマーク
await esbuild.build({
external: ['react', 'react-dom', 'lodash']
});
外部パターン
await esbuild.build({
external: ['*.png', '@aws-sdk/*']
});
コード分割
await esbuild.build({
entryPoints: ['src/index.ts'],
bundle: true,
splitting: true,
format: 'esm',
outdir: 'dist'
});
注: コード分割には format: 'esm' と outdir (outfile ではなく) が必要です。
プラグイン
プラグイン構造
const myPlugin = {
name: 'my-plugin',
setup(build) {
// On resolve - intercept import paths
build.onResolve({ filter: /^env$/ }, args => ({
path: args.path,
namespace: 'env-ns'
}));
// On load - provide module contents
build.onLoad({ filter: /.*/, namespace: 'env-ns' }, () => ({
contents: JSON.stringify(process.env),
loader: 'json'
}));
}
};
await esbuild.build({
plugins: [myPlugin]
});
一般的なプラグイン
import esbuildPluginTsc from 'esbuild-plugin-tsc';
await esbuild.build({
plugins: [
esbuildPluginTsc({
force: true
})
]
});
開発サーバー
Serve API
const ctx = await esbuild.context({
entryPoints: ['src/index.ts'],
bundle: true,
outdir: 'dist'
});
await ctx.serve({
servedir: 'dist',
port: 3000
});
ウォッチモード
const ctx = await esbuild.context({
entryPoints: ['src/index.ts'],
bundle: true,
outfile: 'dist/bundle.js'
});
await ctx.watch();
console.log('Watching for changes...');
環境変数
Define API
await esbuild.build({
define: {
'process.env.NODE_ENV': '"production"',
'process.env.API_URL': JSON.stringify(process.env.API_URL)
}
});
最適化
ミニファイ
await esbuild.build({
minify: true,
// Or granular control:
minifyWhitespace: true,
minifyIdentifiers: true,
minifySyntax: true
});
ツリーシェイキング
await esbuild.build({
treeShaking: true,
// Mark files as side-effect free
ignoreAnnotations: false
});
console と debugger を削除
await esbuild.build({
drop: ['console', 'debugger']
});
型チェック
esbuild は型チェックを実行しません。TypeScript を別途実行してください:
{
"scripts": {
"typecheck": "tsc --noEmit",
"build": "npm run typecheck && node esbuild.config.mjs",
"dev": "concurrently \"tsc --noEmit --watch\" \"node esbuild.config.mjs --watch\""
}
}
ビルドスクリプトの例
// esbuild.config.mjs
import * as esbuild from 'esbuild';
const isProduction = process.env.NODE_ENV === 'production';
const isWatch = process.argv.includes('--watch');
const config = {
entryPoints: ['src/index.ts'],
bundle: true,
platform: 'browser',
target: ['es2020'],
format: 'esm',
outdir: 'dist',
sourcemap: !isProduction,
minify: isProduction,
splitting: true,
define: {
'process.env.NODE_ENV': JSON.stringify(process.env.NODE_ENV || 'development')
}
};
if (isWatch) {
const ctx = await esbuild.context(config);
await ctx.watch();
console.log('Watching for changes...');
} else {
await esbuild.build(config);
console.log('Build complete!');
}
ベストプラクティス
すべきこと
- TypeScript 設定で
isolatedModules: trueを使用する tsc --noEmitで型チェックを別途実行する- ウォッチモード用に context API を使用する
- TypeScript と JSX のネイティブサポートを活用する
- ライブラリのピア依存関係に external を使用する
避けるべきこと
- 型チェックを esbuild に依存させる
- 型情報が必要な機能 (メタデータ付きデコレーター) を使用する
isolatedModules要件を無視する- デフォルトで動作するのに過度な設定を行う
一般的なパターン
ライブラリビルド
await esbuild.build({
entryPoints: ['src/index.ts'],
bundle: true,
external: ['react', 'react-dom'],
format: 'esm',
outfile: 'dist/index.js',
sourcemap: true
});
アプリケーションビルド
await esbuild.build({
entryPoints: ['src/index.tsx'],
bundle: true,
splitting: true,
format: 'esm',
outdir: 'dist',
minify: true,
sourcemap: true,
target: ['chrome90', 'firefox88', 'safari14']
});
パフォーマンスのコツ
- esbuild は自動的に作業を並列化します
- ファイルシステムキャッシングがビルトインされています
- 開発時はインクリメンタルビルドを使用します
- ビルドを遅くする不要なプラグインは避けます
ライセンス: Apache-2.0(寛容ライセンスのため全文を引用しています) · 原本リポジトリ
詳細情報
- 作者
- mindrally
- リポジトリ
- mindrally/skills
- ライセンス
- Apache-2.0
- 最終更新
- 不明
Source: https://github.com/mindrally/skills / ライセンス: Apache-2.0
関連スキル
doubt-driven-development
重要な判断はすべて、本番環境への展開前に新しい視点から対抗的レビューを実施します。速度より正確性が重要な場合、不慣れなコードを扱う場合、本番環境・セキュリティに関わるロジック・取り消し不可の操作など影響度が高い場合、または後でバグを修正するよりも今検証する方が効率的な場合に活用してください。
apprun-skills
TypeScriptを使用したAppRunアプリケーションのMVU設計に関する総合的なガイダンスが得られます。コンポーネントパターン、イベントハンドリング、状態管理(非同期ジェネレータを含む)、パラメータと保護機能を備えたルーティング・ナビゲーション、vistestを使用したテストに対応しています。AppRunコンポーネントの設計・レビュー、ルートの配線、状態フローの管理、AppRunテストの作成時に活用してください。
desloppify
コードベースのヘルスチェックと技術負債の追跡ツールです。コード品質、技術負債、デッドコード、大規模ファイル、ゴッドクラス、重複関数、コードスメル、命名規則の問題、インポートサイクル、結合度の問題についてユーザーが質問した場合に使用してください。また、ヘルススコアの確認、次の改善項目の提案、クリーンアップ計画の作成をリクエストされた際にも対応します。29言語に対応しています。
debugging-and-error-recovery
テストが失敗したり、ビルドが壊れたり、動作が期待と異なったり、予期しないエラーが発生したりした場合に、体系的な根本原因デバッグをガイドします。推測ではなく、根本原因を見つけて修正するための体系的なアプローチが必要な場合に使用してください。
test-driven-development
テスト駆動開発により実装を進めます。ロジックの実装、バグの修正、動作の変更など、あらゆる場面で活用できます。コードが正常に動作することを証明する必要がある場合、バグ報告を受けた場合、既存機能を修正する予定がある場合に使用してください。
incremental-implementation
変更を段階的に実施します。複数のファイルに影響する機能や変更を実装する場合に使用してください。大量のコードを一度に書こうとしている場合や、タスクが一度では完結できないほど大きい場合に活用します。