在PostgreSQL GIN索引中使用JSON对象值
我想为我的JSONB对象中的所有值创建一个trgm-GIN索引在PostgreSQL GIN索引中使用JSON对象值,postgresql,plpgsql,indices,Postgresql,Plpgsql,Indices,我想为我的JSONB对象中的所有值创建一个trgm-GIN索引obj 我想到的第一个方法是: CREATE INDEX table_values_idx ON table USING GIN (array_to_string( (SELECT value FROM jsonb_each_text(obj)), ' ') gin_trgm_ops); 当然,上述方法不起作用,因为子查询(SELECT)不能在PostgreSQL索引中使用 有没有其他方法不使用子查询就连接J
obj
我想到的第一个方法是:
CREATE INDEX table_values_idx ON table
USING GIN (array_to_string(
(SELECT value FROM jsonb_each_text(obj)), ' ') gin_trgm_ops);
当然,上述方法不起作用,因为子查询(SELECT
)不能在PostgreSQL索引中使用
有没有其他方法不使用子查询就连接JSONB对象的值?您需要为此定义自定义函数,因为内置的
json[b]
函数都返回sometype集
create or replace function jsonb_values(jsonb)
returns text array
language sql
immutable
as $func$
select case jsonb_typeof($1)
when 'null' then array[]::text[]
when 'object' then array(select v from jsonb_each($1) e, unnest(jsonb_values(e.value)) v)
when 'array' then array(select v from jsonb_array_elements($1) e, unnest(jsonb_values(e)) v)
else array(select v from jsonb_build_array($1) a, jsonb_array_elements_text(a) v)
end
$func$;
使用此选项,您可以创建一个索引,如:
CREATE INDEX table_values_idx ON table
USING GIN (array_to_string(jsonb_values(obj), ' ') gin_trgm_ops);
之后,您可以将此索引用于类
和FTS查询:
select *
from table
where array_to_string(jsonb_values(obj), ' ') like '%abc%'
谢谢,尽管这看起来像是作弊,因为SELECT也出现在函数中;-)我采用了您的解决方案的一个变体,它似乎有效。@lue3Seba不幸的是,如果函数中没有SELECT
,它就无法解决。此变体还处理内部数组和对象,但如果不需要,请确保可以简化它。我只是试着想想任何可能性。