リバースプロキシ環境でWordPress管理画面をhttps強制にする

0566307c0bf322d30f83ab4450e44bf4_s

わかりにくいので説明しておくと画像は風呂です(フロキシ)。

ゆえあって、こういう構成でWordPressを立てているわけですよ。

といってもわざわざDocker使っていること以外は、

  • フロントエンドに nginx が立っている
  • バックエンドに nginx + WordPress が立っていて、
    フロントエンドがリバースプロキシ参照している

ということで、新婚の奥様がよく構築されているような事例ですね。 環境はCentOS 6.5 + WordPress 3.9 です。

しかーし、ここで以下のような要件が出てきたらどうしましょうか。

  • /wp-login.php, /wp-admin/.* はSSLアクセスを強制したい
    (ログイン画面、管理画面)

で、ちょっとハマったのでメモ。
端的に言うと正解は以下のとおり:


まず、フロントエンド側 nginx の該当 server コンテキスト内に、

と追記する。

そののちバックエンド側WordPressの ドキュメントルート/wp-config.php
に(config.phpじゃないよ!)、

を追加する。


ハマりどころ:

  • フロントエンドにクライアントがhttp/httpsどちらでアクセスしてきたか
    バックエンドに伝える方法がない。
    そのため X-Forwareded-Proto で受け渡す必要がある
  • nginx の proxy_set_header とか proxy_pass は
    if ディレクティブや 正規表現を使った {} ブロック内では
    使用できない(ナンデ?!ナンデ ニンジャ?!)
  • バックエンドのWordPressシステムは
    X-Forwareded-Proto を自動では読まないため、
    $_SERVER[‘HTTPS’] に反映してやる必要がある
  • WordPressの FORCE_SSL_ADMIN は $_SERVER[‘HTTPS’] しか見ない。
    なお、これが true なら FORCE_SSL_LOGIN を設定する必要はなし

死んだ…。

追記

ちなみに、このように管理画面でSSLを強制すると、 WordPressの一部動作に不具合が出ます。

といってもふつうの操作をしているぶんには問題がなくて、 具体的には「自サイトURLがhttpであることを前提にしてい るプラグインなど」がうまく動かない。

たとえば、JetPack(!)のパブリサイズ共有はTwitter認証 ができなくなります…(どこにバグがあるのか丸わかりである)。 とほほ…。