PHP

Laravel Mixでwebpackをもっと簡単に使う方法

2017/07/10

Lasse Rafn

28

Articles in this issue reproduced from SitePoint
Copyright © 2017, All rights reserved. SitePoint Pty Ltd. www.sitepoint.com. Translation copyright © 2017, KADOKAWA CorporationJapanese syndication rights arranged with SitePoint Pty Ltd, Collingwood, Victoria,Australia through Tuttle-Mori Agency, Inc., Tokyo

Laravel本体を使わない小規模なプロジェクトでも、webpackのAPIラッパー「Laravel Mix」を使えばwebpackをもっと手軽に設定できます。チュートリアルでセットアップの簡単さを体験してください。

Laravel Mixなら、webpackのようなビルドツールの設定に時間を費やすことなくプロジェクトに着手できます。さらに、アセットのコンパイルが驚くほど簡単です。Laravel MixをLaravel以外のプロジェクトでも使う方法を紹介します。

Laravel Mixを使う理由

Laravel Mix(旧名Elixir)は、webpackのAPIラッパーです。文法は洗練されていて簡単に使用できます。バージョン管理、ホットリロード、アセットビルドとコンパイルは、設定ファイルにコードを数行追加するだけでセットアップできます。

経緯

私は、仕事でもプライベートでも大半のプロジェクトでLaravelを使っていました。最近、ページとコンテンツをWebサイト上で編集する機能が必要な案件があり、クライアントがCMSを指定したのです。そこで、LaravelベースのOctoberCMSを試すことにしました。

PhpStormからFile Watcherをセットアップするも、Laravel Mixのようには動きませんでした。1週間File Watcherを使ったあと、LaravelプロジェクトからLaravel Mixを取得すると狙い通りの結果になりました。

要件

注意:本記事はJSONファイルの基礎的な理解と、npmNodeをインストールしている前提で執筆しています。

バージョン管理とホットリロードには、PHPとComposerが必要です。

NPMとNodeをインストールしているかは、次のコマンドをターミナルで実行して確認できます。

node -v
npm -v

Nodeとnpmのバージョンが表示されます。

参考:これらのパッケージを一括でインストールするにはHomestead Improvedがオススメです。

インストールと準備

ターミナルかコンソールアプリケーションを起動します。既存のプロジェクトがなく空のプロジェクトを立ち上げるには、任意の場所に空のプロジェクトディレクトリを作ります。初期ファイルなどは不要です。

Laravel MixとSassをインストールする

Laravel Mixのインストールは、プラットホームを超えて環境変数を使うために、依存オブジェクト「cross-env」が必要です。また、Sassファイルのコンパイルに「node-sass」を使います。

次のコマンドを実行して、Laravel MixとSass、cross-envをインストールします。

npm install laravel-mix cross-env node-sass --save-dev

インストールが完了すると、ディレクトリ「node_modules」が作成され、package.jsonファイルが更新されます。

バージョン管理は、node_modules.gitignoreファイルに追加して利用します。

webpack Mixファイルを作成する

Laravel Mixはwebpackの設定ファイルの作成が不要で、コンパイル対象のアセットを指定するファイルを作成するだけです。私が大半のプロジェクトでLaravel Mixを使っている理由です。

プロジェクトのルートディレクトリにファイル「webpack.mix.js」を作成し、次のコードを追加します。

const mix = require('laravel-mix');

mix.js('resources/js/app.js', 'public/js')
   .sass('resources/sass/app.scss', 'public/css');

webpackでコンパイルするJavascriptファイルとSCSS/Sassファイル、さらに出力するディレクトリを定義します。ファイル名と出力名は自由に設定できます。この記事ではmix.js(..).sass(..)コードを「ミックスチェーン」と呼びます。

スクリプトをpackage.jsonに追加する

Mixを使うには、スクリプトをpackage.jsonファイルに加えます。Laravelに準じるため、Laravel 5.4プロジェクトから直接コピーしました。

ファイルにスクリプト変数があれば、削除してください。

コードエディターでpackage.jsonファイルを開いて、scriptsconfig変数を追加します。

  "scripts": {
    "dev": "node node_modules/cross-env/dist/bin/cross-env.js NODE_ENV=development node_modules/webpack/bin/webpack.js --progress --hide-modules --config=node_modules/laravel-mix/setup/webpack.config.js",
    "watch": "node node_modules/cross-env/dist/bin/cross-env.js NODE_ENV=development node_modules/webpack/bin/webpack.js --watch --progress --hide-modules --config=node_modules/laravel-mix/setup/webpack.config.js",
    "hot": "node node_modules/cross-env/dist/bin/cross-env.js NODE_ENV=development node_modules/webpack-dev-server/bin/webpack-dev-server.js --inline --hot --config=node_modules/laravel-mix/setup/webpack.config.js",
    "production": "node node_modules/cross-env/dist/bin/cross-env.js NODE_ENV=production node_modules/webpack/bin/webpack.js --progress --hide-modules --config=node_modules/laravel-mix/setup/webpack.config.js"
  },

完成したファイルです。

コンパイルするアセットを作成

webpack.mix.jsファイルにコンパイル対象のファイルを定義しましたが、新しいプロジェクトには、これらのファイルが存在していない可能性があります。次のようなディレクトリ構造にしてください。

folder-structure.png

なにかコンテンツをresources/sass/app.sassファイルに追加してテストします。

body {
    background: red;
}

Laravel Mixを実行する

動作を確認するため、次のコマンドを実行します。

npm run dev

次の画面が表示されればOKです。

webpack.png

キャッシュバスティングとホットリロードを設定

ホットリロードは、ブラウザーへ再読み込みなしでアセットの変更を即座に反映します。変更を加えるたびに自動的に最新版のファイルが挿入されるので、CSSの調整に役立ちます。

Laravel MixはBrowserSyncでホットリロードを実装しています。BrowserSyncには、ほかのデバイスのコンテンツを閲覧する機能や、入力やスクロールなどの状態をデバイス間で同期する機能など、便利な機能があります。

キャッシュバスティングとは、ブラウザーのキャッシュを使えなくすることです。app.jsapp.b2328beb0372c051d06d.jsに変更するように、コンパイルしたアセットにハッシュを追加することで実現し、ファイルをサーバーからブラウザーに強制的にダウンロードします。

キャシュバスティングとホットリロードの設定は、Laravelと同じmix()メソッドを含むphpファイルを読み込みます。

mix()は基礎的なヘルパーメソッドで、指定したバージョンのアセットを見つけてホットリロードが有効化しているか確認します。

プロジェクトのルートディレクトリや好きな場所にmix.phpファイルを作成し、次のコードを追加します。

<?php
 if (! function_exists('mix')) {
    /**
     * Get the path to a versioned Mix file.
     *
     * @param string $path
     * @param string $manifestDirectory
     * @return string
     *
     * @throws \Exception
     */
    function mix($path, $manifestDirectory = '')
    {
        static $manifest;
        $publicFolder = '/public';
        $rootPath = $_SERVER['DOCUMENT_ROOT'];
        $publicPath = $rootPath . $publicFolder;
        if ($manifestDirectory && ! starts_with($manifestDirectory, '/')) {
            $manifestDirectory = "/{$manifestDirectory}";
        }
        if (! $manifest) {
            if (! file_exists($manifestPath = ($rootPath . $manifestDirectory.'/mix-manifest.json') )) {
                throw new Exception('The Mix manifest does not exist.');
            }
            $manifest = json_decode(file_get_contents($manifestPath), true);
        }
        if (! starts_with($path, '/')) {
            $path = "/{$path}";
        }
        $path = $publicFolder . $path;
        if (! array_key_exists($path, $manifest)) {
            throw new Exception(
                "Unable to locate Mix file: {$path}. Please check your ".
                'webpack.mix.js output paths and try again.'
            );
        }
        return file_exists($publicPath . ($manifestDirectory.'/hot'))
                    ? "http://localhost:8080{$manifest[$path]}"
                    : $manifestDirectory.$manifest[$path];
    }
}

Composerで自動読み込みする

プロジェクトのルートディレクトリに移動し、composer.jsonファイルを開くか、新しく作成します。

PHPリクエストの前にmix.phpを自動的に読み込むためのコードを追加します。

{
    ...

    "autoload": {
        "files": ["mix.php"]
    }

    ...
}

完成したファイルがこちらです。

アセットテスト用のインデックスファイルを作成

バージョン管理が正しく動くことを確認するため、アセットにバージョンを付けます。可能なら加えてホットリロードを有効化します。webpack.mix.jsファイルを開いて、以下の内容に変更します。

const mix = require('laravel-mix');

mix.js('resources/js/app.js', 'public/js')
   .sass('resources/sass/app.scss', 'public/css')
   .version()
   .browserSync(); // Hot reloading

完成したファイルがこちらです。

アセットをテストします。index.phpファイルを作成して、次の確認用コードを追加します。

<?php
  require_once 'vendor/autoload.php';
?>
<!DOCTYPE html>
<html>
  <head>
    <title>Demo</title>
    <link rel="stylesheet" href="<?php echo mix('css/app.css'); ?>" />
  </head>

  <body>
    Hello world.

    <script src="<?php echo mix('js/app.js'); ?>"></script>
  </body>
</html>

ターミナルかコマンドラインで、プロジェクトのルートディレクトリに移動します。

ホットリロードを有効にする場合

ターミナルでnpm run hotを実行し、アセットにバージョンを付けてホットリロードを初期化します。Webページが開いてWebサイトが表示されます。ホットリロードを有効にした場合は、次のサブセクションは不要です。

ホットリロードを有効にしない場合

次のコマンドを実行します。

npm run dev

続いて次のコマンドを実行します。

php -S localhost:8080

PHPサーバーが立ち上がります。

ブラウザーを開いて、ポート8080からWebサイトのURLへ移動します。例:homestead.app:8080

結果

bodyのスタイルをapp.scssファイルに記述した場合は、赤い背景のページが表示されるはずです。

以上で完成です。 Laravel本体なしでLaravel Mixを使って、柔軟にwebpackの設定ができました。Laravel Mixドキュメントも確認してください。

補足

package.jsonファイルには、まだ紹介していないスクリプト/コマンドが2つあります。productionwatchで、どちらも使い方によっては有用です。

production コマンド

本番環境にデプロイするときに、アセットのミニファイ版を作るなら、productionコマンドが役立ちます。

npm run production

本番環境向けにアセットのミニファイ版ができました。

watchコマンド

スクリプトやスタイルを編集するたびにdevを実行するのは生産的ではありません。ファイルが変更されたことを検知してアセットをコンパイルするコマンド「watch」が役立ちます。

npm run watch

watch コマンドを実行中はビルドエラー(特にJSの文法エラー)の内容の特定が難しくなります。困ったらdevコマンドを実行して、通常のアウトプットを確認します。

最後に

細かいプロセスにではなく、とりあえず使いたいならGithubのレポジトリのサンプルプロジェクトを利用ください。

小規模なプロジェクトにおいて、LaravelなしでLaravel Mixを使う最適な方法だと思います。webpackとは異なり、慣れればものの数分でセットアップできるでしょう。

本記事はYounes RafieWern AnchetaChristopher Pittが査読を担当しています。最高のコンテンツに仕上げるために尽力してくれたSitePointの査読担当者のみなさんに感謝します。

(原文:How to Use Laravel Mix in Non-Laravel Projects

[翻訳:内藤 夏樹/編集:Livit

Copyright © 2017, Lasse Rafn All Rights Reserved.

Lasse Rafn

Lasse Rafn

Webのフルスタック開発者であり、VueとLaravelのファン。法人向けWebアプリのデザインと開発が中心で、現在はフルタイム勤務中です。

Loading...