Solr索引:外部文件处理与预分析字段类型详解
概述
Solr提供了两种特殊的字段类型来处理非常规的数据存储和处理需求:
- ExternalFileFieldType:支持在外部文件中存储字段值
- PreAnalyzedFieldType:支持接收已经经过分析处理的token流
这两种字段类型为特定场景下的数据处理提供了灵活的解决方案。
ExternalFileField类型
弃用警告
ExternalFileField已被弃用,将在未来版本中移除。对于数值字段,建议使用就地更新(in-place updates)功能。
工作原理
ExternalFileField
类型允许在Solr索引外部的文件中指定字段值。该字段的文件包含从键字段到字段值的映射关系。
与在文档索引时指定字段不同,Solr从外部文件中查找该字段的值。
重要限制
- 外部字段不可搜索
- 只能用于函数查询或显示
- 适用于需要频繁更新特定字段而不想更新整个文档的场景
适用场景
ExternalFileField特别适用于需要频繁更新特定字段的情况:
典型示例:基于浏览次数的文档排名
- 排名可能需要每日或每小时更新
- 文档的其他内容更新频率较低
- 使用ExternalFileField可避免仅为更新排名而重建整个文档
Schema配置
1 | <fieldType name="entryRankFile" |
配置参数说明:
keyField
:定义外部文件中的键字段(通常是索引的唯一键)defVal
:为外部文件中没有条目的文档定义默认值stored
/indexed
:通常设置为false
外部文件格式
文件位置和命名
- 位置:Solr的索引目录(默认为
$SOLR_HOME/data
) - 命名规则:
external_fieldname
或external_fieldname.*
- 示例:
external_entryRankFile
或external_entryRankFile.txt
文件版本管理
1 | # 如果存在多个 .* 模式的文件 |
文件内容格式
1 | doc33=1.414 |
格式特点:
- 等号左边:键字段值
- 等号右边:字段值
- 键不需要唯一
- 文件不需要排序(但排序后查找更快)
外部文件重新加载
通过事件监听器实现自动重载:
1 | <listener event="newSearcher" |
PreAnalyzedField类型
基本概念
PreAnalyzedField
类型允许向Solr发送序列化的token流,可选择包含字段的独立存储值,无需在Solr中进行额外的文本处理。
适用场景
- 已有外部文本处理管道(分词、注释、词干化、同义词插入等)
- 需要利用Lucene TokenStream的丰富属性
- 要求精确控制分析过程
序列化解析器
Solr提供两种开箱即用的实现:
1. JsonPreAnalyzedParser(默认)
- 使用JSON格式表示字段内容
- 默认解析器
- 结构化程度高,功能完整
2. SimplePreAnalyzedParser
- 使用简单的纯文本格式
- 在某些情况下比JSON更容易创建
- 轻量级选择
配置参数
parserImpl:
- 实现PreAnalyzedParser接口的类的完全限定名
- 默认值:
org.apache.solr.schema.JsonPreAnalyzedParser
查询时分析器配置
1 | <fieldType name="pre_with_query_analyzer" class="solr.PreAnalyzedField"> |
JsonPreAnalyzedParser详解
JSON格式结构
1 | { |
顶级键说明
键 | 描述 | 必需性 |
---|---|---|
v |
版本键,当前支持版本为1 |
必需 |
str |
字段的存储字符串值 | 可选 |
bin |
字段的存储二进制值(Base64编码) | 可选 |
tokens |
序列化的token流(JSON列表) | 可选 |
Token属性详解
键 | 描述 | Lucene属性 | 值类型 | 必需性 |
---|---|---|---|---|
t |
token内容 | CharTermAttribute | UTF-8字符串 | 必需 |
s |
起始偏移 | OffsetAttribute | 非负整数 | 可选 |
e |
结束偏移 | OffsetAttribute | 非负整数 | 可选 |
i |
位置增量 | PositionIncrementAttribute | 非负整数(默认1) | 可选 |
p |
载荷 | PayloadAttribute | Base64编码 | 可选 |
y |
词法类型 | TypeAttribute | UTF-8字符串 | 可选 |
f |
标志 | FlagsAttribute | 十六进制整数字符串 | 可选 |
完整示例
1 | { |
SimplePreAnalyzedParser详解
格式语法
1 | content ::= version (stored)? tokens |
转义字符
转义序列 | 描述 |
---|---|
\ |
字面空格字符 |
\, |
字面逗号字符 |
\= |
字面等号字符 |
\\ |
字面反斜杠字符 |
\n |
换行符 |
\r |
回车符 |
\t |
水平制表符 |
支持的属性
名称 | 描述 | Lucene属性 | 值格式 |
---|---|---|---|
i |
位置增量 | PositionIncrementAttribute | 整数 |
s |
起始偏移 | OffsetAttribute | 整数 |
e |
结束偏移 | OffsetAttribute | 整数 |
y |
词法类型 | TypeAttribute | 字符串 |
f |
标志 | FlagsAttribute | 十六进制整数 |
p |
载荷 | PayloadAttribute | 十六进制格式字节 |
示例
基本示例
1 | 1 one two three |
- 版本:1
- 存储值:null
- tokens:one(0-3), two(4-7), three(8-13)
带属性示例
1 | 1 one,s=123,e=128,i=22 two three,s=20,e=22 |
带存储值示例
1 | 1 =This is the stored part with \= |
实践建议
ExternalFileField使用建议
性能优化:
- 保持外部文件相对较小
- 考虑对文件进行排序以提高查找速度
- 使用适当的默认值
维护策略:
- 建立文件更新和重载的自动化流程
- 监控外部文件的大小和更新频率
- 实施版本控制和备份策略
PreAnalyzedField使用建议
格式选择:
- 复杂需求选择JSON格式
- 简单场景选择SimplePreAnalyzed格式
- 考虑生成和解析的复杂度
性能考虑:
- 预分析可能会增加索引体积
- 权衡预处理时间与索引时间
- 监控内存使用情况
总结
ExternalFileField和PreAnalyzedField为Solr提供了处理特殊数据需求的灵活方案。虽然ExternalFileField已被弃用,但理解其概念对于数据迁移和现有系统维护仍有价值。PreAnalyzedField则为需要精确控制文本分析过程的场景提供了强大的解决方案。
正确使用这些字段类型可以显著优化特定场景下的性能和功能需求,但也需要仔细考虑实现复杂度和维护成本。