令和に向けてフロントエンドツール群を整えた話
こんにちは
https://gyazo.com/422954eb4591d345c7d507cae73748ae
誰
京都大学工学部情報学科7回生
株式会社はてな アルバイト
TypeScript
Nota Inc Gyazo開発チーム アルバイト
JavaScript / React / Ruby on Rails / Browser Extension
ビール仕入れ業 / ビールサーバー運用エンジニア
趣味: ビール🍻
今日のトークテーマ
フロントエンドツール群を整えた話
普通の話しか無いです
必殺技とかも出てこない
Kyoto.jsではお馴染みのいわゆる煩悩取り払いシリーズです
GigaViewer
はてなで提供しているマンガビューワーの名前
このたびの「コミックボーダー」でのビューワ採用は、「少年ジャンプ+」「となりのヤングジャンプ」(株式会社集英社)、「マガジンポケット」「コミックDAYS」(株式会社講談社)、「くらげバンチ」(株式会社新潮社)、「月刊ヒーローズ」(株式会社ヒーローズ)に続く7例目となります。
フロントエンドの挑戦も色々やってます
https://gyazo.com/d6ab1f28ab22d621c4157b65a1bbc910
GigaViewer
全メディアでビューワー部分は共通
ビューワー部分はJavaScriptの塊
ページ送り(アニメーション)
アニメーションGIFの再生開始タイミング合わせ
表示モードの切り替え
閲覧履歴保存(localStorage)
オフライン対応
1stシーズン (〜2018年夏
タスクランナー: gulp
browserify + typescript
gulp-less
サイトごとにjsもcssも1つずつbundlingしていた
ビルドキャッシュとかない
しかし重複箇所はかなり多い
browserify + tsifyをメディア数分やるので、単調に時間が増加していっていた
素朴に一旦先にtscだけ走らせてts -> js にしてからentrypointごとにbrowserifyでbundleして高速化
テストフレームワークはchai + power-assertという感じだったが、新たなものから少しずつjestに移行
カバレッジも測れるように
2ndシーズン (〜2018年秋
ServiceWorkerを提供するようになった
DOM側に提供するJSのファイルとWorker用のJSのファイルを分割するように
lib.dom.d.ts, lib.webworker.d.tsの読み込みを分けたりもする
タスクランナーは引き続きgulpのまま
↑の条件分けなどでカオスになってきた
browserify + typescriptだったところにBabel7を入れた
もともとからIE11対応していた
typescriptはasync-awaitなどをtargetを見て書き換えてくれるが、Array.prototype.includesみたいなのを使いたいので入れた
それまでは Array.prototype.indexOfの結果を-1と比較する古き良きコードを書くようにレビューとかしていた
3rdシーズン (今
gulp脱出→webpackへ
cssのbuildはgulp-lessのまま
移行に際してはbundlingが変わるだけなので、振る舞いに問題ないはずだけど、念のためちゃんとやろうということでビューワーを中心にJSが動く箇所のチェックリストを作ってQA活動をした
特に大きな問題もなく移行できた🎉
開発用のhostへのdeployなどの都合でrepositoryに生成物を入れていたが、真面目に向き合ってやめるようにした
Jenkinsでnpm run buildして成果物をtarballにするように
CodeSplittingなどへの布石
Sentry導入
ユーザーの環境で起きているエラーを把握できるように
localStorageをtry-catchで囲ってないとか見つかる
シークレットモードのときに困るケースがある
フィルタリング書いて広告とかのJSは弾くとか
上手く弾かないとアプリ内ブラウザが挿入しているJSのエラーとかにも遭遇する
webpackについて
pastak.iconwebpackでJSのbundling+α以上をやるのは良くないと思っている
Webpack の本質的な部分は次の3つです。それ以外は全部おまけ機能だと思ってよいです。
・ES Modules のエミュレート
・node_modules のリンカ
・拡張子ごとの変形
css-loaderやimage-loader的なものは入れたくない
webpackからbrowserifyやrollupなどに逃げられるようにプロジェクトの依存は最小にしたい
実際に逃げられるかはハードルがある・・・
影響範囲もJSのbundlingだけにしておくと分かりやすい
Loading chunk ${N} failed.
CodeSplittingを始めたらよく起きるようになった。timeout伸ばしたりしてみてるけど特に改善されない
諦めるしかない?知見あったらください。
現状の構成(まとめ)
とにかくかっこよくもなければ古くもない普通の状態を目指した
ここから後は色んなものを取り込んでいくだけ
Before: gulp / typescript / tslint / chai
After: webpack / typescript / babel / tslint / jest
成果物のbuildを手元でしてcommitしないといけなかったのを撤廃
Sentryも入れて安心してdeploy後を過ごせるように
今後について
testもう少し整備
まだchaiが一部残ってる
e2eテストのためにpuppeteerとかbrowserstackとか用意しているが実装がまだあまり出来てない
jQuery滅ぼしたい
一部依存しているライブラリをデザインのために使っているので完全に捨てられるかは怪しいが代替はあるはず
document.querySelectorとか使えば良い
少なくとも新規のコードでは止めたい
ESLintにあるno-restricted-modulesをtslint向けに簡単に書き直したのを使って阻止している
pastak.iconjQuery型のオブジェクトを受け渡しているのあんまり嬉しさがない
foo(elm: jQuery): void みたいなのが各所にある
先日$.ajaxはaxiosに全部置き換えた
tslint→ESlint引っ越ししたい
ts-loader vs awesome-typescript-loader
今はawesomeを使っているが、メンテされてないよねって話題もある。皆さんはどうです?
手元でのbuildにdocker-for-mac使うのどうするか問題
IO遅すぎる
webpackのwatchが効かないのでpollingしている
令和の時代もやっていこうな💪
any Q?