tabimoba.net

とあるエンジニアの雑記帳

さくらのレンタルサーバでHTTPS(SNI SSL)な独自ドメインのWordpressサイトを構築する際の注意点

2017/7/23 追記

さくらインターネットが、WordPress常時SSL化プラグインの提供を開始しました。さくらのレンタルサーバでHTTPSな独自ドメインのWordpressサイトを構築する場合は、こちらのプラグインを使用することをおすすめします。 https://help.sakura.ad.jp/hc/ja/articles/115000047641

はじめに

さくらのレンタルサーバ(共有サーバ)でHTTPS(SNI SSL)な独自ドメインのWordpressサイトを構築する際の注意点についてまとめました。

まず、2015/2/4より、共有サーバでの独自SSL(SNI SSL)が利用可能となりました。

SNI(ネームベース)のSSLであるため、SNIに非対応の古い環境(ガラケー、Windows XP等)では正常に動作しませんが、これまでVPSや専用サーバ、上位プラン等でしか利用できなかった独自SSLが安価な共有サーバでも利用できるようになり、手軽にWebサイトのHTTPS化が行えるようになりました。

しかし、共有サーバで提供されるHTTPS接続は一般的な(VPSや専用サーバ等でApacheをインストールして運用する)HTTPSサイトとは異なるため、いくつか注意点があります。

さくらのレンタルサーバのHTTPS接続の仕様

さくらのレンタルサーバのHTTPS(SNI SSL)は、プロクシとして動作している(TCP/80のリバースプロクシとして動作している)仕様となっています。

参考

SSL利用時の注意点(さくらのサポート情報)より引用

「さくらのレンタルサーバ」にて提供しているウェブサーバApacheは、 80番ポートを使用する(HTTP)ものと、 443番ポートを使用する(HTTPS)ものとの 2種類に分けられます。 また、後者についてはプロクシとして動作します。 一般的に、前者は「http://」、後者は「https://」という形式でアクセスしますが、 同じディレクトリへのアクセスであっても、その際に呼び出されるウェブサーバ が異なると、 CGIプログラムやウェブサーバが.htaccessなどのファイルを読み込む際、挙動に違いが生じます。

例えば、HTTPとしてアクセスした場合はお手元のコンピュータが、 HTTPSとしてアクセスした場合は サーバそのものがアクセス元となります。 このため、SSLのみのアクセス許可(HTTPアクセスの制限)や、mod_rewriteによるURLの書き換えはできません。

リバースプロキシによる影響

前述の通り、さくらのレンタルサーバはリバースプロキシによるHTTPS接続となっています。

その影響として、VPSや専用サーバ上でApache等のWebサーバを立ち上げた場合(プロクシ等を経由せず直接サーバとHTTPSで接続可能な状態)のように、.htaccessでRewriteCond %{HTTPS}を用いたHTTPS接続の判定や、PHPで$_SERVER['HTTPS']を用いたHTTPS接続の判定が行えません。(リバースプロキシ経由の接続となり、実行されたファイルからはHTTPで接続されたものと見えるため)

また、実行ファイルから見たURL(URI)は、https://www.example.com/ ではなく、http://www.example.com/ となりますので、例えばPHPの$_SERVER['REQUEST_URI']で現在のURLを取得するようなシステムは正常に動作せず、遷移後のURLがHTTPSではなく、HTTPになってしまう(URLが勝手にHTTPになるように見える)等の問題が発生します。

Wordpressにおける影響

WordpressをHTTPSで運用する場合、通常は(VPSや専用サーバ等では)WP_HOMEおよびWP_SITEURLの値をデータベースまたはwp-config.phpいずれの変更だけでHTTPSでのサイト公開が行えますが、さくらのレンタルサーバにおいてはこの設定だけでは「https→httpに勝手にリダイレクトされる」問題が生じます。

原因は前述の通りとなりますが、これに対処するため.htaccessとwp-config.phpに対する設定変更が必要となります。詳細は下記の通りとなります。

対応手順

※環境ごとの設定は適宜変更してください。

まず、Wordpress設置時に追加する(パーマリンク設定時に生成される).htaccessの先頭に、以下の設定を追加します。

<IfModule mod_rewrite.c>
RewriteEngine On
RewriteCond %{HTTP:X-Sakura-Forwarded-For} ^$
RewriteRule ^(.*)$ https://www.example.com/$1 [R=301,L]
</IfModule>

次に、wp-config.phpの先頭に以下の内容を追加します。

if( isset($_SERVER['HTTP_X_SAKURA_FORWARDED_FOR']) ) {
    $_SERVER['HTTPS'] = 'on';
    $_ENV['HTTPS'] = 'on';
    $_SERVER['HTTP_HOST'] = 'www.example.com';
    $_SERVER['SERVER_NAME'] = 'www.example.com';
    $_ENV['HTTP_HOST'] = 'www.example.com';
    $_ENV['SERVER_NAME'] = 'www.example.com';
}

設定例

<IfModule mod_rewrite.c>
RewriteEngine On
RewriteCond %{HTTP:X-Sakura-Forwarded-For} ^$
RewriteRule ^(.*)$ https://www.example.com/$1 [R=301,L]
</IfModule>


# BEGIN WordPress
<IfModule mod_rewrite.c>
RewriteEngine On
RewriteBase /
RewriteRule ^index\.php$ - [L]
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule . /index.php [L]
</IfModule>

# END WordPress
<?php
/**
 * The base configurations of the WordPress.
 *
 * このファイルは、MySQL、テーブル接頭辞、秘密鍵、言語、ABSPATH の設定を含みます。
 * より詳しい情報は {@link http://wpdocs.sourceforge.jp/wp-config.php_%E3%81%AE%E7%B7%A8%E9%9B%86 
 * wp-config.php の編集} を参照してください。MySQL の設定情報はホスティング先より入手できます。
 *
 * このファイルはインストール時に wp-config.php 作成ウィザードが利用します。
 * ウィザードを介さず、このファイルを "wp-config.php" という名前でコピーして直接編集し値を
 * 入力してもかまいません。
 *
 * @package WordPress
 */

// 注意: 
// Windows の "メモ帳" でこのファイルを編集しないでください !
// 問題なく使えるテキストエディタ
// (http://wpdocs.sourceforge.jp/Codex:%E8%AB%87%E8%A9%B1%E5%AE%A4 参照)
// を使用し、必ず UTF-8 の BOM なし (UTF-8N) で保存してください。

// プロクシでIPが入るとSSLアクセス状態をセットする
if( isset($_SERVER['HTTP_X_SAKURA_FORWARDED_FOR']) ) {
    $_SERVER['HTTPS'] = 'on';
    $_ENV['HTTPS'] = 'on';
    $_SERVER['HTTP_HOST'] = 'www.example.com';
    $_SERVER['SERVER_NAME'] = 'www.example.com';
    $_ENV['HTTP_HOST'] = 'www.example.com';
    $_ENV['SERVER_NAME'] = 'www.example.com';
}

// ** MySQL 設定 - こちらの情報はホスティング先から入手してください。 ** //
/** WordPress のためのデータベース名 */
define('DB_NAME', 'DB名');

/** MySQL データベースのユーザー名 */
define('DB_USER', 'DBユーザー名');

/** MySQL データベースのパスワード */
define('DB_PASSWORD', 'DBパスワード');

/** MySQL のホスト名 */
define('DB_HOST', 'DBサーバ');

/** データベースのテーブルを作成する際のデータベースのキャラクターセット */
define('DB_CHARSET', 'utf8');

/** データベースの照合順序 (ほとんどの場合変更する必要はありません) */
define('DB_COLLATE', '');

/**#@+
 * 認証用ユニークキー
 *
 * それぞれを異なるユニーク (一意) な文字列に変更してください。
 * {@link https://api.wordpress.org/secret-key/1.1/salt/ WordPress.org の秘密鍵サービス} で自動生成することもできます。
 * 後でいつでも変更して、既存のすべての cookie を無効にできます。これにより、すべてのユーザーを強制的に再ログインさせることになります。
 *
 * @since 2.6.0
 */
define('AUTH_KEY',         'put your unique phrase here');
define('SECURE_AUTH_KEY',  'put your unique phrase here');
define('LOGGED_IN_KEY',    'put your unique phrase here');
define('NONCE_KEY',        'put your unique phrase here');
define('AUTH_SALT',        'put your unique phrase here');
define('SECURE_AUTH_SALT', 'put your unique phrase here');
define('LOGGED_IN_SALT',   'put your unique phrase here');
define('NONCE_SALT',       'put your unique phrase here');

/**#@-*/

/**
 * WordPress データベーステーブルの接頭辞
 *
 * それぞれにユニーク (一意) な接頭辞を与えることで一つのデータベースに複数の WordPress を
 * インストールすることができます。半角英数字と下線のみを使用してください。
 */
$table_prefix  = 'wp_prefix';

/**
 * ローカル言語 - このパッケージでは初期値として 'ja' (日本語 UTF-8) が設定されています。
 *
 * WordPress のローカル言語を設定します。設定した言語に対応する MO ファイルが
 * wp-content/languages にインストールされている必要があります。例えば de_DE.mo を
 * wp-content/languages にインストールし WPLANG を 'de_DE' に設定することでドイツ語がサポートされます。
 */
define('WPLANG', 'ja');

/**
 * 開発者へ: WordPress デバッグモード
 *
 * この値を true にすると、開発中に注意 (notice) を表示します。
 * テーマおよびプラグインの開発者には、その開発環境においてこの WP_DEBUG を使用することを強く推奨します。
 */
define('WP_DEBUG', false);

/* 編集が必要なのはここまでです ! WordPress でブログをお楽しみください。 */

/** Absolute path to the WordPress directory. */
if ( !defined('ABSPATH') )
    define('ABSPATH', dirname(__FILE__) . '/');

/** Sets up WordPress vars and included files. */
require_once(ABSPATH . 'wp-settings.php');

参考