トップ «前の日記(2014年04月18日) 最新 次の日記(2014年06月03日)» 編集

アペフチ


2014年05月05日 InfratasterでNginxのルーティングのテスト書いてる [長年日記]

_ [Infrataster] InfratasterでNginxのルーティングのテスト書いてる

サーバーのテストはServerspecで書いているんだけど、Nginxの設定ファイルで書いているウェブサーバーのルーティングのテストをどうしようかと思っていました。自分で、簡単なツールでも書くべきかなあと。
  • /path/to/app でアプリケーションにプロクシーする
  • 但しcookieがない場合は静的ファイルをサーブする
  • /path/to/static/file で静的ファイルをNginxが直接サーブする
  • /path/to/health/check でヘルスチェック用のレスポンスを返す、但しHTTPヘッダーを見て普通のブラウザーアクセスではForbiddenにする
  • バーチャルドメインごとに微妙にパスとかが違う

みたいなルーティングのテストは、外側からのテストなのでちょっとServerspecのスコープ外なんですよね(たぶん)。だからそのためのヘルパーとかは提供していない。

というところでmizzyさんに Infratasterを紹介してもらったので先週はこれを触っていました。

_ Infratasterは、ServerspecみたいにRubyのRSpecの記法でテストを書いて、(例えば)HTTPリクエストやMySQLクエリーの戻り値が期待通りかどうかをチェックします。

↑みたいに、
  • 特定のパスに対して
  • あるHTTPヘッダー(CookieやUser-Agent)やクエリーやPOSTパラメーターを持ったリクエストを送って
  • レスポンスのステータスコードが200か調べたり
  • Cache-Controlヘッダーが期待通りか調べたり
  • 本文に特定の文字列が含まれているか調べたり
ということができます:
 describe server(:proxy) do
   describe http("http://192.168.33.10/app") do
     expect(response.body).to include 'Rails'
   end
 
   describe http("http://192.168.33.10/static/file") do
     expect(response['Etag']).not_to be_empty
   end
 
   describe http("http://192.168.33.10/health/check") do
     expect(response.status).to eq 403
   end
 end

Serverspecはサーバーの中で状態を確認しますが、Infratasterは外からサーバーの振る舞いをテストするので、役割が別だろうと思っています(利用シーンは似ているからどっちのテストも同じリポジトリーに入るとは思いますが)。

_ さて。

これって普通アプリケーションで書くべきテストじゃないの? って思いますよね。僕も強くそう思います。ただ、今の僕の環境、サーバーサイドの開発って滅多に無くて、ウェブサイト構築の時にはたいていCMSを使うんです。CMSじゃなくてもアプリケーションはパッケージを使って、ソースコード自体に手を入れないことが殆ど。つまり細かなルーティングとかは、パッケージ側で設定項目になっていなければ、ウェブサーバーの設定で頑張るしか無いのです。

そしてルーティングのルールは、そのうち追加・変更されたりするわけです。

そうなると当然怖いのが、設定を追加したはいいけど、過去の振る舞いを壊してしまった、という状況。それを防ぐために、

  1. 設定ファイルを変更して
  2. サーバーを再起動して
  3. 新しい設定がうまくいっているかブラウザーでアクセスして試して
  4. 過去の振る舞いを壊していないか何パターンもブラウザーで確認する

みたいなのを何度も何度も何度も何度もやらなくていけなくて面倒くさい、面倒くさいということはそのうちどこか漏れちゃう、ということで、自動化したいなあと思っていました。
というのはまあ、言葉にすればそういうことですが、「たまにルールの追加や変更が起こる、そして過去の振る舞いは壊してはいけない」ってなったら直感的に「(リグレッション)テスト書きたいなあ」ってなりますよね。

そんなところでInfratasterに出会えてラッキーでした。紹介してくれたmizzyさん、作ってくれたryotaraiさん、ありがとうございます。

僕みたいな「アプリケーションの開発はやっていない」という状況じゃなくても「テストの習慣のない頃に作ったウェブアプリだからテストしにくい」みたいな時に取り敢えずエンドツーエンドテストで振る舞いを担保しつつリファクタリングするとかいう時にも有用だと思います。標準でCapybaraが使えるので結構複雑な振る舞いもテストできますよ。

_ 関係無いですがこの日記、NoraMarkっていう記法で書いてみました: https://github.com/skoji/noramark