第 28 章 安全
目录
数据库安全在若干个层面上加以处理:
数据库文件保护。数据库中存储的所有文件都受到保护,除Postgres超级用户账户外,任何其他账户都不能读取。
默认情况下,从客户端到数据库服务器的连接只允许通过本地 Unix 套接字进行,而不允许通过 TCP/IP 套接字。后端必须以
-i选项启动才能允许非本地客户端连接。可以通过
pg_hba.conf文件(位于PG_DATA中)按 IP 地址和/或用户名限制客户端连接。客户端连接可以通过其他外部软件包进行认证。
Postgres中的每个用户都被分配一个用户名和(可选的)口令。默认情况下,用户对不是他们创建的数据库没有写权限。
用户可以被分配到组,表访问可以基于组权限加以限制。
28.1. 用户认证
认证是后端服务器和postmaster
确保请求访问数据的用户确实是其声称的那个人的过程。所有调用Postgres的用户都会对照
pg_user类的内容进行检查,以确保他们被授权这样做。不过,用户实际身份的验证可以通过多种方式进行:
- 从用户 shell
从用户 shell 启动的后端服务器会先记录用户的(有效)用户 id,然后执行
setuid切换到用户postgres的用户 id。有效用户 id 被用作访问控制检查的依据。不进行其他认证。- 从网络
如果Postgres系统构建为分布式,任何人都可以访问postmaster 进程的 Internet TCP 端口。DBA 配置 PGDATA 目录中的 pg_hba.conf 文件,根据发起连接的主机以及所连接的数据库来指定要使用的认证系统。可用认证系统的描述见pg_hba.conf(5)。当然,在 Unix 中基于主机的认证也不是万无一失的。意志坚定的入侵者也可能伪装来源主机。这些安全问题超出了Postgres的范围。
28.1.1. 基于主机的访问控制
基于主机的访问控制是 PostgreSQL 对哪些客户端被允许访问数据库以及这些客户端上的用户必须如何认证自己所实施的基本控制的名称。
每个数据库系统都包含一个名为
pg_hba.conf的文件(在其PGDATA
目录中),它控制谁可以连接到每个数据库。
每个访问数据库的客户端必须被pg_hba.conf中的某个条目覆盖。否则来自该客户端的所有连接尝试都将被拒绝,并给出"User authentication failed"错误消息。
pg_hba.conf文件的一般格式是一组记录,每行一条。空行和以井号("#")开头的行被忽略。一条记录由若干个以空格和/或制表符分隔的字段组成。
客户端可以使用 Unix 域套接字或 Internet 域套接字(即 TCP/IP)建立连接。使用 Unix 域套接字建立的连接由以下格式的记录控制:
localdatabaseauthentication method
其中
database
指定该记录适用的数据库。值all
表示它适用于所有数据库。
|
authentication method
指定用户使用 Unix 域套接字连接到该数据库时必须使用的认证方法。各种方法在下面描述。
|
使用 Internet 域套接字建立的连接由以下格式的记录控制。
hostdatabaseTCP/IP addressTCP/IP maskauthentication method
TCP/IP address
与指定的TCP/IP mask
以及连接客户端的 TCP/IP 地址分别做逻辑与。如果得到的两个值相等,则该记录用于此连接。如果一个连接匹配多条记录,则使用文件中最早的那条。TCP/IP address和
TCP/IP mask
都以点分十进制表示法指定。
如果一个连接未能匹配任何记录,则应用 reject认证方法(见下文)。
28.1.1.1. 认证方法
Unix 和 TCP/IP 域套接字都支持以下认证方法:
- trust
无条件允许连接。
- reject
无条件拒绝连接。
- crypt
向客户端询问该用户的口令。口令以加密形式发送(使用crypt(3)),并与
pg_shadow表中保存的口令比较。如果口令匹配,则允许连接。- password
向客户端询问该用户的口令。口令以明文发送,并与
pg_shadow表中保存的口令比较。如果口令匹配,则允许连接。可以在password关键字后指定一个可选的口令文件,用它代替 pg_shadow 表来匹配提供的口令。见 pg_passwd。
以下认证方法仅支持 TCP/IP 域套接字:
- krb4
使用 Kerberos V4 认证用户。
- krb5
使用 Kerberos V5 认证用户。
- ident
使用客户端上的 ident 服务器认证用户(RFC 1413)。可以在
ident关键字后指定一个可选的映射名,它允许把 ident 用户名映射为 Postgres用户名。映射保存在文件$中。PGDATA/pg_ident.conf
28.1.1.2. 示例
# Trust any connection via Unix domain sockets.
local trust
# Trust any connection via TCP/IP from this machine.
host all 127.0.0.1 255.255.255.255 trust
# We don't like this machine.
host all 192.168.0.10 255.255.255.0 reject
# This machine can't encrypt so we ask for passwords in clear.
host all 192.168.0.3 255.255.255.0 password
# The rest of this group of machines should provide encrypted passwords.
host all 192.168.0.0 255.255.255.0 crypt