2019-02-24

あとから@vue/cli 3 + Jest

まとめ

いろいろやって、結局丸一日くらいは掛かることが分かった。

気をつけるべきポイント

  • Babel がすでに入っているなら 7系 にちゃんと上げておく
  • @vue/cli は Webpack と一部概念が違う
  • 関係するツールが増えると当然だが検証時間は伸びる

狙い

大きなフレームワークが入っておらず、中途半端に JavaScript が散らかっている状態の小規模のプロジェクトがある。このうち一部のコードに対して

I/O 周り(HTTPS? や localStorageアクセス)に変更を施す必要がある

ことが分かった。そのため

  1. ビルドプロセスに手を入れる
  2. 既存のコードをテスタブルな状態にもっていく

を行う必要があると判断した。

方向

すでに動いているコードは以下の状態。

  • jQuery ベースのコードがある
  • ビルドプロセスを伴わない状態で Vue も採用されている

テストの欲しい変更を行うコードは Vue の方。そのため、

  • @vue/cli
    • webpack
  • jest

を入れることとした。

理由はimport / exportを書くとasset bundlerが必要になるから

I/O 周りのコードに対する変更を行いたいわけだが、このために

  • I/O 周りのコードを Model として分離する

こととした。

必要なのは View の方ではないので、Vue を利用して構築している部分から I/O 周りを分離し、Model だけをテスタブルにしたうえで変更を加えていくのはごく当たり前の判断と言ってよいと思う1。View 周りまで含んだコードをテスタブルな状態に持っていくのはコストが大きすぎる。幸い、Vue の場合は jQuery ベースよりは anonymous function だらけにはなりにくく、「継ぎ」2を作ればテスタブルな状態を作るのはそれほど難しくなさそうに見えた。

そして Model をテストするわけだが、ここで問題がある。

モダンな開発を行うに当たり、コードを責務の単位で分離したうえで import / export して作っていくのは当たり前のことである。しかし、import / export は Babel の領域ではなく、asset bundler の領域。

asset bundler と言えば Webpack … ?

Webpack の設定はしたくない。絶対にだ。

ということですでに Vue が入っているなら Webpack の面倒くささを避けるために @vue/cli だろうという当然の帰結。

やることリスト

  1. 既存の Babel があれば上げておく
  2. まず @vue/cli プロジェクトを別なところで作る
  3. .babelrc などは babel.config.js へ変更3
  4. package.json などなどを別プロジェクトからコピー
  5. webpack の multi entry は @vue/cli 側で multi page として再定義されているのでそっちを参考に
  6. .eslintrc.js を追加4
  7. Jestの導入(以下のようになる場合アリ)
    • [NG] @vue/cli-plugin-jest-unit
    • [OK] jest

意外とハマる

特に

  • Multi Page という @vue/cli 独自の概念
    • このために HtmlWebpackPlugin とか、あまり欲しくない知識が必要になる5
    • @vue/cli のデフォルト設定の entry 周りから multi entrypoints に持っていく方が面倒
  • @vue/cli が .eslintrc.js を無視してしまう問題
  • @vue/cli-plugin-jest-unit がなぜか babel-jest を適切に適用できない問題

辺り。

@vue/cli は抽象化のレベルがなかなかよいと思っていたのだが、やはりレイヤーが増えればややこしさは増える。まだまだ伸び代だらけだなぁ。Vue に関してはほぼ本家扱いと言ってよいのでそこまで心配は要らないだろうが、Babel, Webpack, Jest は繋ぎの部分の作り込みのレベルにバラツキがあるように見えるので注意が必要。

また Jest が Babel 7 と合わない時代もあったりしたようで、Babel と Webpack の migration は今後も面倒ごとになり続けそう。

参考

  1. この Model 相当のコードが複数箇所から参照されるのは分かっていたのでその判断を加速させたが、それがなくても分離はした方がよい。 

  2. sprout classとかアンチレガシーのプラクティスのこと。 

  3. @vue/cli-service, jest が自動で認識してくれる 

  4. @vue/cli 3.1.1 はバグで .eslintrc.js を無視するので直っているバージョンに上げておくこと 

  5. 読み込み用の HTML も不要だし、後始末が必要になったり。 

About

例によって個人のなんちゃらです

Recent Posts

Categories

Tool 日々 Web Biz Net Apple MS ことば News Unix howto Food PHP Movie Edu Community Book Security Text TV Perl Ruby Music Pdoc 生き方 RDoc ViewCVS CVS Rsync Disk Mail FreeBSD Cygwin PDF Photo Zebedee Debian OSX Comic Cron Sysadmin Font Analog iCal Sunbird DNS Linux Wiki Emacs Thunderbird Sitecopy Terminal Drawing tDiary AppleScript Life Money Omni PukiWiki Xen XREA Zsh Screen CASL Firefox Fink zsh haXe Ecmascript PATH_INFO SQLite PEAR Lighttpd FastCGI Subversion au prototype.js jsUnit Apache Trac Template Java Rhino Mochikit Feed Bloglines CSS del.icio.us SBS qwikWeb gettext Ajax JSDoc Rails HTML CHM EPWING NDTP EB IE CLI ck ThinkPad Toy WSH RFC readline rlwrap ImageMagick epeg Frenzy sysprep Ubuntu MeCab DTP ERD DBMS eclipse Eclipse Awk RD Diigo XAMPP RubyGems PHPDoc iCab DOM YAML Camino Geekmonkey w3m Scheme Gauche Lisp JSAN Google VMware DSL SLAX Safari Markdown Textile IRC Jabber Fastladder MacPorts LLSpirit CPAN Mozilla Twitter OpenFL Rswatch ITS NTP GUI Pragger Yapra XML Mobile Git Study JSON VirtualBox Samba Pear Growl Mercurial Rack Capistrano Rake Win RSS Mechanize Sitemaps Android JavaScript Python RTM OOo iPod Yahoo Unicode Github iTunes God SBM friendfeed Friendfeed HokuUn Sinatra TDD Test Project Evernote iPad Geohash Location Map Search Simplenote Image WebKit RSpec Phone CSV WiMAX USB Chrome RubyKaigi RubyKaigi2011 Space CoffeeScript Nokogiri Hpricot Rubygems jQuery Node GTD CI UX Design VCS Kanazawa.rb Kindle Amazon Agile Vagrant Chef Windows Composer Dotenv PaaS Itamae SaaS Docker Swagger Grape WebAPI Microservices OmniAuth HTTP 分析基盤 CDN Terraform IaaS HCL Webpack Vue.js BigQuery Middleman CMS AWS PNG Laravel Selenium OAuth OpenAPI GitHub UML GCP TypeScript SQL Hanami Document SVG AsciiDoc Pandoc DocBook Develop Jekyll macOS Node.js Vite Heroku Transformer AI Data Cloud Wasm