2016-07-16

Pact試してみた

あるいは Kanazawa.rb meetup #47 に参加してきたよの巻。

Swaggerに対するモヤモヤ

最近 Swagger を動かしたり していたんですが、まぁ確かに Swagger UI は Google API Explorer みたいで感動はするんですが、「いや、『仕様』を書きたいんじゃないんだ」という気持ちがどうもモヤモヤしてましてですね。というのも、API というのはあくまで外部とのインターフェイスで、実際にはそのインターフェイスを実現するためには中で涙ぐましい努力をしたりするわけじゃないですか。そう、シンクロナイズドスイミングみたいなアレです。

そんな気持ちもあって、Swagger ではなく Grape から入るということを前回はやっていたわけです。Swagger UI は「公開されている API のクライアントを書く際にチェック用のツールとしては優れている」けど、ここからコード生成してもなー、っていう。どうせ中の泥臭い部分はサーバを書く言語で書かなきゃいけないのなら、インターフェイス部分を書く手間を減らしてくれる Grape などの DSL からドキュメント起こす方がいいよな、と思うわけです。少なくともサーバを書くという部分においては。

※ いい具合に Facade なコードを作っておけばできなくはないかもしれないし、Grape の中に生々しくロジックが入りすぎていていいわけでもないですが。

同時に自分の中では「仕様を外部に公開するよりはオレはテストをしたいのだ」という気持ちがくすぶってくるわけです。ビビりなので。spec の validation ではなく API のテストをしたいわけです。そんなものは今まで通りやればいいじゃん? うん、まぁそうなんだけど。

Consumer Driven Contract TestingとPact

Consumer Driven Contract Testing という考え方があるらしい。

API サーバの詳細な動作ではなく、「クライアントが壊れないように API が動作してほしい」という意味での Concumer Driven Contract. 自分の理解としては The RSpec Book の中にあった BDD の二重構造の外側の部分のテストみたいな印象です。

これを実現する

realestate-com-au/pact: Enables consumer driven contract testing, providing a mock service and DSL for the consumer project, and interaction playback and verification for the service provider project.

というツールが『マイクロサービスアーキテクチャ』の中で紹介されていたので、これを試す、というのを今回の meetup のお題にしました。

Pactにできること

  • クライアント(Consumer)側が守ってほしい挙動を記述する(標準では RSpec を利用)
    • mock サーバを立ち上げ、サーバ側の挙動は mock として記述する
  • それをサーバ(Provider)側と共有するためのJSONフォーマットがある(Pactfile)
  • これを Provider 側で実行する
  • 集約サーバがある(Broker)
  • Broker から Provider は自分が守るべき Contract を取得し、守れているか自分に対してテストする
    • mock を使ったテストは標準では rack-test を使うので Grape で書いた API はまさにそのままテストできる

mock を stub ではなく正しく mock として使っているので test double が分かっていないと、混乱するかもしれないです。しかも中間形式を用いながら使いまわしているので、クライアント側の期待する動作をサーバ側で検証できるのは非常に面白いです。

Broker はなくても Provider 側でテストの実行方法が分かれば最低限なんとかなるので、以下を目標としました。

本日の目標

  1. Consumer のテストの記述と Mock の動作が分かる
  2. Pactfile を生成する
  3. Grape ですでに途中まで書いてある API があるので、それに対してPactfileからテストを実行する

までできれば練習完了。 3 は完了しなかったけど、これは想定の範囲内ということで。

bethesque/pact-consumer-minitest: Minitest support for the Pact Consumer gem

感想としてはクライアント側のコードを example に合わせて HTTParty を使ってみて、この部分に慣れていなかったのでなかなか手間取ってしまいましたが、サーバの mock は書きやすくてよかったと思います。まずは API のテストの第一歩を歩き始めた気分。

(このあと provider state など不慣れな用語がたくさん出てきて戸惑うことになるのですが、それはまた後日)

参考

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