読者です 読者をやめる 読者になる 読者になる

UNIX的なアレ

UNIX的なこととかいろいろ

mod_proxy_balancer配下で、cakephpのredirectを使う場合の注意点

おてがるにバランシング

mod_proxy_balancerを使うと、普段から使い慣れているapacheでお手軽にロードバランシングを行うことができます。
設定もものすごく簡単ですね。Virtualhostの中に書くこともできるので、NameVirtualを使ったL7バランシングをすることも可能です。

<Virtuslhost *:80>
    ServerName example.com
    ProxyPass / balancer://balancer/
    ProxyPassReverse / balancer://balancer/
    <Proxy balancer://balancer>
        BalancerMember http://localhost.localnet:8080
    </Proxy> 
</Virtualhsot>

mod_proxy_balancer - Apache HTTP サーバ
すごくシンプルにやるとこんな感じになります。
このままでも動くのですが、cakephpと組み合わせると1点問題が生じました

redirect後のURLがちょっとおかしい

cakephpの controller内で利用することができる $this->redirect() を使うと1点問題が起きます。

 1. http://example.com/foo  (アクセスしたURL、ここから/bar へリダイレクトする)
 2. http://example.com//bar (リダイレクト後のURL)

上記のように、リダイレクト後のURLが/(スラッシュ)が二重に重なってしまいます。
まぁ動くのですがすごく気持ち悪いので対応策を考えてみました。

ProxyPreserveHostディレクティブで解決

なんか良い方法がないかなーとおもって探していたところ、本家におもいっきり回答が書いてありました。ProxyPreserveHostというディレクティブです。

このオプションが有効になっている場合、ProxyPassで指定したホスト名の代わりに、受け付けたリクエストの Host: 行を プロキシ先のホストに送ります。

このオプションは通常は Off に設定してください。 ほとんどの場合、これは大量の名前ベースのバーチャルホスティングを行なっていて、 元々の Host ヘッダをバックエンドサーバが解釈する必要のあるときのような、 特別な設定が必要な場合にのみ有用です。

mod_proxy - Apache HTTP サーバ
ああ、これこれまさにこれですよ。というわけでこれを1行だしてあげればOKです。
ProxyPassReverseはいらなくなるので、完成した設定ファイルはこうなります。

<Virtuslhost *:80>
    ServerName example.com
    ProxyPreserveHost On
    ProxyPass / balancer://balancer/
    <Proxy balancer://balancer>
        BalancerMember http://localhost.localnet:8080
    </Proxy> 
</Virtualhsot>

というわけで本日小一時間ほどハマってしまった内容でした。