はじめに
Cypress を使ったE2Eテストに取り組んでおり、環境に応じたrequest headerを付ける必要があった。
公式ドキュメントに従ったやり方だとうまくheaderを付けることができなかったが、ワークアラウンドを見つけたのでQiitaにメモすることにする。
開発環境
- cypress: 4.11.0
システム構成
Browser <--> CDN <--> Reverse Proxy <--> Application Server
やりたかったこと
テストの特性上、CDNを経由せずReverse Proxyに直接接続したかったのだが、CDNを経由する際にcustom request headerが付与されるため、headerを明示的に付与する必要があった。
Cypressのドキュメントを確認するとrequest headerには2つの方法が用意されていたが、いづれも今回のユースケースには合わなかった。
方法1: visit()のオプションとしてヘッダーを渡す。
cy.visit(url, {
headers: {'CUSTOM-HEADER': 'Header value'}
})
この方法の問題はドキュメントにも記載のあるとおり、initial request にしかヘッダーが付与されないこと。つまりHTML内の画像/JS/CSSなどのサブリクエストにはヘッダーが付与されない
Cypressから発せられるすべてのリクエストに対してカスタムヘッダーを付与したいため、このやり方だと今回のユースケースでは使えない。
方法2: server()のonAnyRequestをフックしてヘッダーを付与する。
cy.server({
onAnyRequest: (route, proxy) => {
proxy.xhr.setRequestHeader('CUSTOM-HEADER', 'Header value')
}
})
この方法はドキュメントに記載があるのだが、私が試したところコード自体は発動していいないように思える。または最初の一発だけ発動して他ではトリガーされない感じ、、、
ワークアラウンド:visit() + ModHeader Extension
テストはChromiumで動けば良いので、ModHeader というChrome拡張でヘッダーを付与できないか試したところ、visit()には付与されなかったが、サブリクエストには付与されることがわかった。
そのためあまりスマートな解決策ではないが、下記で対応することにした
- initial request は visit()のオプションでカスタムヘッダーを付与
- サブリクエストはModHeader で付与
initial request は visit()のオプションでカスタムヘッダーを付与
cy.visit(url, {
headers: {'CUSTOM-HEADER': 'Header value'}
})
サブリクエストはModHeader で付与
- cypress panel からChromiumを起動
- Chromiumから
ModHeader
を検索し普通にChromeExtensionとして普通にインストール
- インストールが完了したら
ModHeader
のアイコンをクリックし +ボタンをクリック ->Request header
をクリック
- カスタムヘッダーを登録する。
ModHeaderの設定内容はChromiumを閉じても維持されるため、次回Cypress経由でChromiumを起動したときはカスタムヘッダーが不要される設定の状態で起動する。
最後に
全くスマートさにかける解決策なので onAnyRequest
の正しい使い方を教えてください。