使用自签发的SSL证书来加密nginx与后端服务器的通讯

这个问题很有意思,说起来还是由于可恶的GFW. 我目前使用一台阿里云华南的服务器来服务国内客户,然后用一台阿里云HKB 的服务器 + CDN 来服务国外客户. 但是郁闷的是,HKB 的服务器,nginx运行一会就回出现502 bad gateway,但是把HKB 的业务放在其他的服务商那里,就不会出现这个问题, 而且如果你不是用80端口,也不会出现这个问题

这个debug了将近一个星期才猛然间意识到,这也许是因为GFW 和阿里云盾的敏感词过滤系统,强制TCP 触发RST标志,造成502 connection reset

目前看来唯一的办法就是上https, 也就是说要secure data transfer between nginx and its upstream。。。我发现对我来说,还是英语描述比较完整

在这种情况下,nginx 的 upstream 要是用https, 但是因为只是作为内部数据传输,因此可以不用去买SSL证书,直接用self signed 的证书就可以了.

nginx 的官方,有一篇比较权威的教程:

https://www.nginx.com/resources/admin-guide/nginx-https-upstreams/

但是说实话,这个比较复杂,用的是SSL 的双面认证,类似于国内的网上银行的验证方式,而对于我们这种情况,只需要单向认证就可以了. 也就是说只需要在 后端的nginx 的服务器上安装自签发的SSL证书即可,前端nginx 配置调整为proxy_pass https.

关于如何给nginx安装自签发的ssl 证书,国内的教程也比较多,但是大部分都是先自建CA key crt,再签发,比较麻烦, 类似于这样:

http://blog.creke.net/762.html

这样做比较适合双向SSL认证

一个简单的方式可以借助下面的blog提到的方式:

http://blog.topspeedsnail.com/archives/3768

下面简单说下:

现在很多网站都使用https进行加密通讯及对网络服务器身份的鉴定。这遍文章介绍怎么在Nginx web服务上设置自签名SSL证书。由于不是由权威机构发布的证书,它(自签名证书)不能确认网络服务器身份,但是它可以对通信进行加密。

自签名证书适合个人或公司内部使用,如果要对外提供web服务,最好购买权威机构发布的证书。在github上有一个项目叫Let’s Encrypt,可以使用它签发免费的证书,并且大多数web浏览器都信任它。

创建SSL证书

我们可以创建一个目录用来存放所有SSL相关文件,在/etc/nginx下创建:

创建 SSL密钥和证书文件:

$ sudo openssl req -x509 -nodes -days 365 -newkey rsa:2048 -keyout /etc/nginx/ssl/nginx.key -out /etc/nginx/ssl/nginx.crt

我们来看一看上面命令各个选项的意思:

openssl:这是创建和管理OpenSSL密钥、证书和其它文件的命令行工具
req:指定使用X.509证书签名要求(CSR)
-x509:创建自签名证书,而不生成签名请求
-nodes:证书不使用密码,我们需要Nginx能直接读取文件,在重启Nginx时,不用输入密码
-days 365::证书的有效时间,这里是一年
-newkey rsa:2048:同时生成一个新证书和新密钥,RSA密钥长度:2048位
-keyout:密钥生成的路径
-out:证书生成的路径
执行上面命令,需要回答一系列问题。其中,最重要的一个问题是Common Name (e.g. server FQDN or YOUR name),输入你的域名。这里可以使用泛解析. 如果没有域名的话,使用ip地址。

这样就会生产key 和 crt

一个简单的nginx配置例子:

server {
 listen 80 default_server;
 listen [::]:80 default_server ipv6only=on;
 
 listen 443 ssl;
 
 root /usr/share/nginx/html;
 index index.html index.htm;
 
 server_name your_domain.com;
 ssl_certificate /etc/nginx/ssl/nginx.crt;
 ssl_certificate_key /etc/nginx/ssl/nginx.key;
 
 location / {
 try_files $uri $uri/ =404;
 }
}

discuz x3.2 启动SSL

这是一篇别的地方看到的文章,把所有需要修改的地方都说了,很有借鉴意义,这里就转载过来做个记录

————————————————————————————————————————————–

Discuz! X3.2 本身对 HTTPS 的支持很有限,程序本身支持,但还有很多地方需要调整和修改的。
站点全部链接默认 HTTPS ,无任何 HTTP 链接通过 301 跳转到 HTTPS 。 浏览器显示绿色安全标志,无“不安全内容”提示。

具体来说,我们需要从以下 6 个方面来实现我们最终的效果。

服务器前端程序的配置
一般来说,大家多使用 Nginx 作为前端程序,关于 Nginx 开启 HTTPS 的教程,网上有很多教程,可以参考这篇文章:

https://aotu.io/notes/2016/08/16/nginx-https/
Discuz 判断服务器是否使用 SSL 的修补和完善
 Discuz 判断服务器是否使用 SSL 的代码不适合 Nginx+CGI 的情况,即 PHP-FPM 。这个时候我们需要修改以下文件:
 Discuz 采用 $_SERVER[‘ HTTPS ’] 的方式来判断 SSL ,但是因为服务器 架构问题( nginx+php-fpm ),无法采用这种方式识别,所以需要对 Discuz 程序进行一些调整(使用 $_SERVER[‘ SERVER_PORT ’] 来判断)。 source/class/discuz/discuz_application.php (约第 187 行处): 查找:
 $_G['isHTTPS'] = ($_SERVER['HTTPS'] && strtolower($_SERVER['HTTPS']) != 'off') ? true : false;
 修改为:
 $_G['isHTTPS'] = ($_SERVER['SERVER_PORT'] == 443 || $_SERVER['HTTPS'] && strtolower($_SERVER['HTTPS']) != 'off') ? true : false;
uc_server/avatar.php (约第 13 行处):
 查找:
 define('UC_API', strtolower(($_SERVER['HTTPS'] == 'on' ? 'https' : 'http').'://'.$_SERVER['HTTP_HOST'].substr($_SERVER['PHP_SELF'], 0, strrpos($_SERVER['PHP_SELF'], '/'))));
 修改为:
 define('UC_API', strtolower(($_SERVER['SERVER_PORT'] == 443

除去非 HTTPS 内容避免提示”不安全内容“
Source/plugin/manyou/Service/DiscuzTips.php ,最后的那段 JS 加载脚本删除就行。
非楼主层如果有点评,那么点评者头像不是 HTTPS 开头,也需要修改一个文件来适配: template/default/forum/viewthread_node_body.htm (约 180 行),搜索 div class=”psta vm”>,将下面一行注释掉或者删除。
打开浏览器,使用开发者工具或者查看源码逐一排查加载的非 HTTPS 资源并修改。

后台设置的修改完善
在后台还有一些设置,可能会干扰 https 的使用
后台 >全局 > 站点 URL ,改为 https 开头的
后台 > 站长 > UCenter 设置 > UCenter 访问地址,修改为 https 开头的
UCenter 后台 > 应用管理 > 应用的主 URL ,修改为 https 开头。修改后可能会显示通讯失败,如果 UC 和论坛程序安装在同一机器,此失败可无视,实测可以和 UC 正常通讯不影响(测试是否正常通讯程序的 Bug ),如果 UC 和论坛程序不在一台机器上,有可能不能通讯。 另外在 后台 > 全局 > 域名设置 中的一些设置也可能使 https 失效,如果更新缓存后论坛默认连接还是 HTTP ,请删除 后台 > 全局 > 域名设置 > 应用域名 > 默认 里面的默认域名(一般去 forum.php 尾巴这里会有内容,为了 HTTPS 请删除)。

模板的调整
主要在模板的 foot.html 以及 header.html 等文件中,使用工具逐一排查模板文件中写死的 HTTP 链接,修改为 HTTPS 。

数据库的调整
在论坛这种交互社区中,经常回复发帖时会有出现主域名的链接,在没有 HTTPS 之前,链接都是 HTTP 开头,这个时候,我们需要修改数据库,运行下面的 mysql 命令更新数据库,将 HTTP 替换为 HTTPS :
进入 DZ 后台:站长 – 数据库 – 升级

UPDATE pre_forum_post SET message=REPLACE(message,’http://www.repaik.com‘,’https://www.repaik.com‘);
请将 www.repaik.com 替换为自己的域名

需要注意的是,出于安全考虑, Discuz 后台默认情况下禁止 SQL 语句直接执行,只能使用常用 SQL 当中的内容,如果想自己随意书写 SQL 升级语句,需要将程序文件 config/config_global.php 当中的$_config[admincp][runquery] 设置修改为 1 。

真是有点囧,心里不快

没事的时候经常在论坛上挂一些联盟的 referral link,换点 referral 的commission。 以前一直挂的都是us 和 eu 一些传统联盟,没有任何问题,给钱非常爽快

进来看到 mobile 这么火,我寻思着就挂着 咱本土的企业的link,支持一下。。。谁知道,问题来了。。。

1)  联盟A, referral 的commission 的钱到了threshold 也不支付,虽然很少,但是足够够我买喝一个月的咖啡豆的量了。我去问AM, AM 说他们换了系统,两个系统都在用。我说为啥我没有新系统的账号,对方无反应。然后我又问,如果换了系统,那我推荐了那么多的affiliates,怎么办?对方不回答我的问题,然后说一般都是小白才会通过 别人的affiliate link 注册账号,那些大牛从来不会用别人的link 注册的。

更多

07/13更新

早上醒来,发现很多newrelic 的报警邮件,仔细一看原来是squid 又开始占内存了..

刷刷二话不说,按照以往写了一个squid 自动清除缓存的bash 脚本,可是总是出现 permission denied 的问题

我都改成777了还是出现这个问题。。。nnd。。。

耗费了一上午的时间,才发现是selinux 搞的鬼

关掉selinux,一切恢复正常

Infrastrueture Updates and Bugs fixed

经过一段时间的测试,发现腾讯的多线机房对全国范围内的访问不是很好,而盛大云又确实太贵了,在带宽上。而且从我们这边来看,经常发现有down time。

经过一段时间的考察,现在全面改成了首都在线的多线BGP,经过测试,对全国范围内的访问的速度是非常快的。

discuz 的程序或是用的人太多了,一些不知道的bug实在太多了

我也手动修复了一些图片和附件上传的bug,现在同学们应该可以借助我们的全球CDN的优势,更加方便的上传,下载和浏览图片和附件