AWS ELB + SSL Termination下でEC-CUBEを正しく動かす
今回の構成は SSL Termination を行い、ELB -> EC2(Webサーバ)間ではHTTPS(443)通信を行いません。この場合、EC2側は常にHTTP(80)で通信を受けるので、ユーザーのELBに対するアクセスがHTTPなのかHTTPSなのか普通の方法では判断出来ません。
X-Forwarded-[xxx]ヘッダ
ELBを通過するときに、X-Forwarded-Port/Proto等のヘッダが付きます。これを判別することにより見分けることが出来ます。 http://docs.aws.amazon.com/ElasticLoadBalancing/latest/DeveloperGuide/x-forwarded-headers.html
EC-CUBE内部におけるHTTPS判定
./data/module/Net/URL.php: $this->protocol = (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] == 'on' ? 'https' : 'http'); ./data/module/Net/URL.php: case 'https': return 443; ./data/class/util/SC_Utils.php: if (SC_Utils_Ex::sfIsHTTPS()) { ./data/class/util/SC_Utils.php: $proto = "https://"; ./data/class/util/SC_Utils.php: $domain = SC_Utils_Ex::sfIsHTTPS() ? HTTPS_URL : HTTP_URL; ./data/class/util/SC_Utils.php: * HTTPSかどうかを判定 ./data/class/util/SC_Utils.php: function sfIsHTTPS () { ./data/class/util/SC_Utils.php: // HTTPS時には$_SERVER['HTTPS']には空でない値が入る ./data/class/util/SC_Utils.php: // $_SERVER['HTTPS'] != 'off' はIIS用 ./data/class/util/SC_Utils.php: //if (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] != 'off') { ./data/class/util/SC_Utils.php: #if ($_SERVER['HTTP_X_FORWARDED_PROTO'] == 'https') ./data/class/util/SC_Utils.php: if (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] != 'off') { ./data/class/util/SC_Utils.php: } else if(ereg("^https://", $istr)) { ./data/class/util/SC_Utils.php: $head = "https://";
このように方方で$_SERVER['HTTP']
で判定しています。これらをすべて $_SERVER['HTTP_X_FORWARDED_PROTO']
に変換していくのは至難の業です。
じゃあどうするか。無い変数はつけてしまえばいいです。
mod_setenvif
apacheモジュールで setEnvIfというのがあります。これを使って$_SERVER変数
を無理やり追加します。
SetEnvIf X-Forwarded-Proto ^https$ HTTPS=on
リダイレクトで片っ端からSSLにする
SetEnvIf X-Forwarded-Proto ^https$ HTTPS=on RewriteEngine on RewriteCond %{HTTP:X-Forwarded-Proto} ^http$ RewriteRule ^(.*)$ https://%{HTTP_HOST}%{REQUEST_URI} [R,L]
せっかく HTTPS変数にするんだから、そいつを使えばいいと考えるなら、RewriteCondで HTTP:HTTPSを指定すること。
もう一つの解法、ソースをちょっといじって解消する
https://forge.typo3.org/issues/29693
f ($_SERVER['X-Forwarded-Proto'] == 'https') { $_SERVER['HTTPS'] = 'on'; }
phpの初手でこいつをかませばいい。
まとめ
- EC-CUBEのHTTPS判定は、サーバ変数 $_SERVER['HTTPS']
- HTTPS -> X-Forwarded-Protoに判定をまるっと変えるようなconfigはない
- SetEnvIfで HTTPSサーバ変数を付与するのが楽
X-Forwarded-Protoでリダイレクトだけかけても、商品をカートに入れるときにエラーが出ます。これの対処方法がわからない場合、参考に。 ちなみに、EC-CUBEはセッションをDBに保存するらしいので、(デフォルト) StickySessionは必須ではないはず。