mongodb向solr进行数据同步,须安装mongo-connector插件,此外,mongodb和solr均需要进行相关配置。
mongodb的配置
由于插件mongo-connector同步数据时,是读取副本集的oplog,因此,mongodb须配置主从库,具体步骤可参考菜鸟教程。
solr的配置
- solrconfig.xml,在该文件中添加,<requestHandler name="/admin/luke" class="org.apache.solr.handler.admin.LukeRequestHandler" />
- managed-schema,对该文件中的部分内容进行修改,具体如下:
<uniqueKey>id</uniqueKey>
==>
<uniqueKey>_id</uniqueKey>
<field name="id" type="string" indexed="true" stored="true" required="true" multiValued="false" />
==>
<field name="_id" type="string" indexed="true" stored="true" required="true" multiValued="false" />
并添加如下内容:
<field name="_ts" type="long" indexed="true" stored="true" />
<field name="ns" type="string" indexed="true" stored="true"/>
- 关于数组的问题,managed-schema中的字段应该做一些修改,例如数组file字段:
<field name="file" type="string" indexed="true" stored="true" multiValued="true"/>
<dynamicField name="file*" type="text_general" indexed="false" stored="false" />
<copyField source="file*" dest="file"/>
- 关于数组有序化的问题,须在managed-schema、solrconfig.xml和update-script.js等三个文件中做修改,例如数组cataRows字段。
首先,managed-schema中,cataRows字段如下:
<field name="cataRows" type="text_general" indexed="true" stored="true" multiValued="true"/>
<dynamicField name="cataRows*" type="text_general" indexed="false" stored="false" />;
其次,solrconfig.xml中,做如下修改:
<requestHandler name="/update" class="solr.UpdateRequestHandler">
<lst name="defaults">
<str name="update.chain">script</str>
</lst>
</requestHandler>
<updateRequestProcessorChain name="script">
<processor class="solr.StatelessScriptUpdateProcessorFactory">
<str name="script">update-script.js</str>
<lst name="params">
<str name="config_param">example config parameter</str>
</lst>
</processor>
<processor class="solr.RunUpdateProcessorFactory" />
</updateRequestProcessorChain>
最后,update-script.js中,找到processAdd(cmd)方法,在该方法中获取cataRows的各元素,然后做好排序,之后再添加到solr库中,(注意:该文件中使用的是一种类似于js的语言,但又有所不同,例如变量声明无须var关键字)例如:
field_names = doc.getFieldNames().toArray();
index = 0;
cataRows = [];
for(i=0; i < field_names.length; i++) {
field_name = field_names[i];
if (/cataRows.*/.test(field_name)) {
cataRows[index] = field_names[i];
index++;
}
}
/*该方法为冒泡排序,复杂度较高,但是使用快排一直无法初始化,初步怀疑是该文件的语言无法处理复杂逻辑的代码,不确定*/
for(i=0;i<cataRows.length-1;i++){
for(j=i+1;j<cataRows.length;j++){
a = cataRows[i].split(".")[1];
b = cataRows[j].split(".")[1];
if(parseInt(a)>parseInt(b)){
temp=cataRows[i];
cataRows[i]=cataRows[j];
cataRows[j]=temp;
}
}
}
for(i=0; i < cataRows.length; i++) {
field_name = cataRows[i];
field_value = doc.getFieldValue(field_name);
doc.addField("cataRows", field_value);
logger.info("update-script#processAdd: field_name=" + field_name);
}
mongo-connector的安装
mongo-connector的安装步骤如下:
- pip install mongo_connector
- pip install solr-doc-manager
数据同步命令:
nohup mongo-connector -m 127.0.0.1:40000 -n solrbooks.* -t http://172.18.*.*:8082/solr/book -d solr_doc_manager --auto-commit-interval=1 &
注意1:如果执行不成功,报出ImportError: No module named gridfs错误,则重新安装一下pymongo即可。
注意2:如果执行不成功,报出UnicodeDecodeError: 'ascii' codec can't decode byte 0xe5 in position 459: ordinal not in range(128)错误,则是solr的managed-scheme 文件中某个字段的配置有误造成的,请详细检查。