Gulpの続きです。前回はHTMLテンプレートエンジンのPugをGulpでコンパイルしました。今回はEJSのコンパイルにトライ。それではいきましょう!
【目次】
- フォルダ作成→移動→package.json作成→Gulpインストール
- EJSパッケージ(gulp-ejs他)のインストール
- ファイルを作る
- gulpfile.jsにgulp.task()を記述
- index.ejsを作成
- EJSコンパイル実行
- 外部ejsファイルをインクルードする書き方(include)
- SyntaxErrorは何度も起こった
- 最後に
※参考:前回記事
【HTML】PugをGulpでコンパイルしてみる(メタ言語初コンパイル!) - クモのようにコツコツと
※参考:メタ言語(HTMLテンプレートエンジン、AltCSS、AltJS)まとめ
qiita.com
フォルダ作成→移動→package.json作成→Gulpインストール
前回のPugと同じ手順。
※参考:【HTML】PugをGulpでコンパイルしてみる(メタ言語初コンパイル!) - クモのようにコツコツと
node.jsとnpmは入っている前提(下記のコマンドでバージョン番号が出る)
node -v npm -v
コンパイルを実行したいフォルダを作成する。今回は「gulp_ejs」とする。
cdコマンドで移動する
cd /(フォルダ)/gulp_ejs
package.jsonを作成
npm init -y
ローカルにGulpインストール
npm install -D gulp
EJSパッケージ(gulp-ejs他)のインストール
EJSコンパイルに必要なnpmのパッケージをインストールする。こちらの記事を参考に。
※参考:EJSの使い方!静的なHTMLサイトで「共通パーツ」と「変数」を使おう | HPcode
- gulp-ejs:EJSコンパイル
- gulp-rename:拡張子リネイム(.ejs→.html)
- gulp-replace:空白行削除(任意)
まず「gulp-ejs」をインストール
npm install -D gulp-ejs
次に「gulp-rename」
npm install -D gulp-rename
これはEJSファイルの拡張子「.ejs」を「.html」に変換する役割。以前は不要だったが最近はこれがないと拡張子が「.ejs」のままになってしまうとのこと。
※参考:gulp-ejsで拡張子がejsになってしまう問題(.htmlにしたい) - Qiita
最後に「gulp-replace」
npm install -D gulp-replace
後述する「インクルード」時にインクルードファイルに変数を読み込むとEJSコンパイル時に変数の行が空白行になる。その空白行を削除する役割。これは必須ではなくコードの見た目を整える目的でインストールした。
全てインストールが成功するとpackage.jsonに追記された!
"devDependencies": { "gulp": "^4.0.2", "gulp-ejs": "^5.0.0", "gulp-rename": "^2.0.0", "gulp-replace": "^1.0.0" }
ファイルを作る
「gulp_test」フォルダの中に下記の構成のファイルを追加する。前回と似た構成。
当初、common
フォルダの中に_header.ejs
、_footer.ejs
を作った。
gulp_ejs ├ejs │├common ││├_header.ejs ││└_footer.ejs │└index.ejs └gulpfile.js
そのファイルの中身をindex.ejs
でインクルードさせようとした。そしたらコンパイル実行時にSyntaxErrorが起こった。
シンタックスエラーとはコンパイル時にわかる構文エラーのこと。
※参考:https://wa3.i-3-i.info/word14894.html
原因を調べたが、なかなか特定にいたらなかった。。そのため、今回はインクルードは諦めてindex.ejs
ファイル単体でコンパイルすることにした。
gulp_ejs ├ejs │└index.ejs └gulpfile.js
gulpfile.jsにgulp.task()を記述
gulpfile.jsにgulp.task()
メソッドでコンパイルの設定を記述。
const gulp = require("gulp"); const rename = require("gulp-rename"); const ejs = require("gulp-ejs"); const replace = require("gulp-replace"); gulp.task("ejs", done => { gulp .src(["ejs/**/*.ejs", "!ejs/**/_*.ejs"]) .pipe(ejs({}, {}, { ext: ".html" })) .pipe(rename({ extname: ".html" })) .pipe(replace(/[\s\S]*?(<!DOCTYPE)/, "$1")) .pipe(gulp.dest("./")); done(); });
- 変数
gulp
でgulp
を読み込む - 変数
rename
でgulp-rename
を読み込む - 変数
pjs
でgulp-ejs
を読み込む - 変数
replace
でgulp-replace
を読み込む gulp.task()
メソッド実行。第一引数はejs
、第二引数は無名関数で引数はdone
- 無名関数の中はgulp.src().pipe().pipe().pipe().pipe()とチェーンになっている
src()
の第一引数は「○○.ejs」ファイル、第二引数は「_○○.ejs」ファイル以外(!)- 一つ目の
pipe()
はejs()
メソッドでhtmlにコンパイル - 二つ目の
pipe()
はrename()
メソッドで拡張子を.htmlにリネイム - 三つ目の
pipe()
はreplace ()
メソッドで<!DOCTYPE〜
より上の行を削除 - 四つ目の
pipe()
はgulp.dest()
メソッドで上のディレクトリに吐き出す
前回より記述は増えているものの全体的な構成は似ている。
index.ejsを作成
以前の「EJSでFizzBuzz」のコードをベースに
※参考:【HTML】テンプレートエンジンEJSでFizzBuzzる!(Pugとの比較あり) - クモのようにコツコツと
<!DOCTYPE html> <html lang="ja"> <head> <meta charset="UTF-8"> <title>はじめてのEJSコンパイル</title> <meta name="description" content="GulpでEJSコンパイル、ひとりでできるかな?"> </head> <body> <header> <h1>はじめてのEJSコンパイル</h1> </header> <% var h1Title = 'EJSでフィズバズる'; %> <% var count = 30; %> <section> <h1 class="red"><%= h1Title %></h1> <p>EJSで変数、for文、if文を使ってフィズってバズってみた。</p> <ul> <% for (var i = 1; i < count+1; i++) { %> <% if (i % 3 == 0 && i % 5 == 0) { %> <li>フィズってバズった!</li> <% } else if (i % 3 == 0) { %> <li>フィズった!</li> <% } else if (i % 5 == 0) { %> <li>バズった!</li> <% } else { %> <li><%= i %></li> <% } %> <% } %> </ul> </section> <footer> <p>©️イイダリョウ</p> </footer> </body> </html>
(後述するように記述ミスがいくつか見つかったので、修正しています)
EJSコンパイル実行
コンパイル実行!
npx gulp ejs
前回書いたようにローカルでの実行は頭にnpxが必要。
どうだ? やった、成功!
フォルダ直下にindex.htmlが追加された!
gulp_ejs ├ejs │└index.ejs ├gulpfile.js └index.html
HTMLコード
<!DOCTYPE html> <html lang="ja"> <head> <meta charset="UTF-8"> <title>はじめてのEJSコンパイル</title> <meta name="description" content="GulpでEJSコンパイル、ひとりでできるかな?"> </head> <body> <header> <h1>はじめてのEJSコンパイル</h1> </header> <section> <h1 class="red">EJSでフィズバズる</h1> <p>EJSで変数、for文、if文を使ってフィズってバズってみた。</p> <ul> <li>1</li> <li>2</li> <li>フィズった!</li> <li>4</li> <li>バズった!</li> <li>フィズった!</li> <li>7</li> <li>8</li> <li>フィズった!</li> <li>バズった!</li> <li>11</li> <li>フィズった!</li> <li>13</li> <li>14</li> <li>フィズってバズった!</li> <li>16</li> <li>17</li> <li>フィズった!</li> <li>19</li> <li>バズった!</li> <li>フィズった!</li> <li>22</li> <li>23</li> <li>フィズった!</li> <li>バズった!</li> <li>26</li> <li>フィズった!</li> <li>28</li> <li>29</li> <li>フィズってバズった!</li> </ul> </section> <footer> <p>©️イイダリョウ</p> </footer> </body> </html>
むむ?なんだこれ、スッカスカ。gulp-replaceの空行削除が実行されていないようだ?
(まぁページ表示上は問題ないから今回は良しとしておくか…)
外部ejsファイルをインクルードする書き方(include)
先ほど書いたインクルードを行う場合は、ヘッダーフッター部分はこのような書き方になる。
<!--ヘッダー--> <% include common/_header %> <!--フッター--> <% include common/_footer %>
include の次にフォルダ、ファイル名を書く。commonがフォルダ名。_header
、_footer
とファイル名に拡張子は書かないようだ。
さらにページ固有のtitle
やmeta discription
はindex.ejs
の冒頭に書いてそれを_header
に読み込ませることもできる。(コンパイル後にこの変数部分が空行になるためgulp-replace
を使う)
先ほど書いたようにSyntaxErrorが起こってうまくいかなかったため今回は断念した。
SyntaxErrorは何度も起こった
また、インクルード部分以外にページ本体のFizzBuzz部分にもSyntaxErrorは何度も起こった。記述ミスを結構見つけて書き直して、ようやくエラーがなくなった。
例えばEJSの閉じ記号%>
が抜けていたり、変数を表示する記号<%=
が<%
になっていて表示されなかったり。
※参考:テンプレートエンジンEJSで使える便利な構文まとめ - Qiita
やはり実際にコンパイルしてみないとわからないなーと感じた。
元記事の方も修正しておきました。
※参考:【HTML】テンプレートエンジンEJSでFizzBuzzる!(Pugとの比較あり) - クモのようにコツコツと
SyntaxErrorはこのような表記になった。
まず冒頭の3行に実行状況
[(時間)] Using gulpfile ~/(フォルダ)/gulp_ejs/gulpfile.js [(時間)] Starting 'ejs'... [(時間)] Finished 'ejs' after 8.47 ms
そのあとにエラー通知
events.js:187 throw er; // Unhandled 'error' event ^ PluginError [SyntaxError]: Unexpected identifier in /(フォルダ)/gulp_ejs/ejs/index.ejs while compiling ejs
Google翻訳
events.js:187 スローer; //未処理の「エラー」イベント ^ PluginError [SyntaxError]:ejsのコンパイル中に/Users/iidaryou/Desktop/ir/gulp_ejs/ejs/index.ejsの予期しない識別子
そのあとにこのような助言が。
If the above error is not helpful, you may want to try EJS-Lint: https://github.com/RyanZim/EJS-Lint Or, if you meant to create an async function, pass `async: true` as an option. at new Function (<anonymous>) at Template.compile
Google翻訳
上記のエラーが役に立たない場合は、EJS-Lintを試してください。 https://github.com/RyanZim/EJS-Lint または、非同期関数を作成する場合は、オプションとして「async:true」を渡します。
EJS-Lintを使えばエラーの解決方法がもっと早くわかるのかも。ES-Lintと名前が似ている。これか。
※参考:ejs-lint - npm
このあとには膨大なエラーコードが続く…
なお、ターミナルがエラーコードで埋め尽くされて見にくくなったらclear
コマンドで綺麗にできる。
※参考:【シェル】ターミナル画面をリセット(クリア)するコマンド&ショートカットキー
最後に
ということでPugに続き、EJSのコンパイルも体験できまいした!
今回、本当はテンプレートエンジンならではの共通パーツ(ヘッダーフッターなど)をインクルードするところまで行きたかった。
SyntaxErrorが頻発して原因特定に時間がかかりそうだったため、単体ファイル構成にした。SyntaxErrorがなくなるまで修正し続けてなんとか成功しました!
Pugに比べるとEJSはHTMLとほぼ同じ書式で読み書きしやすいが、その文、閉じ括弧など記述量が増えているため、エラーが起こる確率は増えているように感じました。
その代わり、Pugと違ってEJSは閉じ括弧が目印なのでインデントについては厳密ではないので良し悪しがありますね。
ただ、記述ミスは完全に防ぐのは難しいため、ミスを解決しやすくする仕組み(EJS-Lintなど)を検討した方がいいのかもしれない、と感じました。
次回は、AltCSS!Sass(SCSS)のコンパイルにトライしようと思います。それではまた!
※参考:メタ言語(HTMLテンプレートエンジン、AltCSS、AltJS)まとめ
qiita.com