謎言語使いの徒然

適当に気になった技術や言語を流すブログ。

現時点で Reactを Gulp 上コンパイルして見る

教科書はこれ

qiita.com

package.json をしれっと。

{
  "name": "react-base",
  "version": "0.1.0",
  "description": "React base application template",
  "main": "index.js",
  "scripts": {
    "test": "echo \"Error: no test specified\" && exit 1"
  },
  "author": "",
  "license": "BSD-2-Clause",
  "dependencies": {
    "gulp-util": "^3.0.8",
    "react": "^15.6.1",
    "react-dom": "^15.6.1"
  },
  "devDependencies": {
    "autoprefixer": "^7.1.2",
    "babel": "^6.23.0",
    "babel-preset-es2015": "^6.24.1",
    "babel-preset-react": "^6.24.1",
    "babelify": "^7.3.0",
    "browserify": "^14.4.0",
    "cssnano": "^3.10.0",
    "gulp": "^3.9.1",
    "gulp-postcss": "^7.0.0",
    "gulp-sass": "^3.1.0",
    "gulp-sourcemaps": "^2.6.0",
    "gulp-uglify": "^3.0.0",
    "gulp-webserver": "^0.9.1",
    "rimraf": "^2.6.1",
    "vinyl-buffer": "^1.0.0",
    "vinyl-source-stream": "^1.1.0"
  },
  "scripts": {
    "start": "gulp",
    "clean": "gulp clean",
    "compile": "gulp compile"
  }
}

とりあえず各バージョンは上記の通り。
その上で gulpfile.js を下記のようにすればまずコンパイルできる

var gulp = require('gulp');
var gutil = require('gulp-util');

var browserify = require('browserify');
var babelify = require('babelify');

var source = require('vinyl-source-stream');
var buffer = require('vinyl-buffer');
var sourcemaps = require('gulp-sourcemaps');

var uglify = require('gulp-uglify');

var webserver = require('gulp-webserver');

let SOURCE_DIR = './src';
let JS_SOURCE_DIR = SOURCE_DIR + '/main';

let DIST_DIR = './dist';

// React コードのコンパイル設定
let jsCompileTask = browserify({
  entries: [ JS_SOURCE_DIR + '/index.js'],
  transform: ['babelify'],
  cache: {},
  packageCache: {}
});

// コンパイル実行箇所
function compileJs() {
  function createErrorHandler(name) {
    return function (err) {
      console.error('Error from ' + name + ' in compress task', err.toString());
    };
  }

  return jsCompileTask.bundle() // ソースをコンパイル
    .on('error', gutil.log.bind(gutil, 'Browserify Error')) // コンパイルエラー出力
    .pipe(source('main.min.js')) // 全てのソースをまとめた JavaScript 出力名
    .pipe(buffer())  // バッファリング
    .pipe(sourcemaps.init({loadMaps: true})) // 既に出てるソースマップ取り込み
    .pipe(uglify())  // コード圧縮
    .on('error', createErrorHandler('uglify'))  // エラーメッセージ
    .pipe(sourcemaps.write('./'))  // デバッグ情報出力
    .pipe(gulp.dest(DIST_DIR + '/js'));  // 出力ディレクトリ
}

function runServer() {
  gulp.src(DIST_DIR)
    .pipe(webserver({
      livereload: true,
      open: true,
      fallback: '/index.html'
    }));  
}

function watch() {
  gulp.watch(JS_SOURCE_DIR + '/**/*.js', ['compileJs']);
}

gulp.task('compileJs', compileJs);

gulp.task('compile', ['compileJs'])

gulp.task('watch', watch);
gulp.task('debug', ['compile', 'watch'], runServer);

gulp.task('default', ['debug']);

後は scss でもなんでもすればおk

ただし、この構成は欠点があって、CSS ファイルを include すると死ぬ。
多分 babel-preset-react の問題だと思う。