Postgres中的jsonb性能问题

时间:2015-12-15 16:52:28

标签: ruby-on-rails postgresql database-performance postgresql-9.4 jsonb

我在postgres中遇到了jsonb的一些性能问题。我的数据库中有很多产品,每个产品都有一个名为technical_details的列,它保存了所有这些技术细节

{ 
    detail: {
        unit: unit_name,
        value: value 
    }
} 

例如:

{ 
    weight: { 
        unit: ‘kg’,
        value: 1000 
    } 
}

现在我想进行如下查询:

Product Load (149.4ms) 
    SELECT "products".* FROM "products" 
    WHERE (COALESCE(CAST( nullif(technical_details#>>’{weight,value}','') AS FLOAT),0) BETWEEN 500 AND 1500)

但正如您所看到的,进行此类查询需要很长时间。有人知道我如何才能提高这种查询的性能吗?

非常感谢!

修改 正如德米特里所要求的: 这些是我所拥有的与技术细节相关的指数:

"index_products_on_technical_details" gin (technical_details)
"index_products_on_technical_details_width" btree ((technical_details ->> 'width'::text))
"index_products_on_technical_details_weight" btree ((technical_details ->> 'weight'::text))

这是EXPLAIN ANALYZE查询:

Seq Scan on products  (cost=0.00..926.80 rows=22 width=1288) (actual time=0.100..30.563 rows=498 loops=1)
   Filter: ((COALESCE((NULLIF((technical_details #>> '{weight,value}'::text[]), ''::text))::double precision, 0::double precision) >= 500::double precision) AND (COALESCE((NULLIF((technical_details #>> '{weight,value}'::text[]), ''::text))::double precision, 0::double precision) <= 1500::double precision))
   Rows Removed by Filter: 3997
 Planning time: 0.236 ms
 Execution time: 30.740 ms

1 个答案:

答案 0 :(得分:0)

您可以创建基于表达式的索引来加快速度:

create index on products (
  COALESCE(CAST(nullif(technical_details#>>'{weight,value}','') AS FLOAT),0)
);

当然,查看可能不属于同一单元的值有点奇怪。