バージョン
CakePHP:3.8
構成
ブラウザ
---(HTTPS)--- Load-Balancer(wish SSLサーバ証明書)
---(HTTP)--- WEBサーバ
やりたいこと・困りごと
- Cake\Controller\Controller::redirect的なのを使いたい
- Load-Balancer経由のアクセスでは、httpsでredirectして欲しい
- WEBサーバIPアドレスへのアクセスでは、httpでredirectして欲しい
↓
- https://github.com/cakephp/app/blob/71f9653/config/app.php#L39-L42 のfullBaseUrl に定義すると、2.と3.の挙動切り替えができない
-
https://github.com/cakephp/app/blob/71f9653/config/bootstrap.php#L139-L141 で
env('HTTPS')
を見てhttp→https変換をしているが、3.を満たしたいため、指定できない
解決法1:beforeFilterで書き換え
src/Controller/AppController.php
function beforeFilter(Event $event) {
・・・
if ( isset($_SERVER['HTTP_X_FORWARDED_PROTO']) && 'https' == $_SERVER['HTTP_X_FORWARDED_PROTO'] ) {
Router::fullBaseUrl( 'https://'.$_SERVER['HTTP_HOST'] );
}
・・・
}
- AWSのElastic Load Balancingは、HTTP_X_FORWARDED_PROTOやHTTP_X_FORWARDED_PORTで判定できる
- 他のロードバランサの場合、どのヘッダで判断できるか調査必要
解決法2:Cake\Controller\Controller::redirectをoverwrite
src/Controller/AppController.php
public function redirect($url, $status = 302) {
$this->response = $this->response->withLocation(Router::url($url, false));
return parent::redirect($url, $status);
}
-
https://github.com/cakephp/cakephp/blob/44a7812/src/Controller/Controller.php#L734 にて、
Router::url($url, true)
となっている部分を、Router::url($url, false)
に書き換える- before:
Location: http://example.com/path/to/file
- after:
Location: /path/to/file
- before:
- Locationヘッダは、RFC7231(2014年発行)より、パスのみ指定でも動くべし、となった
- https://tools.ietf.org/html/rfc7231#section-7.1.2
- これに準拠しているブラウザ/クライアントならば、
Router::url($url, false)
で問題なく動く - 準拠していない場合は・・・解決法1使う