PostgreSQL 17/18 不支持 CREATE POLICY IF NOT EXISTS 或 CREATE OR REPLACE POLICY,可重复迁移策略有三种:一是在同一事务中先 DROP POLICY IF EXISTS 再 CREATE POLICY,能确保定义正确,但 DROP 会取 ACCESS EXCLUSIVE 锁,事务外执行会出现无策略空窗,FORCE 下所有租户查不到数据;二是用 DO 块查 pg_policies 再创建,适合只建不改的策略,并发部署需加 advisory 锁;三是仅改表达式或角色时用 ALTER POLICY,但同样取 ACCESS EXCLUSIVE 锁且策略不存在时会失败。建议配合 lock_timeout。
文章讨论PostgreSQL中ALTER TABLE等模式变更的锁等待问题:即使语句本身很快,若等待ACCESS EXCLUSIVE锁,会阻塞后续所有读取。关键在于锁的获取时间、语句持续时间和事务持有时间。建议设置lock_timeout快速失败,并用NOT VALID约束或CREATE INDEX CONCURRENTLY等弱锁操作,避免长时间阻塞。
排查Postgres锁问题:先在pg_stat_activity中查找wait_event非空的等待进程,再用pg_locks定位持锁进程并追溯其操作。可通过COMMIT、ROLLBACK、pg_cancel_backend或pg_terminate_backend解除阻塞。常见锁源有ALTER TABLE、ORM事务、非并发建索引和VACUUM FULL。建议开启log_lock_waits并设置lock_timeout以预防。
完成下面两步后,将自动完成登录并继续当前操作。