【问题标题】:PostgreSQL full-text search with arraysPostgreSQL 带数组的全文搜索
【发布时间】:2017-01-03 15:10:45
【问题描述】:

我想在我的应用程序中实现全文搜索,但我遇到了一些与我的数组类型列相关的障碍。如何实现 psql 触发器,以便在更新我的“对象”表时,将其数组列的每个元素(它们是字符串)添加到我的“搜索”表的 tsvector 列?

【问题讨论】:

  • 只需将数组中的所有元素连接在一起(中间有空格)并将其用作您的文档。
  • @univerio 对,理论上我理解。但是,我将如何在触发器中将其作为 SQL 实际执行。我知道当派生列是文本时如何更新我的 tsvector 列。但是如何提取数组的各个元素(在发出的 SQL 中以创建触发器)。 to_tsvector() 是否仅适用于数组(也适用于数组的每个元素)?似乎不太可能。
  • 这个 SQLAlchemy 有什么关系?我的意思是,虽然您可以创建 SQLA 事件处理程序,但 Postgresql 中的 SQL 触发器可能会更好地服务。
  • @IljaEverilä 我想只是在某种意义上,可能有一种方法可以通过我目前不知道的 sqlalchemy 创建触发器。我正在使用 sqlalchemy 及其声明性基类将我的表映射到 PostgreSQL。
  • 在 Postgresql 中使用 array_to_string(anyarray, text [, text]) 将数组连接到文本。对于 SQLA 和触发器,请看这里stackoverflow.com/questions/8929738/…

标签: arrays postgresql sqlalchemy full-text-search


【解决方案1】:

在 Postgres 9.6 array_to_tsvector was added 中。

如果你正在处理同一张表,你可以这样写。

CREATE FUNCTION tsv_trigger() RETURNS trigger AS $$
  begin
    IF (TG_OP = 'INSERT') OR old.array_column <> new.array_column THEN
     new.tsv := array_to_tsvector( new.array_column);
    END IF;
   return new;
end
$$ LANGUAGE plpgsql;

CREATE TRIGGER tsvectorupdate BEFORE INSERT OR UPDATE
ON my_table FOR EACH ROW EXECUTE PROCEDURE tsv_trigger();

如果你正在处理两个表而不是你需要编写更新

CREATE FUNCTION cross_tables_tsv_trigger() RETURNS trigger AS $$
  begin
    IF (TG_OP = 'INSERT') OR old.array_column <> new.array_column THEN
     UPDATE search_table st
     SET tsv = array_to_tsvector( new.array_column )
     WHERE st.id = new.searchable_record_id
    END IF;
   # you can't return NULL because you'll break the chain 
   return new; 
end
$$ LANGUAGE plpgsql;

注意它会不同于默认的 to_tsvector(array_to_string()) 组合。

它没有位置编号和小写规范化,因此您可以获得意想不到的结果。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-03-09
    • 2023-03-22
    • 2013-07-25
    • 2011-04-14
    • 1970-01-01
    • 2016-06-18
    相关资源
    最近更新 更多