postgresql hash索引流复制备库报错

标签: postgresql hash 索引 | 发表时间:2014-06-04 13:19 | 作者:xmarker
出处:http://xmarker.blog.163.com
今天测试了一把postgresql的hash索引,在流复制过程中会有些问题,一下是测试过程:
1.首先搭建pg9.3.4的流复制环境,略,我的环境如下:db3为主库,db4为从库
2.创建测试表及索引
create table t_test(id int,name varchar(512),age int,time timestamp);
postgres=# create index idx_t_test on t_test using hash (name);
CREATE INDEX
插入数据:
postgres=# insert into t_test values (1,'mcl',28,now());
INSERT 0 1
postgres=# insert into t_test values (2,'afas',22,now());
INSERT 0 1
postgres=# insert into t_test values(3,'aaa',32,now());
INSERT 0 1
再批量插入些数据:
postgres=# insert into t_test select a,md5(a::text),a,clock_timestamp() from generate_series(10,1000) a;
INSERT 0 991
看下主库数据条数和备库条数:
db3(主库):
postgres=# select count(*) from t_test ;
 count 
-------
   994
(1 row)
表结构:
postgres=# \d t_test 
              Table "public.t_test"
 Column |            Type             | Modifiers 
--------+-----------------------------+-----------
 id     | integer                     | 
 name   | character varying(512)      | 
 age    | integer                     | 
 time   | timestamp without time zone | 
Indexes:
    "idx_t_test" hash (name)
db4(备库):
postgres=# select count(*) from t_test ;
 count 
-------
   994
(1 row)
表结构:
postgres=# \d t_test 
              Table "public.t_test"
 Column |            Type             | Modifiers 
--------+-----------------------------+-----------
 id     | integer                     | 
 name   | character varying(512)      | 
 age    | integer                     | 
 time   | timestamp without time zone | 
Indexes:
    "idx_t_test" hash (name)
主备库的数据一致,表结构也都完全一样,下面测试;
3.测试hash索引检索:
db3(主库):
postgres=# explain( analyze,verbose,buffers,timing) select * from t_test where name='mcl';
                                                        QUERY PLAN                                                         
---------------------------------------------------------------------------------------------------------------------------
 Index Scan using idx_t_test on public.t_test  (cost=0.00..8.02 rows=1 width=48) (actual time=0.032..0.038 rows=1 loops=1)
   Output: id, name, age, "time"
   Index Cond: ((t_test.name)::text = 'mcl'::text)
   Buffers: shared hit=3
 Total runtime: 0.106 ms
(5 rows)

Time: 0.832 ms
可以看出已经使用了hash索引来扫描,下面看备库
db4(备库):
postgres=#  explain( analyze,verbose,buffers,timing) select * from t_test where name='mcl';
ERROR:  could not read block 0 in file "base/12896/16388": read only 0 of 8192 bytes

这样执行竟然报错,我猜测是因为hash索引因为没有被流复制过来,所以通过索引扫描报错,现在让他走全表扫描试试:
postgres=# set enable_bitmapscan =off;
SET
postgres=# set enable_indexscan =off;
SET
postgres=#  explain( analyze,verbose,buffers,timing) select * from t_test where name='mcl';
                                               QUERY PLAN                                                
---------------------------------------------------------------------------------------------------------
 Seq Scan on public.t_test  (cost=0.00..23.43 rows=1 width=48) (actual time=0.050..0.252 rows=1 loops=1)
   Output: id, name, age, "time"
   Filter: ((t_test.name)::text = 'mcl'::text)
   Rows Removed by Filter: 993
   Buffers: shared hit=11
 Total runtime: 0.416 ms
(6 rows)
果真走全表扫描就可以了

另外索引换成btree索引也是可以的:
postgres=# drop index idx_t_test ;
DROP INDEX
postgres=# create index ind_t_test on t_test (name);
CREATE INDEX
db4(备库)再次查询:
postgres=# select * from t_test where name='mcl';
 id | name | age |            time            
----+------+-----+----------------------------
  1 | mcl  |  28 | 2014-06-04 10:17:00.405492
(1 row)

postgres=#  explain( analyze,verbose,buffers,timing) select * from t_test where name='mcl';
                                                        QUERY PLAN                                                         
---------------------------------------------------------------------------------------------------------------------------
 Index Scan using ind_t_test on public.t_test  (cost=0.28..8.29 rows=1 width=48) (actual time=0.028..0.032 rows=1 loops=1)
   Output: id, name, age, "time"
   Index Cond: ((t_test.name)::text = 'mcl'::text)
   Buffers: shared hit=3
 Total runtime: 0.126 ms
(5 rows)

最后看下官网对hash索引的说明:
Hash index operations are not presently WAL-logged, so hash indexes might need to be rebuilt with REINDEX after a database crash if there were unwritten changes. Also, changes to hash indexes are not replicated over streaming or file-based replication after the initial base backup, so they give wrong answers to queries that subsequently use them. For these reasons, hash index use is presently discouraged.

hash索引目前没有被wal日志记录,因此数据库宕机后可能要重新reindex,而且也不会通过流复制传递到备库,所以在备库查询基于hash索引的时候会报错,所以hash索引目前是不被鼓励使用的。

相关 [postgresql hash 索引] 推荐:

postgresql hash索引流复制备库报错

- - x-marker的博客
今天测试了一把postgresql的hash索引,在流复制过程中会有些问题,一下是测试过程: 1.首先搭建pg9.3.4的流复制环境,略,我的环境如下:db3为主库,db4为从库. 看下主库数据条数和备库条数:. 主备库的数据一致,表结构也都完全一样,下面测试;. 3.测试hash索引检索:.                                                         QUERY PLAN                                                         .

mysql 索引优化 btree hash rtree

- - 数据库 - ITeye博客
mysql里目前只支持4种索引分别是:b-tree,full-text,hash以及r-tree索引. b-tree索引应该是mysql里最广泛的索引的了,除了archive,基本所有的存储引擎都支持它. 1.b-tree在myisam里的形式和innodb稍有不同. 在innodb里面有两种形态:其一是primary key形态其leafnode里存放的是数据.而且不仅存放了索引键的数据,还存放了其他字段的数据.其二是secondary index,其leafnode和普通的b-tree差不多,只是还存放了指向主键的信息.

B-Tree索引与Hash索引的比较

- - SegmentFault 最新的文章
B-Tree索引与Hash索引的比较. 翻译自 http://dev.mysql.com/doc/refman/5.6/en/index-btree-hash.html. 理解B-Tree和Hash的数据结构能够帮助我们预测不同存储引擎下的查询性能差异. 存储引擎在索引中使用这些数据结构,尤其是 MEMORY 同时提供了B-Tree和Hash索引让你选择.

一致性hash

- - 互联网 - ITeye博客
一致性hash算法 - consistent hashing. 分类:  算法艺术2010-02-02 09:19 69836人阅读  评论(97)  收藏  举报. 算法 cache object 服务器 存储 c. 一致性 hash 算法( consistent hashing ).

PostgreSQL 9.1发布

- Kai Chen - Solidot
开源数据库项目PostgreSQL发布了v9.1版. 新版本主要的特性包括:同步复制,序列化快照隔离,支持基于列的排序,近邻邻近索引,外来数据封装,支持SELinux许可控制,等等.

PostgreSQL 9.2发布

- - Solidot
时隔一年之后,开源数据库PostgreSQL发布了v9.2版. 主要新特性包括:原生JSON支持,覆盖索引(covering indexes),改进复制和性能等. PostgreSQL显著改善了可伸缩性:线性可扩展性支持最高64核,仅扫描索引,减少CPU消耗;改进垂直可伸缩性:有效利用大服务器硬件资源,锁管理,仅访问索引等底层操作允许数据库引擎处理更大的工作负荷——每秒最高35万只读查询,每秒写入1.4万条数据.

Hash Collision DoS 问题

- mazhechao - 酷壳 - CoolShell.cn
最近,除了国内明文密码的安全事件,还有一个事是比较大的,那就是 Hash Collision DoS (Hash碰撞的拒绝式服务攻击),有恶意的人会通过这个安全弱点会让你的服务器运行巨慢无比. 这个安全弱点利用了各语言的Hash算法的“非随机性”可以制造出N多的value不一样,但是key一样数据,然后让你的Hash表成为一张单向链表,而导致你的整个网站或是程序的运行性能以级数下降(可以很轻松的让你的CPU升到100%).

局部敏感Hash

- - xiaobaoqiu Blog
之前在项目中做数据聚合去重的逻辑的时候简单看过局部敏感Hash(Locality Sensitive Hashing,简称LSH)这个东东. LSH可以理解为一种衡量文本相似度的算法,特点是散列前的相似点经过哈希之后,也能够在一定程度上相似,并且具有一定的概率保证. 其有坚实的理论依据(98年左右理论就提出来了,99年有第一版实现)并且在高维数据空间中表现优异.

Mysql 和 Postgresql 对比

- - 膘叔
vampire告诉我服务器上安装好了postgreSQL,他也一直在推荐这个玩意,所以了解了一下. Mysql 使用太广泛了,以至于我不得不将一些应用从mysql 迁移到postgresql, 很多开源软件都是以Mysql 作为数据库标准,并且以Mysql 作为抽象基础的,但是具体使用过程中,发现Mysql 有很多问题,所以都迁移到postgresql上了,转一个Mysql 和Postgresql 对比的文章:.

PostgreSQL与MySQL比较

- - 数据库 - ITeye博客
通过执行 MySQL 命令(mysqld)启动实例. 一个实例可以管理一个或多个数据库. 一台服务器可以运行多个 mysqld 实例. 一个实例管理器可以监视 mysqld 的各个实例. 通过执行 Postmaster 进程(pg_ctl)启动实例. 一个实例可以管理一个或多个数据库,这些数据库组成一个集群.