显示重复功能的 postgres 转储

postgres dump showing duplicate FUNCTION

我的 postgres 版本是 9.0.4 我已经创建了我的数据库的 postgres 转储并且包含自定义的重复条目 FUNCTIONS.When 我直接查询我的数据库我没有看到任何重复的条目,但是转储有这个重复项.

以下是我使用 pg_restore -l 命令获取的列表。

37; 1255 16402 FUNCTION public sql_dirdepth(character varying) nidhin
31; 1255 16402 FUNCTION public sql_dirdepth(character varying) nidhin
29; 1255 16403 FUNCTION public sql_getdir(character varying) nidhin
35; 1255 16403 FUNCTION public sql_getdir(character varying) nidhin
30; 1255 16404 FUNCTION public sql_subdir(character varying, integer, integer) nidhin
36; 1255 16404 FUNCTION public sql_subdir(character varying, integer, integer) nidhin
32; 1255 16405 FUNCTION public unnest(anyarray) nidhin
38; 1255 16405 FUNCTION public unnest(anyarray) nidhin

我检查了 DB 中的函数,没有看到任何重复的条目。

CDB=# \df
                                      List of functions
 Schema |      Name       | Result data type  |         Argument data types         |  Type
--------+-----------------+-------------------+-------------------------------------+--------
 public | sql_dirdepth | integer           | character varying                   | normal
 public | sql_getdir   | character varying | character varying                   | normal
 public | sql_subdir   | character varying | character varying, integer, integer | normal
(3 rows)

所以我想知道 pg_dump 是如何在我的转储文件中创建这些函数的重复条目的。

查询

SELECT * 
FROM pg_proc 
WHERE proname || '' IN ('unnest', 'sql_dirdepth', 'sql_getdir', 'sql_subdir');  

给出以下结果。

我可以看到其中有重复项,如何删除重复的函数?

|   proname    | pronamespace | proowner | prolang | procost | prorows | provariadic | proisagg | proiswindow | prosecdef | proisstrict | proretset | provolatile | pronargs | pronargdefaults | prorettype | proargtypes | proallargtypes | proargmodes | proargnames | proargdefaults |                                    prosrc                                    |         probin          | proconfig | proacl |
|--------------|--------------|----------|---------|---------|---------|-------------|----------|-------------|-----------|-------------|-----------|-------------|----------|-----------------|------------|-------------|----------------|-------------|-------------|----------------|------------------------------------------------------------------------------|-------------------------|-----------|--------|
| unnest       |           11 |       10 |      12 |       1 |     100 |           0 | f        | f           | f         | t           | t         | i           |        1 |               0 |       2283 |        2277 |                |             |             |                | array_unnest                                                                 |                         |           |        |
| sql_getdir   |         2200 |       10 |      13 |       1 |       0 |           0 | f        | f           | f         | t           | f         | i           |        1 |               0 |       1043 |        1043 |                |             |             |                | sql_getdir                                                                   | /opt/openkaz/lib/kazsql |           |        |
| sql_subdir   |         2200 |       10 |      13 |       1 |       0 |           0 | f        | f           | f         | t           | f         | i           |        3 |               0 |       1043 |  1043 23 23 |                |             |             |                | sql_subdir                                                                   | /opt/openkaz/lib/kazsql |           |        |
| sql_dirdepth |         2200 |       10 |      13 |       1 |       0 |           0 | f        | f           | f         | t           | f         | i           |        1 |               0 |         23 |        1043 |                |             |             |                | sql_dirdepth                                                                 | /opt/openkaz/lib/kazsql |           |        |
| unnest       |         2200 |       10 |      14 |     100 |    1000 |           0 | f        | f           | f         | f           | t         | i           |        1 |               0 |       2283 |        2277 |                |             |             |                | "select [i] from generate_series(array_lower(,1), array_upper(,1)) i;" |                         |           |        |
| sql_subdir   |         2200 |       10 |      13 |       1 |       0 |           0 | f        | f           | f         | t           | f         | i           |        3 |               0 |       1043 |  1043 23 23 |                |             |             |                | sql_subdir                                                                   | /opt/openkaz/lib/kazsql |           |        |
| sql_dirdepth |         2200 |       10 |      13 |       1 |       0 |           0 | f        | f           | f         | t           | f         | i           |        1 |               0 |         23 |        1043 |                |             |             |                | sql_dirdepth                                                                 | /opt/openkaz/lib/kazsql |           |        |
| unnest       |         2200 |       10 |      14 |     100 |    1000 |           0 | f        | f           | f         | f           | t         | i           |        1 |               0 |       2283 |        2277 |                |             |             |                | "select [i] from generate_series(array_lower(,1), array_upper(,1)) i;" |                         |           |        |
| sql_getdir   |         2200 |       10 |      13 |       1 |       0 |           0 | f        | f           | f         | t           | f         | i           |        1 |               0 |       1043 |        1043 |                |             |             |                | sql_getdir                                                                   | /opt/openkaz/lib/kazsql |           |        |

那是目录数据损坏,因为在 pg_proc 目录中实际上有重复的条目,即使有一个唯一索引保证模式名称、函数名称和参数列表的组合是唯一的。

您应该立即关闭(使数据库崩溃)并对数据目录进行物理备份。这始终是处理数据损坏的第一步。

重新启动数据库后,采用集群的文本模式pg_dumpall,并手动从转储文件中删除重复的条目。将转储恢复到新集群并删除旧集群。

成功消除数据损坏后,您应该立即在新硬件上升级到 PostgreSQL v12,因为 9.0 的旧版本包含许多已知错误,可以导致各种数据损坏。

这是一个很好的例子,为什么升级不仅仅是 IT 部门为了保住工作和惹恼最终用户而发明的东西。