Skip to content

PostgreSQL 审计与合规

审计与合规概述

审计与合规是PostgreSQL数据库安全管理的重要组成部分,通过配置审计机制可以记录数据库的所有操作,满足合规要求,防止数据泄露和滥用。常见的合规要求包括GDPR、PCI DSS、HIPAA、CCPA等。

审计日志配置

基本审计日志配置

PostgreSQL内置了基本的审计日志功能,可以通过配置参数启用和调整:

ini
# postgresql.conf

# 日志目标
log_destination = 'csvlog'  # 推荐使用CSV格式便于分析
logging_collector = on       # 启用日志收集器

# 日志目录和文件名
log_directory = 'pg_log'     # 日志存储目录
log_filename = 'postgresql-%Y-%m-%d_%H%M%S.log'  # 日志文件名格式
log_rotation_age = 1d        # 每天轮换日志
log_rotation_size = 100MB    # 日志文件达到100MB时轮换

# 日志内容配置
log_statement = 'all'         # 记录所有SQL语句
log_connections = on          # 记录连接事件
log_disconnections = on       # 记录断开连接事件
log_duration = on             # 记录语句执行时间
log_line_prefix = '%t [%p]: [%l-1] user=%u,db=%d,app=%a,client=%h '  # 日志前缀格式

# 详细日志配置
log_min_duration_statement = 1000  # 记录执行时间超过1秒的语句
log_parameter_max_length_on_error = -1  # 记录错误语句的完整参数
log_checkpoints = on          # 记录检查点事件
log_autovacuum_min_duration = 0  # 记录所有自动清理操作

重启日志配置

bash
# 重新加载配置(无需重启数据库)
pg_ctl reload -D /var/lib/pgsql/14/data

# 或使用SQL命令
SELECT pg_reload_conf();

pgAudit扩展

pgAudit是PostgreSQL的审计扩展,提供了更详细和灵活的审计功能,支持细粒度的审计规则配置。

安装pgAudit扩展

1. 编译安装

bash
# 克隆源代码
git clone https://github.com/pgaudit/pgaudit.git
cd pgaudit

# 编译安装
make PG_CONFIG=/usr/pgsql-14/bin/pg_config
make install PG_CONFIG=/usr/pgsql-14/bin/pg_config

2. 使用包管理器安装

bash
# CentOS/RHEL
yum install postgresql14-pgaudit

# Ubuntu/Debian
apt-get install postgresql-14-pgaudit

配置pgAudit

1. 在postgresql.conf中启用pgAudit

ini
# postgresql.conf
shared_preload_libraries = 'pgaudit'  # 添加到共享预加载库

注意:修改shared_preload_libraries需要重启数据库才能生效。

2. 配置pgAudit参数

ini
# pgaudit配置参数
pgaudit.log = 'READ,WRITE,DDL'  # 审计读取、写入和DDL操作
pgaudit.log_catalog = on        # 审计系统目录操作
pgaudit.log_parameter = on       # 审计语句参数
pgaudit.log_level = 'log'       # 日志级别
pgaudit.log_client = off        # 是否发送审计日志到客户端
pgaudit.log_temporary_relations = on  # 审计临时关系操作
pgaudit.log_rows = on           # 审计影响的行数

3. 重启数据库

bash
# 重启数据库使配置生效
systemctl restart postgresql-14

使用pgAudit

1. 创建审计策略

sql
-- 创建扩展
CREATE EXTENSION IF NOT EXISTS pgaudit;

-- 审计特定表的操作
ALTER SYSTEM SET pgaudit.log = 'READ,WRITE';
SELECT pg_reload_conf();

-- 审计特定角色的操作
ALTER ROLE app_user SET pgaudit.log = 'ALL';

2. 查看审计日志

bash
# 查看审计日志文件
ls -la /var/lib/pgsql/14/data/pg_log/

# 使用cat或tail查看日志内容
tail -f /var/lib/pgsql/14/data/pg_log/postgresql-2025-12-23_*.csv

3. 审计日志格式

pgAudit日志格式示例:

csv
2025-12-23 14:30:00.123 UTC,12345,[1-1],user=app_user,db=mydb,app=psql,client=192.168.1.100,AUDIT: SESSION,1,2025-12-23 14:30:00.123 UTC,12345,postgres,app_user,mydb,SELECT,SELECT * FROM users WHERE id = 1;,<not logged>

合规要求

GDPR(通用数据保护条例)

合规要求

  • 数据最小化:只收集和存储必要的数据
  • 数据主体权利:支持数据访问、修改、删除等权利
  • 数据保护影响评估(DPIA):对高风险数据处理进行评估
  • 数据泄露通知:72小时内通知监管机构
  • 审计跟踪:记录所有数据访问和修改操作

实现建议

sql
-- 启用详细审计
ALTER SYSTEM SET pgaudit.log = 'ALL';
ALTER SYSTEM SET log_statement = 'all';

-- 定期导出审计日志到安全存储
CREATE OR REPLACE FUNCTION export_audit_logs()
RETURNS void AS $$
BEGIN
    -- 导出日志到安全位置
    EXECUTE format('COPY (SELECT * FROM pg_log) TO ''/secure/audit/logs/audit_%s.csv'' WITH CSV', now()::date);
END;
$$ LANGUAGE plpgsql;

-- 每天执行一次
SELECT cron.schedule('0 0 * * *', 'SELECT export_audit_logs();');

PCI DSS(支付卡行业数据安全标准)

合规要求

  • 敏感数据保护:不得存储完整的信用卡验证码(CVV)
  • 访问控制:实施严格的访问控制和身份验证
  • 网络安全:使用防火墙和加密保护网络
  • 定期测试:定期进行漏洞扫描和渗透测试
  • 审计跟踪:记录所有访问和修改支付卡数据的操作

实现建议

sql
-- 限制对支付卡数据的访问
CREATE ROLE pci_user NOLOGIN;
GRANT SELECT (id, last_four_digits) ON credit_cards TO pci_user;
-- 不授予完整信用卡号的访问权限

-- 审计支付卡数据访问
ALTER SYSTEM SET pgaudit.log = 'READ,WRITE,DDL';
ALTER SYSTEM SET pgaudit.log_parameter = on;

HIPAA(健康保险流通与责任法案)

合规要求

  • 保护电子健康记录(EHR):加密存储和传输健康数据
  • 访问控制:实施基于角色的访问控制
  • 审计跟踪:记录所有访问和修改健康数据的操作
  • 业务伙伴协议:与业务伙伴签订安全协议
  • 应急计划:制定数据泄露应急响应计划

实现建议

sql
-- 启用详细审计
ALTER SYSTEM SET pgaudit.log = 'ALL';
ALTER SYSTEM SET pgaudit.log_rows = on;

-- 加密健康数据
CREATE TABLE health_records (
    id SERIAL PRIMARY KEY,
    patient_id INTEGER NOT NULL,
    diagnosis TEXT,
    treatment TEXT,
    created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);

-- 使用行级安全策略限制访问
CREATE POLICY health_records_policy ON health_records
    USING (patient_id = current_setting('app.current_patient')::integer);

ALTER TABLE health_records ENABLE ROW LEVEL SECURITY;

个人信息保护法

合规要求

  • 个人信息处理原则:合法、正当、必要
  • 敏感个人信息特殊保护:严格保护生物识别、医疗健康等敏感个人信息
  • 个人信息跨境传输:符合跨境传输规则
  • 数据泄露通知:及时通知监管机构和个人
  • 审计要求:记录个人信息处理活动

实现建议

sql
-- 敏感个人信息加密存储
ALTER TABLE users ADD COLUMN sensitive_info_encrypted BYTEA;

-- 审计个人信息访问
CREATE TRIGGER audit_user_access
AFTER INSERT OR UPDATE OR DELETE ON users
FOR EACH ROW EXECUTE FUNCTION audit_sensitive_data();

审计日志分析

日志分析工具

1. pgBadger

pgBadger是一个PostgreSQL日志分析工具,可以生成详细的HTML报告:

bash
# 安装pgBadger
sudo yum install pgbadger  # CentOS/RHEL
sudo apt-get install pgbadger  # Ubuntu/Debian

# 分析日志
pgbadger -f csv pg_log/postgresql-2025-12-23_*.log -o pgaudit_report.html

2. ELK Stack

ELK Stack(Elasticsearch + Logstash + Kibana)是一个强大的日志管理和分析平台:

  • Logstash:收集和处理日志
  • Elasticsearch:存储和索引日志
  • Kibana:可视化分析日志

3. Prometheus + Grafana

用于监控和可视化数据库指标,结合日志分析:

  • Prometheus:收集数据库指标
  • Grafana:可视化指标和日志

常见审计查询

sql
-- 查看特定用户的所有操作
SELECT * FROM pg_log WHERE user = 'app_user';

-- 查看对敏感表的访问
SELECT * FROM pg_log WHERE query LIKE '%sensitive_table%';

-- 查看执行时间超过5秒的语句
SELECT * FROM pg_log WHERE duration > 5000;

-- 查看连接失败事件
SELECT * FROM pg_log WHERE message LIKE '%connection failed%';

审计最佳实践

1. 实施分层审计策略

  • 基础审计:使用PostgreSQL内置日志功能记录基本操作
  • 详细审计:使用pgAudit扩展记录细粒度的审计日志
  • 应用级审计:在应用层面记录业务相关的审计日志

2. 保护审计日志

  • 日志加密:对审计日志进行加密存储
  • 访问控制:限制审计日志的访问权限
  • 日志备份:定期备份审计日志到安全位置
  • 日志保留:根据合规要求设置日志保留期限

3. 定期审计审查

  • 定期分析:定期分析审计日志,识别异常访问
  • 生成报告:生成审计报告,用于合规审计
  • 改进措施:根据审计结果改进安全措施

4. 审计日志管理

  • 日志轮换:配置合理的日志轮换策略
  • 日志清理:定期清理过期日志
  • 日志归档:将过期日志归档到长期存储

5. 自动化审计

  • 自动告警:配置异常访问自动告警
  • 自动报告:定期自动生成审计报告
  • 自动归档:自动归档过期日志

版本差异

PostgreSQL 9.x版本

  • 支持基本的日志功能
  • 不支持pgAudit扩展
  • 日志格式和配置选项有限
  • 性能影响较大

PostgreSQL 10-11版本

  • 增强了日志功能
  • 开始支持pgAudit扩展
  • 日志性能优化
  • 增加了更多日志配置选项

PostgreSQL 12-13版本

  • 进一步增强了日志功能
  • pgAudit扩展更加成熟
  • 支持更多的审计选项
  • 日志性能进一步优化

PostgreSQL 14及以上版本

  • 支持JSON格式日志
  • 增强了日志过滤功能
  • pgAudit扩展支持更多的审计规则
  • 日志管理更加灵活

常见问题与故障排查

1. 审计日志过大

问题:审计日志增长过快,占用大量磁盘空间

解决方案

ini
# 优化日志配置
log_statement = 'mod'  # 只记录修改语句,减少日志量
log_min_duration_statement = 5000  # 只记录执行时间超过5秒的语句
log_rotation_size = 50MB  # 减小日志文件大小
log_rotation_age = 1h  # 缩短日志轮换时间

2. 审计性能影响

问题:启用详细审计后,数据库性能下降

解决方案

ini
# 优化审计配置
pgaudit.log = 'DDL,WRITE'  # 只审计DDL和写入操作
log_statement = 'none'  # 禁用内置日志,只使用pgAudit
log_min_duration_statement = 1000  # 只记录慢查询

3. 审计日志丢失

问题:审计日志丢失,无法进行合规审计

解决方案

bash
# 配置日志冗余存储
rsync -avz /var/lib/pgsql/14/data/pg_log/ /backup/audit_logs/

# 启用日志校验
ALTER SYSTEM SET log_checkpoints = on;
ALTER SYSTEM SET log_wal_receiver_stats = on;

4. 审计日志无法分析

问题:审计日志格式混乱,无法使用工具分析

解决方案

ini
# 统一日志格式
log_destination = 'csvlog'  # 使用CSV格式
log_line_prefix = '%t [%p]: [%l-1] user=%u,db=%d,app=%a,client=%h '  # 标准化日志前缀

审计与合规实施建议

  1. 评估合规需求

    • 识别适用的合规框架
    • 确定审计范围和要求
    • 评估当前审计能力
  2. 设计审计策略

    • 选择合适的审计工具
    • 设计审计日志格式和存储方案
    • 制定审计日志管理流程
  3. 实施审计配置

    • 配置PostgreSQL日志参数
    • 安装和配置pgAudit扩展
    • 配置审计规则
  4. 测试和验证

    • 测试审计日志生成
    • 验证审计日志完整性
    • 测试审计日志分析
  5. 运营和维护

    • 定期审查审计日志
    • 更新审计规则
    • 维护审计日志存储
  6. 持续改进

    • 根据合规要求更新审计策略
    • 优化审计性能
    • 改进审计日志分析