2016-07-19 28 views
0

我有postgresql 9.5.2生产服务器,有一些严重的索引问题。最强的证据支持这种说法是有些疑问的不一致:Postgresql索引损坏的原因 - postgresql的错误或硬件故障

select count(*) from x inner join y on x.a = y.a 
select *  from x inner join y on x.a = y.a 

的COUNT(*)查询将返回不同数量比选择*查询,刚刚返回的行返回的行数。我尝试的第一件事是真空分析,但这并没有解决问题。最后,为了让服务器再次运行,删除所有索引并重建它们,此时select *和select count(*)查询之间的结果变得一致。

这两个表都没有任何触发器。表x有170万行,表y有690万行和600,000行删除,并且这些表使用外键字段a(它是表x中的主键)和表b中的非空外键约束。数据库服务器位于虚拟机中。服务器是唯一的节点,并且不会复制到其他服务器。系统从来没有崩溃,所以虽然我知道崩溃的服务器或postgres服务可能会损坏索引,但我没有理由相信发生这些事件的原因之一,因为:a)postgres服务从未不可用; b)服务器指出它有这个问题早在这个问题出现之前就已经存在很长时间了。

所有这些数据都表明问题是索引无法正常工作。我对损坏索引的研究通常指向两个原因,postgresql中的错误或硬件故障。

硬件故障的解决方案和数据库本身的错误是通过完全不同的技术来解决的,即一种涉及采购硬件,另一种涉及编写程序来检查索引的完整性,并在必要时采取适当的措施来纠正问题。

我可以收集哪些证据来支持每种理论(硬件故障与软件错误)?

回答

0

防止硬件问题的最佳防范措施是在创建群集时通过使用initdb--data-checksums选项启用页面校验和。
但这不会帮助调查过去的问题,它需要转储/重新加载数据库集群。

如果你做物理备份(与pg_basebackuppg_start_backup()pg_stop_backup),这将是有趣的发现上一次备份,事情仍然正常。这可能很乏味,但它会缩小寻找问题的窗口。

您有fsync = offfull_page_writes = off?或者你使用unreliable storage?那么即使没有错误并且硬件没问题,您的数据库也可能会因崩溃而损坏。检查数据库日志是否存在崩溃。

要了解您是否遇到硬件问题,请查看操作系统日志文件并执行硬件测试。

要检查已知的软件问题,请查看release notes。如果您的索引损坏,您可以要求pgsql-hacker mailing list寻求帮助。

+0

我们使用pg_dump进行备份,备份索引的存在,但我不认为它会复制索引本身。托管服务器的系统没有崩溃,据我所知,postgresql服务器也没有崩溃。 – zelinka