LAMP 环境下安装配置 SSL 证书并自动跳转到 HTTPS

昨天给网站加了个 HTTPS,并且已经全站做了跳转。今天记录一下整个过程。主要包括 Apache 下对于 SSL 的配置,以及整站 301 跳转。

安装 LAMP

这个不是重点,顺便说一下。我用的是 lamp.sh 提供的一键包。安装方法(以 Ubuntu 16.04 LTS 为例,更多的请前往参考文献查看):

apt-get -y install wget screen git
git clone https://github.com/teddysun/lamp.git 
cd lamp 
chmod +x *.sh
screen -S lamp 
./lamp.sh

安装完成即可。

配置 SSL 证书

LAMP 一键包目前提供两种配置 SSL 证书的方法,使用第三方购买的证书,或者使用 Let’s Encrypt 提供的免费证书。这个在最新版的 LAMP 添加网站的时候就会有提示。不过今天说的不是这个自动配置的,说一下手动配置的流程。毕竟不少人是之前已经配置过网站,现在想手动加 SSL 证书的。(主要也是记录一下方便自己日后查看)

1. 生成 CSR 文件

输入下面命令(在你希望存放的目录下,比如 /data/ssl),生成 CSR 文件:

openssl req -new -newkey rsa:2048 -nodes -keyout example.key -out example.csr

上面的 example.key 和 example.csr 请替换成自己想要的名字,比如 oldtang_com.key,oldtang_com.csr。

需要填写的内容如下:

You are about to be asked to enter information that will be incorporated
into your certificate request.
What you are about to enter is what is called a Distinguished Name or a DN.
There are quite a few fields but you can leave some blank
For some fields there will be a default value,
If you enter '.', the field will be left blank.
-----
Country Name (2 letter code) [XX]:CN  // 国家代码
State or Province Name (full name) []:Shanghai  // 省
Locality Name (eg, city) [Default City]:Shanghai  // 城市
Organization Name (eg, company) [Default Company Ltd]:OldTang // 组织或公司名
Organizational Unit Name (eg, section) []:  // 不填
Common Name (eg, your name or your server's hostname) []:oldtang.com // 需要加 SSL 的域名
Email Address []:[email protected]  // 邮箱地址

Please enter the following 'extra' attributes
to be sent with your certificate request
A challenge password []:  // 不填
An optional company name []:  // 不填

2. 获取证书

这一步一般就是去你购买的 SSL 证书的服务提供商那里,提交 CSR 文件,然后获取你的证书。可以通过

cat example.csr

查看刚刚生成的 CSR 文件的内容,然后整个复制即可。提交到你的 SSL 证书提供商。比如我是在 ssls.com 买的,3 年 15 美元。

获取到的证书一般有两个,一个是 example.crt,一个是 example.ca-bundle,都下载下来,放到刚刚的目录下(比如现在在 /data/ssl/example.crt 和 /data/ssl/example.ca-bundle)。

3. 配置 Apache

首先我们需要打开 Apache 的 https 配置。修改文件 /usr/local/apache/conf/httpd.conf,找到 #Include conf/extra/httpd-ssl.conf,把前面的 # 去掉,保存。

然后配置一下 /usr/local/apache/conf/extra/httpd-ssl.conf,模板如下:

Listen 443
SSLPassPhraseDialog  builtin
SSLSessionCache  "shmcb:/usr/local/apache/logs/ssl_scache(512000)"
SSLSessionCacheTimeout  300

<VirtualHost *:443>
	DocumentRoot /data/www/example.com/
	ServerName example.com
	ServerAlias www.example.com
	ErrorLog "/usr/local/apache/logs/lamp_error_log"
	TransferLog "/usr/local/apache/logs/lamp_access_log"

	SSLEngine on
	SSLProtocol All -SSLv2 -SSLv3
	SSLHonorCipherOrder on
	SSLCipherSuite ALL:!aNULL:!eNULL:!EXPORT:!DES:!RC4:!MD5:!PSK:!aECDH:!EDH-DSS-DES-CBC3-SHA:!EDH-RSA-DES-CBC3-SHA:!KRB5-DES-CBC3-SHA

	SSLCertificateFile /data/ssl/example.crt
	SSLCertificateKeyFile /data/ssl/example.key
        SSLCertificateChainFile /data/ssl/example.ca-bundle

	CustomLog "/usr/local/apache/logs/lamp_ssl_request_log" \
		"%t %h %{SSL_PROTOCOL}x %{SSL_CIPHER}x \"%r\" %b \"%{Referer}i\" \"%{User-Agent}i\""

	BrowserMatch "MSIE [2-5]" \
		nokeepalive ssl-unclean-shutdown \
		downgrade-1.0 force-response-1.0

	<Directory /data/www/example.com/>
		Options -Indexes +FollowSymLinks
		AllowOverride All
		Require all granted
	</Directory>
</VirtualHost>

把上面所有带有 example 字样的,都修改成你自己的信息。

如果有多个不同的域名需要加 SSL 的,也很简单,<VirtualHost *:443> </VirtualHost> 前面的东西不变,连带里面的东西再复制一份即可。就像这样:

Listen 443
SSLPassPhraseDialog  builtin
SSLSessionCache  "shmcb:/usr/local/apache/logs/ssl_scache(512000)"
SSLSessionCacheTimeout  300

<VirtualHost *:443>
    ....
</VirtualHost>
<VirtualHost *:443> 
    .... 
</VirtualHost>

然后重启一下 Apache 即可:

/etc/init.d/httpd restart

如果开了防火墙,记得检查一下防火墙状态,要放行 443 端口。

自动跳转到 HTTPS

配置完成后,会发现通过 HTTP 和 HTTPS 都能访问。如果我们想要保持统一,可以对 HTTP 的链接做强制跳转,都跳转到 HTTPS。

1. HTTP 自动跳转到 HTTPS

方法很简单,在网站目录下,新建或者编辑 .htaccess 文件,在最前面加入以下内容:

RewriteEngine On
RewriteCond %{HTTPS} !on [NC]
RewriteRule (.*) https://oldtang.com%{REQUEST_URI} [R=301,NC,L]

这段代码的意思是说:当检测到 HTTPS 未开启(!on 嘛)的时候,把请求重定向到 https:// 的对应 URI。

如果想要针对不同的搜索引擎,配置是否跳转或者不跳转,也简单。稍作修改如下:

RewriteEngine On
RewriteCond %{HTTPS} !on [NC]
RewriteCond %{HTTP_USER_AGENT} !(baiduspider|soso|bing|sogou|yahoo|sohu-search|yodao|robozilla|msnbot|msie|feedburner) [NC]
RewriteRule (.*) https://oldtang.com%{REQUEST_URI} [R=301,NC,L]

这段代码比刚刚那段多加了一个判断条件,即判断访客的 User Agent 是否是搜索引擎或者 IE 用户,如果不是,那才跳转到 https:// 版的页面。注意,这里面是不包含 Google Bot(Google 的爬虫)的,因为 Google 本身就是能抓取 https:// 站点的,没必要重定向。而 IE 用户则是像其他的非 Google 的搜索引擎一般看待了,保持不跳转。

2. 带 WWW 的自动跳转到不带 WWW 的域名

仅仅是跳转到 HTTPS,还不够,为了保持更统一,我们要把带 WWW 的域名和不带 WWW 的域名也统一起来。比如我这里都是跳转到不带 WWW 的,方法如下。

在刚刚的 .htaccess 文件里,紧跟着加入:

RewriteEngine On
RewriteCond %{HTTP_HOST} ^www.oldtang.com [NC]
RewriteRule ^(.*)$ https://oldtang.com/$1 [L,R=301]

那么最后的文件就大概变成这样子了,可以实现 HTTP 跳转到 HTTPS,并且带 WWW 的域名跳转到不带 WWW 的域名:

RewriteEngine On 
RewriteCond %{HTTP_HOST} ^www.oldtang.com [NC]
RewriteRule ^(.*)$ https://oldtang.com/$1 [L,R=301]
RewriteCond %{HTTPS} !on [NC] 
RewriteRule (.*) https://oldtang.com%{REQUEST_URI} [R=301,NC,L]

最终的效果就是我的网站现在的样子。

参考文献

  1. https://lamp.sh/
  2. https://helpdesk.ssls.com/hc/en-us/articles/203427502-How-to-generate-a-CSR-code-on-Apache-Nginx-using-OpenSSL
  3. https://teddysun.com/395.html
  4. https://helpdesk.ssls.com/hc/en-us/articles/203482651-How-to-install-a-SSL-certificate-on-Apache

【AD】美国洛杉矶CN2 VPS/香港CN2 VPS/日本CN2 VPS推荐,延迟低、稳定性高、免费备份_搬瓦工vps

【AD】RackNerd 推出的 KVM VPS 特价优惠,在纽约、西雅图、圣何塞和阿什本每年仅需 12.88 美元!