postgres-网络传输安全-openssl

网络传输安全

默认情况下pg服务端和客户端之间的数据传输是明文传输,有一定的安全隐患。pg中可以使用ssl进行安全的tcp/ip连接,以密文的形式进行数据的安全传输。

这个特性要求在客户端和服务器都安装OpenSSL,并且在编译pg的时候打开这个支持,使用openssl指令生成私钥和证书,用来对数据加解密

注意在编译安装pg的时候需要添加–with-openssl参数,让pg支持ssl认证方式

./configure   --with-openssl
--如果没有加上--with-openssl参数,在打开ssl配置,启动pg的时候会报错
SSL is not supported by this build

使用opsnessl生成密钥和证书

--生成一个有效期365天的简单自签名证书,将bhost.yourdomain.com替换为服务器的主机名
openssl req -new -x509 -days 365 -nodes -text -out server.crt \
Ceyout server.key -subj "/CN=dbhost.yourdomain.com"
--然后执行:
chmod og-rwx server.key

配置postgres.conf和pg_hba.conf文件

--修改postgres.conf
ssl=on
ssl_cert_file='server.crt'
ssl_key_file='server.key'

--修改pg_hba.conf,新增ssl认证连接规则
hostssl all all 0.0.0.0/0 md5

重启数据库,ssl生效

[postgres@localhost ~]$ psql -Usa postgres -h localhost
Password for user sa: 
psql (11.1)
SSL connection (protocol: TLSv1.2, cipher: ECDHE-RSA-AES256-GCM-SHA384, bits: 256, compression: off)
Type "help" for help.

postgres=# select pg_backend_pid(), ssl_is_used(), ssl_version(), ssl_cipher();
 pg_backend_pid | ssl_is_used | ssl_version |         ssl_cipher          
----------------+-------------+-------------+-----------------------------
          12401 | t           | TLSv1.2     | ECDHE-RSA-AES256-GCM-SHA384
(1 row)

  • 验证传输加密
1.--创建t_ssl测试表
postgres=# create table t_ssl(id int);
CREATE TABLE
postgres=# insert into t_ssl select generate_series(1,100);
INSERT 0 100

2.--在客户端用psql远程连接数据库(如果抓包后再连接会把这个信息也抓进去)
psql -Usa postgres -p 6543 -h ip

3.--在服务器端使用tcpdump抓取数据包
[root@localhost opt]# tcpdump  host ip -w /home/opt/ssl.cap
tcpdump: listening on eth0, link-type EN10MB (Ethernet), capture size 262144 bytes

4.--在客户端使用psql执行命令
select * from t_ssl limit 10;

5.--使用wireshark工具对抓取的包解析
0000   00 50 56 86 d3 fd 00 0c 29 c8 7d 95 08 00 45 00   .PV.....).}...E.
0010   00 74 5e 01 40 00 40 06 63 a1 ac 19 10 44 ac 19   .t^.@[email protected]..
0020   10 6b 8b 2c 19 8f 68 de d1 97 c9 c2 2a 9b 80 18   .k.,..h.....*...
0030   00 b3 2a 11 00 00 01 01 08 0a 63 01 30 c1 9a 61   ..*.......c.0..a
0040   6c 16 17 03 03 00 3b dd ae 8c 9b 38 9b 7d 02 9f   l.....;....8.}..
0050   68 1a 42 05 91 11 42 4d 95 d0 e4 1b db d4 b9 46   h.B...BM.......F
0060   7c fa fd 71 3d 70 f6 0b ea bb ab 5f 16 1c 89 b2   |..q=p....._....
0070   c3 79 50 28 bf 52 93 c8 17 88 ec 35 f7 53 b2 7f   .yP(.R.....5.S..
0080   a2 9a          

 6.--如果不使用openssl进行数据加密抓包的话,传输的sql会被抓取到
0000   00 50 56 86 d3 fd 00 0c 29 c8 7d 95 08 00 45 00   .PV.....).}...E.
0010   00 57 b5 0c 40 00 40 06 0c b3 ac 19 10 44 ac 19   .W..@[email protected]..
0020   10 6b 8a fa 19 8f e3 33 04 75 b9 1a 0d 9f 80 18   .k.....3.u......
0030   00 7b 87 09 00 00 01 01 08 0a 62 f9 bc 8b 9a 5a   .{........b....Z
0040   7f ee 51 00 00 00 22 73 65 6c 65 63 74 20 2a 20   ..Q..."select * 
0050   66 72 6f 6d 20 74 5f 73 73 6c 20 6c 69 6d 69 74   from t_ssl limit
0060   20 31 30 3b 00                                     10;.                                                             

SSL双向认证和SSL单向认证的区别

双向认证 SSL 协议要求服务器和用户双方都有证书。单向认证 SSL 协议不需要客户拥有CA证书,服务器端不会验证客户证书,以及在协商对称密码方案,对称通话密钥时,服务器发送给客户的是没有加过密的(这并不影响 SSL 过程的安全性)密码方案。这样,双方具体的通讯内容,都是加过密的数据,如果有第三方攻击,获得的只是加密的数据,第三方要获得有用的信息,就需要对加密的数据进行解密,这时候的安全就依赖于密码方案的安全。而幸运的是,目前所用的密码方案,只要通讯密钥长度足够的长,就足够的安全。这也是我们强调要求使用128位加密通讯的原因。

一般Web应用都是采用SSL单向认证的,原因很简单,用户数目广泛,且无需在通讯层对用户身份进行验证,一般都在应用逻辑层来保证用户的合法登入。但如果是企业应用对接,情况就不一样,可能会要求对客户端(相对而言)做身份验证。这时就需要做SSL双向认证。

由于单向认证和双向认证的区别仅在于创建连接阶段,数据的传输均为加密的,因此客户端与PG服务端的连接采取SSL单向认证即可,即仅在PG Server端配置SSL证书

参考文档