在这个全民 HTTPS 的时代,似乎网站不开启 HTTPS 就不正常似的。以前一直懒得折腾也就没设置 HTTPS ,每天看着谷歌浏览器地址栏上的“不安全”三个大字也确实不是太舒服,今天刚好休班,晚上闲来无事顺便折腾了下 HTTPS ,折腾的过程中也确实出现了一些问题,想着记录下来希望遇到同样问题的小伙伴可以规避一下。

特别提醒:如果你的网站之前使用了 WPS Hide Login 之类的插件,折腾前务必停用以防后期无法登陆后台!另外,记得备份数据库!记得备份数据库!!记得备份数据库!!!重要的事情说三遍。

好了,下面说一下具体步骤:

申请 HTTPS 证书

在配置 HTTPS 之前,我们需要一个 SSL 证书,这里我是直接通过阿里云申请的赛门铁克的免费证书,当然你也可以使用其他证书,后面上传即可。申请位置“管理控制台/安全(云盾)/SSL证书(应用安全)”

申请的步骤就不详细说了,申请完成后会有一个“已签发”的状态,后面我们就用这个证书配置即可。

配置HTTPS 证书

获取到 HTTPS 证书后,我们需要前往“管理控制台/云计算基础服务/CDN/域名管理”处新建一个加速域名(可暂时不做 CNAME 解析,等完全配置好后再做解析)。

然后我们需要对这个加速域名做些简单的配置,主要是证书的配置。这里我选择的是阿里云证书,直接选择“已签发”的证书即可,当然如果你有别的证书可通过“自有证书”上传即可。

注意将跳转类型设置为 HTTP->HTTPS,后面我们会具体说明不设置时可能出现的问题。

修改 WordPress 地址、站点地址及文件的完整URL地址

如果前面未设置解析,则我们现在依旧可以通过 HTTP 方式登录后台。可以在 WordPress 后台常规选项下将  WordPress 地址 及站点地址修改为 https 方式。当然,如果上面将跳转类型设置为默认的话也可以在设置完解析后进行修改:

或者你也可以登录数据库,找到 wp_options 数据表中的下面这两个字段将其修改为 https 方式。

另外,如果之前我们自定义过后台媒体的上传路径,此时我们需要将上传文件的完整 URL 请求方式也修改为 HTTPS 。默认文件的完整URL地址是留空的,如果你此处的选项是默认值则可以不做修改。另外关于文件上传路径的自定义可以查看这篇文章>>>开启WordPress后台自定义媒体上传功能 。

修改上述路径的目的是为了我们访问的时候可以采用 HTTPS 的方式进行访问,但是如果在配置证书的时候我们选择了默认的跳转方式(前面配置的时候已经强制将跳转类型设置为 HTTP->HTTPS 了,这只是证书方面的设置。)则发现我们既可以通过 HTTP 方式访问网站及后台,也可以通过 HTTPS 方式访问,这显然是不安全的,所以我们需要简单配置一下 wp-config.php 文件。

配置 wp-config.php文件

强制登录及管理使用 HTTPS 方式

WordPress 默认是使用 HTTP 协议的,所以说为了网站的安全我们要使其强制使用 HTTPS 协议,将以下代码添加到 wp-config.php 文件中去:

/** HTTPS 强制开启 */
define('FORCE_SSL_LOGIN', true);
define('FORCE_SSL_ADMIN', true);

添加完成后并设置 CNAME 解析后,访问网站,我们发现如下问题:

  • 网站静态文件(JS、CSS)因为采用原有的 http 方式请求的导致浏览器禁止了其访问
  • 图片文件虽然加载了,但是其使用的也是 http 方式

造成这个的原因是由于 wp-includes/load.php 中启用 SSL 函数搞得鬼,代码如下:

/**
 * Determines if SSL is used.
 *
 * @since 2.6.0
 * @since 4.6.0 Moved from functions.php to load.php.
 *
 * @return bool True if SSL, otherwise false.
 */
function is_ssl() {
    if ( isset( $_SERVER['HTTPS'] ) ) {
        if ( 'on' == strtolower( $_SERVER['HTTPS'] ) ) {
            return true;
        }
        if ( '1' == $_SERVER['HTTPS'] ) {
            return true;
        }
    } elseif ( isset($_SERVER['SERVER_PORT'] ) && ( '443' == $_SERVER['SERVER_PORT'] ) ) {
        return true;
    }
        return false;
    }

WordPress 通过 $_SERVER[‘HTTPS’] 判断网站是否启用 HTTPS 的,但是虚拟主机好像是由于 CGI 配置的问题返回 $_SERVER[‘HTTPS’] 的值为 null ,所以 WordPress 无法判断网站已启用 SSL ,所有静态资源也就无法加载了。那么,如何解决上述问题呢?我们只需要在 wp-config.php 文件中添加如下代码即可:

//强制定义 HTTPS 参数
$_SERVER['HTTPS']='on';

添加完上述代码后我们再次访问网站,发现网站又出现如下问题:

 

修改静态资源请求方式

虽然静态资源加载了,但是由于链接依旧是 HTTP 方式请求的,导致浏览器判断网站仍旧不安全,未显示小绿锁。我们通过查看数据库的 wp_posts 数据表发现,原来之前发布的文章所有的图片资源记录的是 http 协议的链接,我们需要将其替换为 https 方式,具体可使用如下两种方法:

 

方法一:更新数据库

方法一使用的方法是直接通过命令将数据库原有的 http 替换为 https ,使用该方法的唯一问题就是博客所有的资源链接都变成了 https ,以后如果我们停用了 SSL 网站的静态资源,那么网站的静态资源就会加载失败,当然我们到时候还可以在通过反向利用命令将链接再次替换为 http 的即可。

update wp_posts set post_content = replace(post_content, 'http://blog.quietguoguo.com','https://blog.quietguoguo.com');

将上面的链接替换成你自己网站地址的链接即可。

方法二:修改 functions.php 文件

方法二使用代码在网站加载的时候讲 http 链接替换为 https 的,将代码添加到主题的 functions.php 文件中即可,具体代码如下:

//WordPress SSL at 2016/12/29 update
add_filter('get_header', 'fanly_ssl');
function fanly_ssl(){
	if( is_ssl() ){
		function fanly_ssl_main ($content){
			$siteurl = get_option('siteurl');
			$upload_dir = wp_upload_dir();
			$content = str_replace( 'http:'.strstr($siteurl, '//'), 'https:'.strstr($siteurl, '//'), $content);
			$content = str_replace( 'http:'.strstr($upload_dir['baseurl'], '//'), 'https:'.strstr($upload_dir['baseurl'], '//'), $content);
			return $content;
		}
		ob_start("fanly_ssl_main");
	}
}

感谢泪雪博客提供的代码。添加完代码后再次刷新网站,显示结果如下:

至此 HTTPS 配置完成。