Gulpのタスクをグルーピングしたいです。
Gulpでファイルを生成し、生成したファイルの変数をもとにシンボリックリンクを作成する一連のタスクを作るにはどのようにすればよいでしょうか?
下記が詳細になります。
説明がかなり長くなってしまい恐縮ではありますが、目的から順序立てて説明してまいります。
01. 前提
Gulp を使用しています。開発はローカルで行っています。( browser-sync )
02. 目的・実現したいこと
大目標としては、異なる子プロジェクトへのシンボリックリンクの作成です。
まず、 prj_name/
という親プロジェクトがあり、その下層に _master
と _template
という2つの子プロジェクトがあります。
ファイル構成は下記の様な構造になっております。
下記のように _template/
にも Gulp を入れてあり、目的としては _template/
で Gulp を実行する際に _master/
の共通アセット( A と B )を参照したいのです。
prj_name/
├── _master/
│ ├── _development/
│ │ ├── _assets/
│ │ │ ├── css/
│ │ │ │ └── style.css ← A
│ │ │ └── js
│ │ │ └── bundle.js ← B
│ │ └── index.html
│ └ gulpfile.js
│
└── _template/
├── _development/
│ └── index.html
└ gulpfile.js
上記の prj_name/
は、丸ごとリモートリポジトリに置いてあり、複数人が各自でローカルにクローンし、 _template/
を更新したり、複製・リネームして新規プロジェクトを作成するのですが、 _master/
に入っている JS や CSS などの共通アセットを _template/
や、その派生版のプロジェクトで使用することになっています。共通アセットは _template/
へ(単純にコピーするのではなく)シンボリックリンクとして配置したいのです。
各自がクローンするディレクトリの構造や名称も異なるため、例えば私のローカルのシンボリックリンクをコミットしても他の作業者では当然処理されません。そこで、クローンしたらまず最初に各自でシンボリックリンクの生成を作業の前に行ってもらうことになり、また、そのための Gulp のタスクを用意することになりました。
現段階では Gulp の設定の途中であり、 _template/
へのシンボリックリンクの作成のタスクと、シンボリックリンク作成に必要なJSファイルを生成するタスク自体は用意出来ており、その2つのタスクを順番に実行すれば作業者各自の最初の準備が完了する、というところまで出来ているため大きな問題という訳ではないのですが、 Gulp コマンドを2回も叩かせたくないので、この2つのタスクを1つのタスクにまとめたいのです。
ご教示いただきたいのは1つのタスクにまとめる方法です。
以下、回りくどくなるかとは思いますが順を追って説明してまいります。
この方法以外の代替手段で実現できるのであれば、別の手段でも構いませんm(_ _)m
03. 現段階での Gulp の設定およびディレクトリの説明
_template/
でローカル作業をする際に localhost を立ち上げるので、 _master/
にある共通アセットは相対パスなどを駆使しても参照できません。(ホスト配下にないため…)
そのため、 _master/
にある共通アセットのシンボリックリンクを _template/
内に作成する必要がありました。下記の A' と B' のようなイメージです。
(※ _master
が完成品であれば、共通アセットをコピーするだけでも良いのですが、 _master
はスタイルの追加などの更新がされているため、シンボリックリンクにて同期させる必要があります。今までは毎回コピーして上書きしていましたが、ストレージや作業効率の観点からNGとなりました。)
prj_name/
├── _master/
│ ├── _development/
│ │ ├── _assets/
│ │ │ ├── css/
│ │ │ │ └── style.css ← A
│ │ │ └── js
│ │ │ └── bundle.js ← B
│ │ └── index.html
│ └ gulpfile.js
│
└── _template/
├── _development/
│ ├── _assets/
│ │ └── _symbolic/
│ │ ├── css/
│ │ │ └── style.css ← A'
│ │ └── js
│ │ └── bundle.js ← B'
│ └── index.html
└ gulpfile.js
03.01. タスク - $ gulp symlink
「 A と B のシンボリックリンクを A' と B' に作成する 」・・・
そのためには、シンボリックリンクの元となるファイル( = A と B )へのファイルパスを使用して、Gulp によって処理させています。
03.01.01. ./symlink_config.js
シンボリックリンクの元となるファイルのファイルパスを記述した、 './symlink_config.js'
( = C' )を用意し、それを元にシンボリックリンクの作成を行うことにしました。
※なぜ C' なのか(なぜダッシュを付けているのか)は、後に C が出てくるためです。
一時的に分かりづらいですがご容赦下さい。
prj_name/
├── _master/
│ └── _development/
│ └── _assets/
│ ├── css/
│ │ └── style.css ← A
│ └── js
│ └── bundle.js ← B
│
├── _template/
│ └── _development/
│ └── _assets/
│ └── _symbolic/
│ ├── css/
│ │ └── style.css ← A'
│ └── js
│ └── bundle.js ← B'
│
├── gulpfile.js
└── symlink_config.js ← C'
./symlink_config.js
js
1 2module.exports = { 3 commonPath : [ 4 '/Users/u_name/prj/prj_name/_master/_development/_assets/**/**.css', 5 '/Users/u_name/prj/prj_name/_master/_development/_assets/**/**.js' 6 ] 7};
03.01.02. $ gulp symlink
./symlink_config.js
( = C' )に記載されている値をもとに vinyl-fs で生成する、symlink
というタスクを用意しました。
./gulpfile.js
js
1var gulp = require('gulp'); 2var symlink = require('gulp-sym'); 3var vfs = require('vinyl-fs'); 4var symlink_config = require('./symlink_config'); 5 6gulp.task('symlink', function () { 7 return vfs.src(symlink_config.commonPath, {followSymlinks: false}) 8 .pipe(vfs.symlink('_template/_development/_assets/_symbolic/')); 9});
これにより( $ gulp symlink
を実行することで) A' と B' は正常に作成されました。
03.02. タスク - $ gulp symlink_config_create
しかし、 ./symlink_config.js
( = C' ) 内に記述している commonPath
(クローンしたプロジェクトのあるローカルのファイルパスを入れている変数)は、作業者ごとにフォルダ構造やユーザー名が変わるため、作業する前に作業者ごとに ./symlink_config.js
( = C' ) を作成する必要があります。
03.02.01. ./.origin_files/symlink_config.js
これ(作業する前に作業者ごとに C を作成する作業)を手作業で行うのは手間なので、別のディレクトリに C' の元ファイルとなる
./.origin_files/symlink_config.js
( = C )を用意し、それをもとに C' を作成することにしました。
prj_name/
├── _master/
│ └── _development/
│ └── _assets/
│ ├── css/
│ │ └── style.css ← A
│ └── js
│ └── bundle.js ← B
│
├── _template/
│ └── _development/
│ └── _assets/
│ └── _symbolic/
│ ├── css/
│ │ └── style.css ← A'
│ └── js
│ └── bundle.js ← B'
│
├── .origin_files/
│ └── symlink_config.js ← C
│
├── gulpfile.js
└── symlink_config.js ← C'
./.origin_files/symlink_config.js
js
1 2module.exports = { 3 commonPath : [ 4 'FILEPATH/_master/_development/_assets/**/**.css', 5 'FILEPATH/_master/_development/_assets/**/**.js' 6 ] 7}; 8
文字列 FILEPATH
の部分は仮のファイルパスであり、タスクの実行の際に正規のファイルパスで書き換えを行うという考えです。
03.02.02. $ gulp symlink_config_create
次に、このファイル( = C )を ./.origin_files/
から ./
へ dest し、その際に仮のファイルパスである文字列 FILEPATH
が正規のファイルパスへ置換されるタスクとして、 symlink_config_create
を用意しました。
./gulpfile.js
js
1gulp.task('symlink_config_create', function() { 2 return gulp 3 .src(['./.origin_files/symlink_config.js']) 4 .pipe(replace('FILEPATH', path.resolve())) 5 .pipe(gulp.dest('./')); 6});
これにより C' は正常に作成されました。
ここまでは正常に動作ています
$ gulp symlink_config_create
$ gulp symlink
いずれも、正常に動作します。
問題はここからとなります。
04. 問題
問題というほどの問題ではないのですが、この2つのタスクは作業者が最初にクローンして npm install してからまずたたいてもらうものなので、手間がかかると感じています。
なので、この2つのタスクを1つにまとめたタスクを用意したいのです。
04.01. この様にしたい
通常はタスクをグルーピングする場合、例えば、
./gulpfile.js
js
1// CSSを納品用フォルダへ持っていく 2gulp.task('css-dest', function () { 3 return gulp.src('./css/*.css') 4 .pipe(gulp.dest('./district/css')); 5}); 6 7// JSを圧縮して納品用フォルダへ持っていく 8gulp.task('js-dest', function () { 9 return gulp.src(paths.js + '/**/*.js') 10 .pipe(uglify()) 11 .pipe(gulp.dest('./district/js')); 12});
などのタスクがあるとした場合、
./gulpfile.js
js
1// いっぺんに納品用ファイルを生成する 2gulp.task('dest', function () { 3 gulp.run('css-dest'); 4 gulp.run('js-dest'); 5});
の様にして1つのタスクにできますよね?
これと同様に、前回用意してある2つのタスクをグルーピングした 'pj_init_1' というタスクを下記の様に用意しましたが…
04.02. 試したこと
下記の通り、 Gulp にて3つほど試しています。
04.02.01 試したこと その1 単純に
./gulpfile.js
js
1gulp.task('pj_init_1', function () { 2 gulp.run('symlink_config_create'); 3 gulp.run('symlink'); 4});
symlink_config_create
までは正常に動作しています。
エラーの内容は下記のようなものです。
machine_name:prj_name u_name$ gulp pj_init_1 [18:09:42] Using gulpfile ~/prj/prj_name/gulpfile.js [18:09:42] Starting 'pj_init_1'... gulp.run() has been deprecated. Use task dependencies or gulp.watch task triggering instead. [18:09:42] Starting 'symlink_config_create'... [18:09:42] Starting 'symlink'... [18:09:42] 'symlink' errored after 430 μs [18:09:42] Error: Invalid glob argument: undefined at Object.src (/Users/u_name/prj/prj_name/node_modules/vinyl-fs/lib/src/index.js:20:11) at Gulp.<anonymous> (/Users/u_name/prj/prj_name/gulpfile.js:164:13) at module.exports (/Users/u_name/prj/prj_name/node_modules/orchestrator/lib/runTask.js:34:7) at Gulp.Orchestrator._runTask (/Users/u_name/prj/prj_name/node_modules/orchestrator/index.js:273:3) at Gulp.Orchestrator._runStep (/Users/u_name/prj/prj_name/node_modules/orchestrator/index.js:214:10) at Gulp.Orchestrator.start (/Users/u_name/prj/prj_name/node_modules/orchestrator/index.js:134:8) at Gulp.run (/Users/u_name/prj/prj_name/node_modules/gulp/index.js:22:14) at Gulp.run (/Users/u_name/prj/prj_name/node_modules/deprecated/index.js:9:17) at Gulp.<anonymous> (/Users/u_name/prj/prj_name/gulpfile.js:185:7) at module.exports (/Users/u_name/prj/prj_name/node_modules/orchestrator/lib/runTask.js:34:7) [18:09:42] Finished 'pj_init_1' after 8.08 ms [18:09:42] Finished 'symlink_config_create' after 18 ms machine_name:prj_name u_name$
これは勝手な予想になりますが、 Gulp のタスクが並列に処理されているため、 symlink が動作するために必要な symlink_config.js の作成が間に合っていないためなのでしょうか。
04.02.02 試したこと その2 タスクの直列処理
Gulp のタスクが並列に処理されている事が原因であると考え、単純に直列で動作するように下記の pj_init_2
というタスクを用意しました。
./gulpfile.js
js
1var runSequence = require('run-sequence'); 2gulp.task('pj_init_2', function () { 3 return runSequence( 4 'symlink_config_create', 5 'symlink' 6 ); 7});
しかし、これも結果は pj_init_1
の時と同様に、 symlink_config_create
までしか処理されません。
04.02.03 試したこと その3 タスクの依存関係を考慮
他にも symlink
が symlink_config_create
に依存しているのではないかという理由で、第2引数に'symlink_config_create'を入れてみました。
./gulpfile.js
js
1gulp.task('pj_init_3', ['symlink_config_create'], function() { 2 gulp.run('symlink'); 3});
しかしながら、こちらもまた pj_init_1
や pj_init_2
と同様に、 symlink_config_create
までしか処理されませんでした。
正常に処理させるためにはどうしたら良いでしょうか?
また、見落としやご指摘、アドバイスなどがあればご教示頂きたいです。
よろしくお願いいたしますm(_ _)m
回答2件
あなたの回答
tips
プレビュー
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。