1 在服务器上安装Solr8.3
官网下载:https://www.apache.org/dyn/closer.lua/lucene/solr/8.3.0/solr-8.3.0.zip
下完后是zip包,新建/usr/local/solr文件夹,将zip包解压到次目录
2 启动solr
进入到bin目录,执行: ./solr start -force
默认端口为8983,可打开浏览器直接访问了
3 创建core
新建core需要自定义配置文件
将/usr/local/solr/solr-8.3.0/server/solr/configsets/_default/conf 文件夹
复制到/usr/local/solr/solr-8.3.0/server/solr/new_core2
name和instanceDir即上一步复制的文件夹路径,dataDir、config、schema建议默认就行,点击add
上面是通过solr页面添加core,也可以通过linux窗口添加,具体:
到bin目录下,如果有权限限制,需要先设置全局的solr验证:
export SOLR_AUTHENTICATION_OPTS='-Dbasicauth=user:password'
export SOLR_AUTH_TYPE='basic'
创建core: ./solr create -c [core_name] ,这里core_name使用new_core2
将/usr/local/solr/solr-8.3.0/server/solr/configsets/_default/conf 文件夹
复制到/usr/local/solr/solr-8.3.0/server/solr/new_core2
在new_core2文件夹下新建data文件夹和core.properties文件
修改core.properties文件
#Written by CorePropertiesLocator
#Fri Nov 29 09:15:38 UTC 2019
name=new_core2
config=conf/solrconfig.xml
schema=conf/manage-schema
dataDir=data
重启solr即可
4 导入postgresql的数据到solr
现将solr自带的两个jar包复制到lib目录,然后再从maven下载postgresql的jar复制到lib目录
进入到 /usr/local/solr/solr-8.3.0/dist/目录
复制solr-dataimporthandler-8.3.0.jar 和solr-dataimporthandler-extras-8.3.0.jar到
/usr/local/solr/solr-8.3.0/server/solr-webapp/webapp/WEB-INF/lib目录下,同事postgresql的jar也放进去
复制数据配置文件db-data-config.xml到我们新建的文件夹下:
cp /usr/local/solr/solr-8.3.0/example/example-DIH/solr/db/conf/db-data-config.xml /usr/local/solr/solr- 8.3.0/server/solr/new_core2/conf,并重命名为postgresql_db.xml,方便识别,可以不改
修改此文件:
<dataConfig>
<dataSource driver="org.postgresql.Driver" url="jdbc:postgresql://IP地址:端口/数据库" user="用户名" password="密码" />
<document>
<entity name="news" query="select id,title,content from why_news"
deltaQuery="select id from item where last_modified > '${dataimporter.last_index_time}'">
<field column="id" name="id" />
<field column="title" name="title" />
<field column="content" name="content" />
</entity>
</document>
</dataConfig>
其他多余的文字不用就删掉,不然导数据的时候报错
编辑同目录下的第二个配置文件solrconfig.xml
在倒数第二行添加
<requestHandler name="/dataimport" class="org.apache.solr.handler.dataimport.DataImportHandler">
<lst name="defaults">
<str name="config">postgresql_db.xml</str>
</lst>
</requestHandler>
编辑同目录的第三个配置文件managed-schema,加入想要导入的表的列,在倒数第二行添加
<field name="title" type="string" indexed="true" stored="true"/>
<field name="content" type="string" indexed="true" stored="true"/>
至此就可以重启solr并导入数据了
重启: ./solr restart -force
选择新创建的core --> 选择 DateImport
--> 选择 full-import
全量导入 --> 提交 --> 点击Refresh刷新
可以查看刚导入的数据
这里注意导入数据的配置必须要保证主键不重复,否则实际导入的数据条数和查询所有结果的条数不符合,id重复会被覆盖
这里我的logic_id是不会重复的,所以我将logic_id用作solr的主键id,加上其他的资源表都要导入,下面是完整的postgresql_db.xml
这里我只搜索标题(有title和name,都存储为title)和内容(有content和description,都存储为description)
现在我这里总共的数据导入信息
5 使用IK Analyzer中文分词器
因为使用的Solr8.3,试过老版的加入IK jar的方法不能用,这里使用IK solr7的jar包:ik-analyzer-solr7-7.x.jar
下载地址:https://search.maven.org/search?q=com.github.magese
下载完成将此jar包放到 /usr/local/solr/solr-8.3.0/server/solr-webapp/webapp/WEB-INF/lib下面
配置使用IK Analyzer,编辑managed-schema文件,加入以下代码:
<!-- ik分词器 -->
<fieldType name="text_ik" class="solr.TextField">
<analyzer type="index">
<tokenizer class="org.wltea.analyzer.lucene.IKTokenizerFactory" useSmart="false" conf="ik.conf"/>
<filter class="solr.LowerCaseFilterFactory"/>
</analyzer>
<analyzer type="query">
<tokenizer class="org.wltea.analyzer.lucene.IKTokenizerFactory" useSmart="true" conf="ik.conf"/>
<filter class="solr.LowerCaseFilterFactory"/>
</analyzer>
</fieldType>
保存退出之后重启solr即可看到IK Analyzer分词
下面是分词结果:
既然使用了IK ,那么现在就可以配置搜索了,编辑managed-schema,在IK配置下面追加:
<field name="logic_id" type="string" indexed="true" stored="true"/>
<field name="title" type="text_ik" indexed="true" stored="true"/>
<field name="description" type="text_ik" indexed="true" stored="true"/>
<field name="resource_keywords" type="text_ik" indexed="true" stored="false" multiValued="true"/>
<copyField source="title" dest="resource_keywords"/>
<copyField source="description" dest="resource_keywords"/>
这里不需要参与搜索的如logic_id,type就写string,要参与的如title就使用type为text_ik
copyField是用了某一个搜索具有搜索多条的功能,传说中的一片顶四片,这里resource_keywords绑定了
title和description两个字段的搜索,配置完成之后可以试一下
6 使用solrj完成搜索功能,核心代码如下
后面就是对搜索的结果封装打包返回给前端
使用swagger测试效果图
7 使用Spring的定时任务定时同步数据库数据到solr
使用的是HttpClent定时发送请求,请求url格式
http://ip:端口/solr/core的名称/dataimport?command=full-import&clean=%20true&commit=true&wt=json&indent=true&verbose=false&optimize=false&debug=false&id=1
只需要改下ip端口和core的名称即可
@Component
@Configuration //1.主要用于标记配置类,兼备Component的效果。
@EnableScheduling // 2.开启定时任务
public class SolrImportDataFromPostgresqlSchedule {
private static final Logger LOGGER = LoggerFactory.getLogger(SolrImportDataFromPostgresqlSchedule.class);
//@Scheduled(cron = "0/5 * * * * ?")
//或直接指定时间间隔,例如:30秒
@Scheduled(fixedRate=30000)
private void configureTasks() {
String uri =
"http://ip地址:8983/solr/new_core2/dataimport?command=full-import&clean=%20true&commit=true&wt=json&indent=true&verbose=false&optimize=false&debug=false&id=1";
CloseableHttpClient client = null;
CloseableHttpResponse response = null;
try {
HttpGet httpGet = new HttpGet(uri);
client = HttpClients.createDefault();
response = client.execute(httpGet);
HttpEntity entity = response.getEntity();
String result = EntityUtils.toString(entity);
LOGGER.info(result);
} catch (ClientProtocolException ex) {
ex.printStackTrace();
} catch (IOException ex) {
ex.printStackTrace();
} finally {
if (response != null) {
try {
response.close();
} catch (IOException ex) {
ex.printStackTrace();
}
}
if (client != null) {
try {
client.close();
} catch (IOException ex) {
ex.printStackTrace();
}
}
}
}
下面是定时任务控制台输出
至此使用solr完成搜索功能就大功告成了