轻松了解HTTPS原理并信任自签名证书,解决HTTPS协议导致的本地开发难的问题
既然有自动信任的机构,当然也可以手动添加信任机构或信任证书了,这就是后面我们用来使用自签名证书的原理。这里使用的是cfssl来创建自签名证书,下载自己平台支持的即可,这里我选的是wiindows,需要用到两个软件。通过引入CA,可以看到,客户端有了校验公钥的能力,随后就可以在传递对称密钥后,开始加密通信了。原因就在于12306使用的证书是“自签名”的,它CA不被浏览器默认信任,感兴趣的话可以搜搜。
文章目录
一、背景
随着安全需求的发展,现在几乎所有的第三方应用都要求回调地址是https协议的,而且很多微服务软件部署的时候,也会要求内网之间的通信也用https协议,这就导致我们在本地开发的时候很不方便,有没有什么办法解决呢?
有的,兄弟,有的!
二、原理
在讲解如何本地创建证书和信任ca之前,先来简单说说原理。
大家都知道,http协议是明文传输,所以,网络中间的任何人都可以知道其中的内容,当然也可以篡改,例如:到达客户端的网页被莫名其妙被注入广告。
既然明文会被中间人查看和篡改,聪明的你肯定立马想到,把内容加密不就解决了。
这里就要提到两种加密方式:
1. 对称加密:
顾名思义,对称指的就是加密和解密用的密钥相同,它的特点是加解密速度很快,但也导致很容易破解。
2. 非对称加密:
既然和上面有区别,它的加密解密自然就使用不同的密钥。这里大家只需要知道它的效果是:私钥(服务端用)加密的内容只有公钥(客户端用)能解,公钥加密的内容只有私钥能解就够了,它的特点是虽然安全,但加密解密速度慢。
聪明的你,立马又想到了:
(1) 服务端只需要先把公钥发给客户端,私钥在自己手里,这样客户端加密的内容,中间人就解不了了
(2) 再结合一下对称加密:客户端拿到公钥后,回给服务端一个对称加密用的密钥,服务端后续用对称密钥加密内容,这样中间人也解不了服务端的内容了,安全又高效。
兄弟,6啊!
但中间人也有新的办法截获信息。
从上图可以发现,加密算法并不能解决传递密钥的安全问题,机智的中间人总可以获取通信内容,理解了这个,那么恭喜,兄dei,你掌握了https抓包的原理。
同时也引出了下一个问题:如何安全传递密钥呢?
3. CA
CA的全拼是:Certification Authority,可以译为证书颁发机构。
浏览器内会预置一些信任机构,用以校验证书是否可信。既然有自动信任的机构,当然也可以手动添加信任机构或信任证书了,这就是后面我们用来使用自签名证书的原理。
通过引入CA,可以看到,客户端有了校验公钥的能力,随后就可以在传递对称密钥后,开始加密通信了。
这里想提一下12306,不知道大家还记得不,早期访问会提示不安全:
原因就在于12306使用的证书是“自签名”的,它CA不被浏览器默认信任,感兴趣的话可以搜搜。
三、生成自签名证书
1. 准备工作
这里使用的是cfssl来创建自签名证书,下载自己平台支持的即可,这里我选的是windows,需要用到两个软件
- cfssl.exe
- cfssljson.exe
记得把文件路径添加到系统PATH中,否则cmd中无法识别相关命令。
2. 创建并信任CA
2.1 创建并生成ca相关文件
ca-csr.json
{
"CN": "Local Root CA",
"key": {
"algo": "rsa",
"size": 4096
},
"names": [{
"C": "CN",
"ST": "Beijing",
"L": "Beijing",
"O": "Example Co",
"OU": "PKI"
}],
"ca": {
"expiry": "87600h"
}
}
解释相关配置含义:
- CN:(Common Name)根 CA 的名称。
- key:加密算法。
- names:
- C:Country,国家代码(例如 CN、US)
- ST:State/Province,省/州
- L:Locality,城市
- O:Organization,组织名称(公司或机构)
- OU:Organizational Unit,部门或单位
- ca.expiry:根 CA 证书有效期(示例为10年,87600小时)。
生成根CA证书
cfssl gencert -initca ca-csr.json | cfssljson -bare ca
输出文件:
- ca.csr(根 CA 的 CSR)
- ca-key.pem(根 CA 私钥)
- ca.pem(根 CA 证书)
由于windows无法识别pem格式的证书,把ca.pem复制并更改类型改为crt,如下图所示:
2.2 信任自建的根CA
双击ca.crt进行安装:安装证书 -> 本地计算机 -> 将所有的证书都放入下列存储 -> 浏览 -> 受信任的根证书颁发机构。

至此就会提示完成,相关窗口点完成或确认至退出即可。
2.3 验证查看根证书是否安装完成
在运行中输入:certlm.msc
然后在弹出的窗口左侧:受信任的根证书颁发机构 -> 证书,找到刚安装的自建证书即可。

至此,我们就创建好了ca,可以为其他网站签名证书了。
3. 为本地开发的域名签发证书
3.1 准备签发策略配置
ca-config.json
{
"signing": {
"default": {
"expiry": "87600h",
"usages": ["signing", "key encipherment", "server auth", "client auth"]
}
},
"profiles": {
"server": {
"expiry": "87600h",
"usages": ["signing", "key encipherment", "server auth", "client auth"]
}
}
}
3.2 准备申请网站的配置并生成证书
这里我们模拟一个百度的单点登录中心,拟申请的域名是sso.baidu.com
server-csr.json
{
"CN": "sso.baidu.com",
"hosts": [
"sso.baidu.com"
],
"key": {
"algo": "rsa",
"size": 2048
},
"names": [
{
"C": "CN",
"ST": "Beijing",
"L": "Beijing",
"O": "Example Co",
"OU": "SSO"
}
]
}
cfssl gencert -ca=ca.pem -ca-key=ca-key.pem --config=ca-config.json -profile=server server-csr.json | cfssljson -bare server
输出文件:
- server.csr(CSR)
- server-key.pem(私钥)
- server.pem(证书)

读到这里,细心的你可能会发现,之前说的是公钥私钥,怎么到这里公钥不见了,取而代之的出现个证书?
是的,公钥并没有以单独的文件形式存在,它其实存在了证书里。证书中除了公钥外,还有很多额外信息:颁发者、颁发对象、有效期等(参考上面12306的证书截图)。由于已经懂得了HTTPS的大致原理,感兴趣的话可以自行了解实际细节,这里不再赘述了。
四、验证自签名证书
1. 修改hosts,使模拟域名指向本机
windows的hosts文件在:C:\Windows\System32\drivers\etc
记事本要使用管理员权限打开,否则无法保存。
2. 使用自签名密钥启动server
这里使用tornado来启动一个简易服务,当然你也可以用nginx等软件。代码如下:
main.py
import tornado.web
import tornado.ioloop
import tornado.httpserver
class MainHandler(tornado.web.RequestHandler):
def get(self):
self.write("Hello, HTTPS world!")
def make_app():
return tornado.web.Application([
(r"/", MainHandler),
])
if __name__ == "__main__":
ssl_options = {
"certfile": "server.pem", # 证书文件
"keyfile": "server-key.pem", # 私钥文件
# "ca_certs": "ca.pem", # 可选,若需双向认证或客户端校验
}
app = make_app()
server = tornado.httpserver.HTTPServer(app, ssl_options=ssl_options)
server.listen(4433) # 监听 4433 端口,非 443 方便测试
print("HTTPS server started on https://sso.baidu.com:4433")
tornado.ioloop.IOLoop.current().start()
安装tornado
pip install tornado
启动服务
python main.py
3. 浏览器验证

更多推荐



所有评论(0)