回答の準備
まず、以下のようなディレクトリ構造を作成し、
test_project
├ node_modules
├ sass
│ ├ reset
│ │ └ _reset.scss
│ └ style.scss
├ gulpfile.js
└ package.json
package.json
を以下のように、
JSON
1{
2 "name": "test_project",
3 "version": "1.0.0",
4 "description": "",
5 "main": "index.js",
6 "scripts": {
7 "test": "echo \"Error: no test specified\" && exit 1"
8 },
9 "keywords": [],
10 "author": "",
11 "license": "ISC",
12 "devDependencies": {
13 "autoprefixer": "^9.4.7",
14 "css-mqpacker": "^7.0.0",
15 "gulp": "^4.0.0",
16 "gulp-postcss": "^8.0.0",
17 "gulp-sass": "^4.0.2",
18 "gulp-sass-glob": "^1.0.9",
19 "gulp-sourcemaps": "^2.6.4"
20 },
21 "dependencies": {}
22}
gulpfile.js
を以下のように、
JavaScript
1'use strict';
2
3var gulp = require('gulp');
4var sass = require('gulp-sass');
5var sassGlob = require('gulp-sass-glob');//①「gulp-sass-glob」を読み込み
6var sourcemaps = require('gulp-sourcemaps');//「gulp-sourcemaps」を読み込み
7var autoprefixer = require('autoprefixer');//「autoprefixer」を読み込み
8var mqpacker = require('css-mqpacker');//①「css-mqpacker」を読み込み
9sass.compiler = require('node-sass');
10
11gulp.task('sass', function () {
12 return gulp.src('./sass/**/*.scss')
13 .pipe(sourcemaps.init())//②「gulp.src」の直後に指定
14 .pipe(sassGlob())//②「sass」の前に指定
15 .pipe(sass().on('error', sass.logError))
16 .pipe(sass({outputStyle: 'expanded'}))
17 .pipe(postcss([mqpacker()]))//②「sass」の後に指定
18 .pipe(postcss([autoprefixer()]))//②「sass」の後に指定
19 .pipe(sourcemaps.write())//③「gulp.dest」の直後に指定
20 .pipe(gulp.dest('./css'));
21});
22
23gulp.task('sass:watch', function () {
24 gulp.watch('./sass/**/*.scss', ['sass']);
25});
./sass/style.scss
を以下のように、
SCSS
1@import './reset/reset';
2
3body {
4 font: 100% Helvetica, sans-serif;
5 background-color: #efefef;
6}
./sass/reset/reset.scss
を以下のようにしました。
SCSS
1html,
2body,
3ul,
4ol {
5 margin: 0;
6 padding: 0;
7}
ここで、sass:watch
タスクを実行すると、以下のようにエラーが再現しました。
bash
1C:\Users\s8_chu\Desktop\test_project>npx gulp sass:watch
2[21:19:50] Using gulpfile ~\Desktop\test_project\gulpfile.js
3[21:19:50] Starting 'sass:watch'...
4[21:19:50] 'sass:watch' errored after 2.47 ms
5[21:19:50] Error: watching ./sass/**/*.scss: watch task has to be a function (optionally generated by using gulp.parallel or gulp.series)
6 at Gulp.watch (C:\Users\s8_chu\Desktop\test_project\node_modules\gulp\index.js:28:11)
7 at C:\Users\s8_chu\Desktop\test_project\gulpfile.js:25:8
8 at taskWrapper (C:\Users\s8_chu\Desktop\test_project\node_modules\undertaker\lib\set-task.js:13:15)
9 at bound (domain.js:396:14)
10 at runBound (domain.js:409:12)
11 at asyncRunner (C:\Users\s8_chu\Desktop\test_project\node_modules\async-done\index.js:55:18)
12 at process._tickCallback (internal/process/next_tick.js:61:11)
13
回答
上記のエラー文に書かれているとおり、gulp 4.x からは、gulp.watch
の取る引数が変更されました。
これにより、gulp.watch
に設定している引数の値が gulp に理解できない状態になっていることが、今回のエラーの原因です。 gulp の API ドキュメントを読むと、gulp 4.x からは、gulp.watch(globs[, opts][, fn])
のように引数を取ることがわかります。
gulp 3.9.1 の場合
gulp.watch(glob [, opts], tasks) or gulp.watch(glob [, opts, cb])
Watch files and do something when a file changes. This always returns an EventEmitter that emits change events.
参考: gulp/API.md at v3.9.1 · gulpjs/gulp · GitHub
gulp 4.0.0 の場合
gulp.watch(globs[, opts][, fn])
Takes a path string, an array of path strings, a glob string or an array of glob strings as globs to watch on the filesystem. Also optionally takes options to configure the watcher and a fn to execute when a file changes.
参考: gulp/API.md at v4.0.0 · gulpjs/gulp · GitHub
そのため、今回の質問文のコードを以下のように変更することで、
JavaScript
1'use strict';
2
3var gulp = require('gulp');
4var sass = require('gulp-sass');
5var sassGlob = require('gulp-sass-glob');
6var sourcemaps = require('gulp-sourcemaps');
7var autoprefixer = require('autoprefixer');
8var mqpacker = require('css-mqpacker');
9var postcss = require('gulp-postcss');
10sass.compiler = require('node-sass');
11
12gulp.task('sass', function () {
13 return gulp.src('./sass/**/*.scss')
14 .pipe(sourcemaps.init())
15 .pipe(sassGlob())
16 .pipe(sass().on('error', sass.logError))
17 .pipe(sass({outputStyle: 'expanded'}))
18 .pipe(postcss([mqpacker()]))
19 .pipe(postcss([autoprefixer()]))
20 .pipe(sourcemaps.write())
21 .pipe(gulp.dest('./css'));
22});
23
24gulp.task('sass:watch', function () {
25 gulp.watch('./sass/**/*.scss', gulp.series('sass')); // 変更
26});
gulp:watch
タスクがエラーなく行えるようになると思います。
bash
1C:\Users\s8_chu\Desktop\test_project>npx gulp sass:watch
2[21:29:19] Using gulpfile ~\Desktop\test_project\gulpfile.js
3[21:29:19] Starting 'sass:watch'...
4[21:30:37] Starting 'sass'...
5[21:30:37] Finished 'sass' after 120 ms
また、質問文のpackage.json
の場合、sass
タスクを実行するためにgulp-postcss
パッケージをインストールしておく必要があると思います。
bash
1npm i -D gulp-postcss