跳转到主要内容

27.5 参数作用域与变更方式

一个参数变更有三个不同状态:

desired
  inventory/template/DCS/database-role policy 想要什么

configured
  file/catalog/command line 中写了什么

effective
  当前 server/session 实际用了什么

它们可以不同。

最常见事故不是参数值本身,而是:

  • 改错 scope;
  • 被更高优先级覆盖;
  • reload 了一个必须 restart 的参数;
  • 只改 primary,failover 后消失;
  • 手工 ALTER SYSTEM 被下一次 IaC 覆盖;
  • 改了 role default,却继续复用旧 pool session;
  • pending_restart 长期无人处理。

27.5.1 编译、初始化、启动、reload 与会话级

先问“这个属性什么时候还能改变”

从最早到最晚:

build/compile
  -> initdb
      -> postmaster startup
          -> SIGHUP reload
              -> backend startup
                  -> superuser/session
                      -> transaction

越靠左,变更成本、兼容性和回退风险通常越大。

build-time

有些物理属性来自 build:

block size
some segment/page layout options
compiled features/libraries
architecture/compiler

查询:

SHOW block_size;
SELECT version();

这些不是普通 GUC。改变 block size 通常意味着不同 binary/cluster physical format, 不能用 reload/restart 改现有集群。

initdb-time

cluster 创建时固定或高度绑定:

encoding
locale/ICU provider and version choices
data checksums
WAL segment size
system identifier

例如:

SHOW data_checksums;
SHOW wal_segment_size;
SELECT datname, encoding, datcollate, datctype
FROM pg_database;

某些能力可能有离线工具/特定版本转换路径,但不能把它当作普通 GUC rollout。 参数 ADR 要标注:

new cluster / migration / offline conversion

而不是写“restart”。

pg_settings.context

SELECT DISTINCT context
FROM pg_settings
ORDER BY context;

典型语义:

context 最早/最小变化边界
internal 不能由用户改变,来自 build/init/internal
postmaster server start
sighup config reload
superuser-backend backend start,需 superuser/SET privilege
backend backend start
superuser session 可改,但权限受限
user ordinary session 可改

context=user 只表示权限/生命周期允许,不表示业务上可随意改。

restart parameter

shared_buffers
max_connections
max_worker_processes
shared_preload_libraries
huge_pages

写进 config 后 reload:

SELECT name, setting, pending_restart
FROM pg_settings
WHERE pending_restart;

pending_restart=true 表示 file 中的新值尚未成为 effective value。不能把 config diff 当作运行事实。

reload parameter

SIGHUP:

SELECT pg_reload_conf();

或平台命令。reload:

  • 重新读取配置;
  • 不停止 server;
  • 不保证每个参数/每个 backend 立即按你想象生效;
  • 不证明配置无 syntax/semantic error;
  • 不处理 postmaster parameter。

先查 pg_file_settings.error,再 reload,随后查 effective/source。

backend-start parameter

一些设置只在新 backend 建立时取得。reload 后:

new sessions see candidate
old sessions retain previous

connection pool 可让“旧 session”存活很久。变更计划要包括:

  • pool recycle/drain;
  • prepared/session state;
  • transaction 不中断;
  • 新旧 session 混合窗口;
  • verification 分别取样。

session 与 transaction

SHOW work_mem;

SET work_mem = '32MB';
-- 当前 session 后续 statement 使用

BEGIN;
SET LOCAL work_mem = '128MB';
-- 仅当前 transaction
COMMIT;
-- 回到 session value

RESET work_mem;
-- 回到 session default

SET LOCAL 在 transaction 外没有你想要的持久语义。transaction rollback 也影响配置 变化;用 connection pool 时必须测试 reset 行为。

查单位与规范化值

pg_settings.setting 常是 base unit:

SELECT
    name,
    setting,
    unit,
    vartype,
    min_val,
    max_val,
    enumvals
FROM pg_settings
WHERE name IN ('work_mem', 'shared_buffers', 'checkpoint_timeout');

不要把:

shared_buffers setting=62592

读成 bytes;unit 是 8kB

27.5.2 系统、数据库、角色与事务覆盖层

global 配置层

来源可能包括:

compiled boot value
postgresql.conf + includes
postgresql.auto.conf / ALTER SYSTEM
postmaster command-line -c
environment/client startup

postgresql.auto.conf 在普通 config 后读取;server command-line setting 又可覆盖 file。 参考沙箱:

max_connections = 500
source          = command line

所以在 postgresql.conf 写 200、reload/restart 后,若 Patroni/postmaster 仍用 -c max_connections=500,effective 仍可能是 500。

database/role defaults

ALTER DATABASE app
SET statement_timeout = '5s';

ALTER ROLE dbuser_app
SET work_mem = '16MB';

ALTER ROLE dbuser_app
IN DATABASE app
SET statement_timeout = '2s';

新 login 的优先关系可概括为:

global
  < database-specific
  < role-specific
  < role-in-database-specific
  < session SET / startup option
  < transaction SET LOCAL

database 与 role 的精确冲突规则:role-in-database 最具体;role-specific 覆盖 database-specific。

官方 Setting Parameters 强调 ALTER DATABASE/ALTER ROLE 只在新 session建立时应用。SET ROLE 不会重新 加载目标 role 的配置 default。

catalog 事实

这些 default 存在:

SELECT
    setdatabase::regdatabase,
    setrole::regrole,
    setconfig
FROM pg_db_role_setting
ORDER BY setdatabase, setrole;

需要处理 OID=0 的 all database/all role 显示;不要直接把系统 catalog 结果发给不该 看到 role policy 的用户。

current session 的 source

SELECT
    name,
    setting,
    unit,
    source,
    sourcefile,
    sourceline,
    reset_val,
    boot_val
FROM pg_settings
WHERE name = 'statement_timeout';

sourcefile 只对有 pg_read_all_settings 等权限的用户可见。公共报告不应发布主机 绝对路径。

注意:

source

在当前 session 被 SET 后会显示 session source;要验证 cluster default,需要新建 干净 session 或查 catalog/file,不要在已被测试脚本修改的 session 中判断。

ALTER SYSTEM

ALTER SYSTEM SET work_mem = '64MB';
SELECT pg_reload_conf();

写入 postgresql.auto.conf。它适合某些 standalone 管理模式,但在 IaC/Patroni/Pigsty 中会产生第二个 desired-state writer。

Pigsty 官方 parameter scopes 指出,受管集群的 postgresql.auto.conf 可由 pg_parameters 管理,手工 ALTER SYSTEM 可能被下一次 playbook 覆盖。生产持久变更应回到 inventory/desired state,除非有明确 break-glass 流程和回写。

ALTER SYSTEM RESET ALL 很危险

它不是“恢复 PostgreSQL 默认”,而是清空 postgresql.auto.conf 中 ALTER SYSTEM 设置;文件可能还有平台管理内容。不要为了撤一项变更执行 RESET ALL。

精确回退:

ALTER SYSTEM RESET work_mem;

仍要确认 lower-priority value 是预期值。

startup packet / PGOPTIONS

libpq:

env PGOPTIONS="-c statement_timeout=2s -c plan_cache_mode=auto" \
  psql ...

只影响连接 session。第 27 章实验用它确保 candidate 不落盘。

风险:

  • application 可覆盖平台 default;
  • pool 连接建立时固定;
  • 不允许的 GUC 会导致连接失败;
  • connection string/log/env 可能泄露;
  • startup setting provenance 易被忽略。

应用允许的 startup option 应纳入 policy。

自定义 GUC 与 extension

extension 可能增加:

shared_preload_libraries
extension.parameter
custom namespace

参数在 extension 未加载/版本变化时可能无效或阻止启动。升级前检查:

available extension version
preload library presence
pg_file_settings errors
standby binary parity
rollback binary compatibility

27.5.3 配置漂移、审计、回退和滚动风险

一条事实查询

SELECT
    name,
    setting,
    unit,
    context,
    source,
    sourcefile,
    sourceline,
    pending_restart
FROM pg_settings
ORDER BY name;

它回答 effective/session fact。配置文件事实:

SELECT
    sourcefile,
    sourceline,
    seqno,
    name,
    setting,
    applied,
    error
FROM pg_file_settings
ORDER BY seqno;

官方 pg_file_settings 指出:

  • 每条 file entry 一行;
  • invalid/syntax error 出现在 error
  • 被后续同名项覆盖时 applied=false,不一定是 error;
  • 它反映当前文件内容,不是 last-applied runtime。

两张 view 要一起看。

duplicate setting

postgresql.conf:100  work_mem=4MB
included/app.conf:20 work_mem=16MB
postgresql.auto.conf work_mem=64MB
command line         none

只 grep 第一处会误判。用 seqno/applied/source 还原 precedence。

drift 类型

drift desired configured effective
未应用 new new old
手工热改 old manual new manual new
command override desired desired command
session override desired desired session
member mismatch same differs by node differs
pool stale new new old/new sessions
invalid file new error old

每种 remediation 不同。

配置 snapshot 不要泄密

pg_settings 里可能有:

  • file path;
  • library/path;
  • connection-like extension setting;
  • topology;
  • logging destination。

私密 evidence 保存完整;公共报告使用 allowlist:

name
normalized setting
unit
context
coarse source
pending_restart

不发布 sourcefile absolute path、secret 或 raw extension config。

变更前检查

target cluster/member/role
current desired commit
current effective values on every member
file errors
pending_restart
HA health/lag
backup/recovery health
resource headroom
active DDL/maintenance
pool/session lifecycle
rollback value and command

参数名相同不代表 primary/replica 应完全相同,例如 delayed replica;但差异必须是 desired,而不是 drift。

reload 风险

reload 低于 restart,不等于零风险:

  • logging 参数可制造 I/O storm;
  • autovacuum 参数可启动更多工作;
  • timeout 可中断新 workload;
  • HBA/SSL/config error 可影响连接;
  • query cost 可在新 planning 时改变 plan;
  • backend-start setting 造成混合。

reload 后观察:

config log
pg_settings effective/source
new and old session sample
query/latency/resource
HA/replica/archive

rolling restart 风险

restart parameter 在 HA cluster 中通常逐 member:

replica 1
  -> restart
  -> recover/catch up/validate
replica 2
  -> ...
planned switchover if needed
old primary

但是否安全取决于 parameter:

  • standby max_connections 不应低于 primary,否则 recovery query 限制;
  • max_worker_processes standby 需要与 primary 相容;
  • shared_preload_libraries 的 extension/binary 每台都要存在;
  • protocol/physical compatibility;
  • restart 期间 N+1 capacity;
  • failover 在 mixed-version/mixed-config 窗口的行为。

不能一概写“滚动无中断”。

rollback 也可能 restart

若 candidate 是 postmaster:

apply candidate -> rolling restart
regression -> restore desired -> another rolling restart

这段时间风险是两倍操作,不是一条 git revert。change window 必须预留 rollback 时长和 N+1 capacity。

failover 中的 source of truth

Patroni 管理的参数可能来自 DCS/postmaster command line。只编辑 local postgresql.conf

  • Patroni 可能重写;
  • failover 后 candidate 消失;
  • replica effective 不同;
  • automation reconcile 回旧值。

变更前先确定:

who owns this parameter?
template, inventory, DCS, auto.conf, role catalog, or application?

一个参数只能有一个持续 desired-state owner。

configuration ADR

parameter: ...
owner: ...
current:
  desired: ...
  configured: ...
  effective: ...
  source: ...
context: postmaster|sighup|user|...
scope: cluster|instance|database|role|session
hypothesis: ...
members:
  - name: ...
    before: ...
apply:
  method: ...
  order: ...
  observation: ...
rollback:
  method: ...
  order: ...
  maximum_time: ...
failure:
  mixed_state_behavior: ...
  failover_behavior: ...
validation:
  native_sql: ...
  file_fact: ...
  Pigsty: ...

参数值只是 ADR 中一行;scope、owner、effective evidence 与 mixed-state behavior 同样重要。


上一节:规划器、并行与连接参数 · 返回本章目录 · 下一节:模板参数与集群变更 · 查看全书目录 · 查看索引中心