前書き
w2uiというjQueryのUIプラグインを、Laravel Mixを使って管理しようとしたのですが、苦労したので残しておきます。w2ui以外にも、CommonJSに対応していないライブラリを使う時に応用が効くと思います。
Mixを使う事により、npm管理したり、モジュール化されたり、jsをまとめたり、まとまったjsのキャッシュをコントロールしたりできます。
Laravel Mixの概要についてはこちら。基本的なセットアップは済んでいるものとして説明します。
アセットのコンパイル(Laravel Mix) 5.4 Laravel
w2uiについてはこちらを参照してください。
100万行扱えるグリッドw2ui GridとHandsontableの紹介 - Qiita
環境
MacVagrant上で構築したCentOS
Laravel5.4(5.4で検証しましたが、他のバージョンでも同じように使えると思います)
yarn(互換性があるのでnpmでも同じになるはずです)
(yarnとnpmコマンドの互換はこちら yarnを使ってみた - Qiita)
バージョンの罠
まず、w2uiのバージョンについて説明する必要があります。
公式ページ(Home | JavaScript UI - w2ui) からDownloadしたり、GitHubのmasterを参照すると1.5.rc1が、npmから取得するとstableな1.4が取得されます。
Laravel mixはwebpackをラップしており、CommonJSに対応していればrequireするだけで簡単に動きます。
が、1.4系はCommonJSに対応していないため、単純にrequireしても動きません。
逆に1.5系はnpmに登録されていません。
というわけで、作戦としては2つ考えられます
- npmから取得した1.4系を頑張ってCommonJS対応して使う
- 1.5系をダウンロードするなり、url参照するなりする
最終的に作戦2を採用しましたが(実処理が1.5に依存していたため)、途中までこの事実に気が付かずに作戦1も検証していました。というわけで、作戦1についてもいけた所までは公開しておきます。
手順 作戦1.npmから取得した1.4系を頑張ってCommonJS対応して使う
packageの取得
yarn add w2ui
w2ui使う処理
$(window).on('load', function() {
w2utils.locale('ja-jp.json');
$('#grid').w2grid({
name: 'grid',
recid:'id',
method: 'GET',
// 省略
});
w2ui['grid'].load('hogeAction');
色々機能があるのですが、今回はこんな感じの処理にしていました。
w2tils
やw2ui
というグローバルな変数がある前提の処理になっています。
app.jsへの組み込み
var w2uiModule = require('exports-loader?w2ui,w2utils,w2obj!w2ui');
window.w2utils = w2uiModule["w2utils"];
window.w2ui = w2uiModule["w2ui"];
window.w2obj = w2uiModule["w2obj"];
前述の通り、w2tils
やw2ui
というグローバルな変数がある事にしないといけません。
1.4系はCommonJSに対応していない(exports記述が無い)ので、var w2uiModule = require('w2ui');
としてもw2uiModule
は空objectです。
そこで、exports-loaderという特殊なloaderを指定し、取得したい値を指定する事で、w2uiモジュールの値を外部に取り出す事が可能です。exports-loaderはyarn(npm)で取得しておく必要があります。
LaravelMixは内部的にwebpackを使っているため、こういった便利なwebpackの機能を使う事ができます。loaderについてはこちらを参考にしました。
webpackを使い倒す - Thujikun blog
また、似たようなissueもあがっていたので、同じく参考にしました。
Compatibility with browserify · Issue #712 · vitmalina/w2ui
手順 作戦2 1.5系をダウンロードするなり、url参照するなりする
packageの取得
扱うファイルを固定にしたかったので(本体が更新されても影響しない)、公式ページからダウンロードして、resouces/assets/jsにjsファイルを、resouces/assets/sassにcssファイルを直接配置します。
w2ui使う処理
作戦1と同じ
app.jsへの組み込み
var w2uiModule = require('./w2ui.min.js');
window.w2utils = w2uiModule["w2utils"];
window.w2ui = w2uiModule["w2ui"];
今度は単純にrequire
で取得できます。
以下のような処理がw2uiに記述されていて、CommonJSに対応しているからです。
(function(global, w2ui) {
if (typeof define=='function' && define.amd) {
return define(function(){ return w2ui; });
}
if (typeof exports!='undefined') {
if (typeof module!='undefined' && module.exports)
return exports = module.exports = w2ui;
global = exports;
}
for (var m in w2ui) {
global[m] = w2ui[m];
}
})(this, { w2ui: w2ui, w2obj: w2obj, w2utils: w2utils });
app.cssへの組み込み
app.scssに
@import "w2ui.min.css";
と書けばapp.cssにコンパイルされます。
まとめ
webpackの便利機能を使って、CommonJSに対応していないライブラリを頑張って対応する事もできました。(最終的には作戦2を採用したのですが)
LaravelMixのドキュメントや使用事例はまだ少ないのですが、困った時はwebpackを調査する事で色々対応が可能そうです。