ビルドシステム大転換!webpackからViteへの移行実践記

はじめに

こんにちは。AG-Boost事業本部のF石崎です。 この記事では、従来webpackを使用していたプロジェクトのビルドシステムをViteに置き換えた過程について書こうと思います。この記事が、同様の転換を検討しているエンジニアの方への参考になれば幸いかもしれません。

webpackからViteへの移行の動機

  • webpackのビルド時間に対する不満
  • 開発サーバーの起動時間の長さ(プロジェクトのサイズが大きくなってより顕著に感じるようになった)
  • モダンなフロントエンド開発ツールの進化に興味を持ったから

Viteとは

まず、Viteとは何か、その特徴を簡単に説明します。Viteは、現代のJavaScriptフレームワーク用に特化したビルドツールであり、速度と使いやすさを重視しています。ESモジュールを前提とし、不要な再ビルドや再読み込みなく効率的にリソースを扱えるものです。

移行プロセス

ここでは、webpackからViteへの移行プロセスをざっくり解説します。

  1. 事前準備 - プロジェクトの依存関係の整理、不要なコードやプラグインの削除
  2. Viteの導入 - Viteをプロジェクトに導入し、基本的な設定ファイル(vite.config.js)の作成。この段階で、プロジェクトの構造や依存関係に応じて、設定をカスタマイズする必要がある。
  3. webpack固有の機能の置き換え - webpackで利用していたLoaderやPluginsをViteにおけるプラグインで置き換え。ファイルの読み込み、環境変数の管理、CSSプリプロセッサの利用方法などがよくある事例。
  4. 開発サーバーの移行 - Viteの開発サーバーを使用するように変更。具体的にはwebpack-dev-serverからvite devコマンドへ変更。
  5. ビルドコマンドの更新 - webpackのビルドコマンドをVite用に変更します。具体的にはwebpackコマンドからvite buildコマンドへ変更。

移行の際に直面した問題と解決策

問題1: 依存関係の互換性

状況: 使用しているライブラリや依存関係がViteに完全に対応していない。特に、webpack固有のローダーやプラグイン周りで起こった。

解決策: 互換性の問題を解決するため、まずは各依存関係の最新バージョンがViteをサポートしているか確認しました。対応していない場合は、代替のライブラリを探したり、必要であればソースコードを直接修正してViteに適合させる方法をとりました。また、Viteのプラグインエコシステムを活用し、相当する機能を提供するViteプラグインを探すことで、多くの互換性問題を解決することができました。例えば、webpackでcssとsassファイルを扱っていた部分については、vite-plugin-sassを使用して同等の機能を実現しました。

問題2: 環境変数と設定の違い

状況: webpackとViteでは、環境変数の扱い方やプロジェクトの設定方法が異なるので、移行初期に環境設定が正しく読み込まれず、ビルドに失敗するなどの問題が発生した。

解決策: Viteは .env ファイルを基本として環境変数を扱うが、webpackと異なりプレフィックス VITE_ を付ける必要があるので、全ての環境変数に VITE_ プレフィックスを付け直した。また、既存のwebpack設定をVite用に書き換える過程で、vite.config.js ファイル内で環境変数を適切に参照できるように修正し、設定方法の違いを吸収た。特に、webpackで使用していた DefinePlugin に相当する機能を define オプションを使用して解決する等。

問題3: パス解決の問題

状況: 移行中に、webpackで慣れ親しんだエイリアスや相対パスによるモジュール解決がVite環境では期待通りに動作しないケースがあった。特に、プロジェクト内で複雑に設定されたパスエイリアスが、Viteのデフォルト設定では正しく解決されない問題があった。

その他

react-css-modulesを使う際のcss名の名前解決をreactCssModuleのgenerateScopeNameで自作の関数を作って解決したりなど他にも色々ありますが、多すぎるので割愛します。

解決策: vite.config.jsresolve.alias オプション使用した。webpackで設定していたエイリアスを同等の形でViteの設定に追加することで、モジュールの解決方法を統一した。具体的には、プロジェクトのルートディレクトリを基準に相対パスを設定し、以下のように設定ファイルでエイリアスを明示的に定義した。

// vite.config.js
import { defineConfig } from 'vite';
import path from 'path';

export default defineConfig({
  resolve: {
    alias: {
      '@': path.resolve(__dirname, './src'),
      'components': path.resolve(__dirname, './src/components')
      // 他のエイリアスも同様に定義
    },
  },
});

この設定により、webpackの時に設定したパスエイリアスをVite環境でも使えるようになった。

移行後の成果とメリット

webpackからViteへの移行によって、ビルド時間の短縮、開発サーバーの応答性の向上、煩わしいwebpackの設定ファイルから解放されたことがメリットとしては大きく感じました。特に開発時の更新応答速度の向上は、それだけで移行の価値を感じられるものでした。

最後に

webpackからViteへの移行は、プロジェクトにとって大きな変化をもたらしますが、場合によっては修正箇所が多かったりするのでそこそこの覚悟は必要です。がんばってください。

この記事を通じて、実際に移行を行う上での不安を微量ながら取り除くことができれば幸いです。

Viteを活用することで、開発体験は大きく向上し、プロジェクトのパフォーマンスも改善されますので興味がある人はやりましょう。

おわり