为SQLite全文搜索(FTS)创建触发器时出现“不安全地使用虚拟表”

rkkpypqq  于 2023-05-29  发布在  SQLite
关注(0)|答案(1)|浏览(174)

我试图通过遵循官方文档在外部内容表中使用SQLite的全文搜索(FTS)扩展。我正在运行来自Arch linux软件包sqlite的sqlite版本3.42.0,当前版本为3.42.0-1。
架构如下:

-- Create main data table
CREATE TABLE users (
    id INTEGER PRIMARY KEY,
    name TEXT NOT NULL
);

-- Create fts index table
CREATE VIRTUAL TABLE users_fts USING fts5 (
    content='users',
    content_rowid='id',
    name
);

-- Create insert trigger
CREATE TRIGGER users_fts_insert AFTER INSERT ON users
BEGIN
    INSERT INTO users_fts (rowid, name) VALUES (new.rowid, new.name);
END;

-- Insert some sample data
INSERT INTO users (rowid, name) VALUES
(NULL, 'John Smith'),
(NULL, 'John Doe'),
(NULL, 'Jane Doe');

当在sqlite3中运行上述步骤时,INSERT步骤失败,并显示错误消息:
Parse error near line 21: unsafe use of virtual table "users_fts"
如果我注解掉触发器块,它就成功地创建了两个表并将值插入到主表中。奇怪的是,FTS表似乎也是用匹配的行创建的,并且这些行似乎在不同的INSERT/UPDATE/DELETE之间保持同步,尽管通过MATCH的实际FTS功能不起作用(例如,MATCH)。SELECT * FROM users_fts WHERE users_fts MATCH 'John'不返回行)。
由于我不想手动处理保持两个表同步的问题,我更希望有一个基于触发器的自动解决方案,如上面所述。问题是在于如何设置触发器,还是在于如何配置FTS表?或者,SQLite FTS中有一些隐藏的限制,排除了这种触发器?
任何帮助在这里将不胜感激!

fnx2tebb

fnx2tebb1#

这是TRUSTED_SCHEMA杂注设置为false的副作用。
这个杂注是在Sqlite3.31中添加的,并且被记录为默认为true,但是3.42现在让sqlite3 shell程序默认禁用它。这似乎是新选项--unsafe-testing的副作用。如果不存在该选项,则包括此选项在内的多个设置将从其默认值切换。
令人高兴的是,用户代码中与数据库的连接不受影响,只影响使用标准sqlite3程序建立的连接。因此,您可以使用--unsafe-testing调用它,或者在启动shell后运行以下命令(每次;它不持久):

PRAGMA trusted_schema=1;

相关问题