普通索引的文本数据是不可变的,这意味着要刷新数据,我们需要进行完全重建索引。在许多情况下,重建索引可能需要很长时间。为此,使用了 main+delta schema 。
这个概念假设一个大的索引,保存了在某一特定时间的数据快照,以及一个较小的索引,保存了从快照时间到更近日期的变化(增量)。由于后者较小,它可以更频繁地重新索引。增量变化可以是新记录、更新或删除的记录。更新或删除的记录会引入一个问题:当引擎在两个索引中搜索时,它不知道主索引中的某条记录是否已经不再有效。这导致不断显示实际上已删除的记录或(在更新记录的情况下)包含旧版本的记录,而不是增量索引中的新版本。
为了解决这个问题,引入了 kill-list 特性。kill-list 定义了在增量索引中需忽略的文档 ID 列表,告诉引擎这些记录应在之前的索引中被忽略。
sql_query_killlist = \
SELECT id FROM documents WHERE updated_ts>=@last_reindex UNION \
SELECT id FROM documents_deleted WHERE deleted_ts>=@last_reindex
在这个示例中,我们在 kill-list 中包含了自 @last_reindex 以来更新的文档 ID,这个日期是上次主索引发生的时间,以及已删除的文档 ID。documents_deleted 表可以在 documents 中某条记录被删除时手动填充,或者可以使用触发器。
关于 kill-list 需要记住的一件重要事情是,移除是在声明的顺序上执行的之前的索引。
如果您正在对索引进行顺序搜索,则增量必须在主索引 之后。
mysql> SELECT * FROM main,delta WHERE MATCH('...');
同样的情况也适用于我们使用多个增量(如 delta_daily, delta_hourly),顺序应该为 main,delta_daily,delta_hourly,而不是 main,delta_hourly,delta_daily。
kill-list 也用于本地分布式索引,在这种情况下,索引的定义顺序也很重要,即使我们对本地索引进行并行处理(使用 dist_threads > 0):
index dist
{
local = main
local = delta
}