基于Spring+SpringMVC+MyBatis博客系统的开发教程(十四)
Solr 概述
Solr 是一个独立的企业级搜索应用服务器,它对外提供类似于 Web Service 的 API 接口。用户可以通过 HTTP 请求,向搜索引擎服务器提交一定格式的 XML 文件,生成索引;也可以通过 HTTP Get 操作提出查找请求,并得到 XML 格式的返回结果。
它具有以下特点(来自百度百科):
Solr是一个高性能,采用 Java 5 开发,基于 Lucene 的全文搜索服务器。同时对其进行了扩展,提供了比 Lucene 更为丰富的查询语言,同时实现了可配置、可扩展,并对查询性能进行了优化,且提供了一个完善的功能管理界面,是一款非常优秀的全文搜索引擎。
我们使用将 Solr 达到什么样的效果呢?
首先能根据搜索条件进行分词,查询出需要的结果,然后将分词高亮显示。
比如查询:“SSM 框架实战”,分词的结果可能是:“SSM 框架 实战”或者“S S M 框 架 实战”等。
我们将根据分词的结果去数据库查询,将查询结果以高亮显示在页面。
本文主要分三部分来介绍:
- Solr 单元测试;
- Solr 在项目中的应用;
- Tomcat 服务器运行 Solr。
Solr单元测试
Solr 单元测试步骤如下:
- 开启 Solr 服务;
- 添加 Java 操作 Solr 的依赖;
- 编写测试代码。
下载和启动 Solr
下载 Solr
我将 Solr 压缩包放在本课程最后的百度网盘中,大家也可从 Solr 官网中下载.
等待3秒自动跳转到下载页面,如图:
我下载的时候版本是 7.3.1。
点击链接进入后总共有三个版本包:
solr-7.3.1-src.tgz
含有 Lucene 源码 tgz 包;solr-7.3.1.tgz
不含源码 tgz 包;solr-7.3.1.zip
不含源码 zip 包;
我们下载后面两个,tgz 包用于 Linux 系统,zip 包用于 Windows 系统。
启动 Solr
下载完成后,将 zip 后缀压缩包解压到自定义目录,进入到 solr-7.3.1\bin
目录下,shift+鼠标右键,点击在此处打开命令窗口,如果是 Windows 10 系统先 shift+鼠标右键打开 PowerShell 窗口,然后输入 start cmd,打开命令窗口,在命令窗口中输入:
solr start
启动 Solr 服务,如图:
访问端口为8983,我们可以通过 localhost:8983
或者 127.0.0.1:8983
访问 Solr 网页。
进入网页后发现提示“no cores avaiable”,即没有可用的内核,其实就是没有 Solr 的索引库,如图:
那我们就创建一个 core,还是在刚才的命令窗口中输入:solr create -c mycore
。其中 mycore 为 core 的名字,如图
在 solr-7.3.1\server\solr
目录下发现多一个文件夹 mycore,然后再重新进入 Solr 网页查看,发现已经有了我们刚才创建的 mycore。选择mycore,点击后出现一个列表,点击 Query,执行 Execute Query,查询出了一条数据,这是 Solr 默认的。
补充:Solr 重启命令
solr restart -p 8983
-p 后面指定端口号
添加 Java 操作 Solr 的依赖——SolrJ
Java 就是通过 Solrj 来操作 Solr 的。它提供了一些增、删、改、查的方法。使用起来很方便。
在 pom.xml 中引入依赖 solr-solrj
<dependency>
<groupId>org.apache.solr</groupId>
<artifactId>solr-solrj</artifactId>
<version>7.3.0</version>
</dependency>
通过 Solr 客户端对象调用相关方法,操作 Solr,测试类中会介绍。
Solr 与 Spring 的整合
在 src/main/resources
目录下新建 applicationContext-solr.xml
,主要是将 Solr 客户端对象交给 Spring 来管理,配置内容如下:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd">
<bean id="httpSolrClient" class="org.apache.solr.client.solrj.impl.HttpSolrClient">
<constructor-arg name="builder" value="http://localhost:8983/solr/mycore"/>
</bean>
</beans>
通过 Ctrl+鼠标右键点击 HttpSolrClient,查看源码。Ctrl+F 搜索 Builder,发现它有一个构造方法,接收的参数名正是 builder,这里就是构造方法注入,它的参数 name="builder"
是固定格式,value 就是 builder 对应的值,是一个 solrCore 的远程地址,mycore 就是我们刚才创建的。
编写测试代码
单元测试代码都放在了 src/test
目录下。
在 test/java
目录下新建 TestSolrJ.java
代码如下:
@ContextConfiguration(locations = {"classpath:applicationContext-solr.xml"})
public class TestSolrJ extends AbstractJUnit4SpringContextTests {
@Autowired
private SolrClient solrServer;
@Test
public void testSave() throws Exception {
//1.创建一个文档对象
SolrInputDocument inputDocument = new SolrInputDocument();
inputDocument.addField( "id", "32" );
inputDocument.addField( "item_title", "ssm项目开发实战" );
inputDocument.addField( "item_image", "www.ssm.png" );
inputDocument.addField( "author", "wly" );
//2.将文档写入索引库中
solrServer.add( inputDocument );
//3.提交
solrServer.commit();
}
}
代码解读如下:
(1)@ContextConfiguration
注解表示加载配置文件,就是我们之前配置的 Solr 与 Spring 的整合配置文件,如果有多个配置文件用逗号隔开,如:
locations = {"classpath:applicationContext-solr.xml","classpath:spring-mvc.xml"}
(2)测试类要继承 AbstractJUnit4SpringContextTests 测试基类,否则注入不了对象。
(3)通过 @Autowired
注解注入 Solr 客户端对象 SolrClient。
(4)@Test
注解,代表这是一个测试方法。
(5)创建文档对象 SolrInputDocument。
(6)向文档中添加字段和对应的值。
(7)通过客户端对象的 add 方法将文档写入索引库中。
(8)提交(一定要提交,否则添加不成功)。
启动单元测试,点击 testSave,右键选择 Run testSave,启动完成后再次访问 Solr 网页。
执行 Execute Query 发现多了一条数据,就是刚才我们插入的,如下图:
Solr 单元测试完成,通过单元测试说明操作 Solr 成功!
但是发现一个问题,查询出来的结果除了 id 都是 ArrayList 集合形式 []
,如果取值的话转换起来会很麻烦。怎么解决这个问题呢?
主要就是对 solr-7.3.1\server\solr\mycore\conf\
下的配置文件managed-schema进行修改,配置对应的字段以及字段类型,如下:
<field name="id" type="string" multiValued="false" indexed="true" required="true" stored="true"/>
<field name="item_image" type="string" stored="false" docValues="false"/>
<field name="item_title" type="string" />
<field name="item_content" type="string"/>
<field name="author" type="string"/>
之前对应的 type="text_general"
是 Solr 自动生成的,其中
- name:字段的名字;
- type:字段的数据类型;
- multiValued:是否有多值,有多值时设置为 true,否则设置为 false;
- indexed:是否创建索引;
- required:是否必须;
- stored:是否存储数据,如果设置为 false 则不存储,结合
docValues="false"
使得查询不返回结果。
将 item_image
字段设置 stored="false"
和 docValues="false"
进行测试。
在命令窗口输入:
solr restart -p 8983
重启 Solr,重启成功后刷新网页,点击 Documents,然后选择 XML,在Document(s) 文本域内输入:
<delete><id>33</id></delete>
然后点击按钮 Submit Document,删除 id=33 的数据,如图:
点击 Query -> Execute Query 查看,数据已删除。
然后再运行单元测试,执行 Execute Query 查看结果,如下,需要的字段已不包含中括号并且 item_image
字段没有返回查询结果,如图:
其中 item_content_str
和 author_str
等是复制域,在配置文件 managed-schema
的最后可以找到,它可以将某一个 Field 中的数据复制到另一个域中,比如将 item_content
中的数据复制到 item_content_str
中。
当两个域都有可能包含某个关键字,不知道查询的结果在哪个域中的时候,可以将这两个域中的内容复制到一个复制域中,从复制域中进行查找,我们将配置文件中的 item_title
和 item_content
都复制到 item_title_str
域中进行测试,配置如下:
<copyField source="item_title" dest="item_title_str" maxChars="256"/>
<copyField source="item_content" dest="item_title_str" maxChars="256"/>
重启 Solr,将测试类中的 id 改为34,然后运行单元测试,查看结果如下:
id=34 的 item_title_str
复制域中包含了 item_title
和 item_content
两个域中的内容。
接下来就是将 Solr 应用到项目中,通过 Solr 搜索并将结果高亮显示。
Solr 在项目中的应用
IKAnalyzer 分词器
Solr 可通过自带的分词器 smartcn 或者第三方分词器 IKAnalyzer 来实现,IKAnalyzer 分词效果较好,所以这里使用 IKAnalyzer 分词器。
使用 IKAnalyzer 分词器需要以下几个步骤:
1. 下载 IKAnalyzer 分词器 Jar 包,我已将 ikanalyzer-solr5.zip
文件放入了百度网盘中。
2. 压缩包解压后,将其中的两个 Jar 包放入 solr-7.3.1\server\solr-webapp\webapp\WEB-INF\lib
下。
3. 配置 solr-7.3.1\server\solr\mycore\conf
下的 managed-schema
文件,添加分词器和需要分词的字段。
<!-- 添加ik分词器 -->
<fieldType name="text_ik" class="solr.TextField">
<analyzer type="index" isMaxWordLength="false" class="org.wltea.analyzer.lucene.IKAnalyzer"/>
<analyzer type="query" isMaxWordLength="true" class="org.wltea.analyzer.lucene.IKAnalyzer"/>
</fieldType>
type="index"
代表创建索引时分词,type="query"
代表查询时分词。
<!-- 需要分词的字段 -->
<field name="title" type="text_ik" indexed="true" stored="true" required="true" multiValued="false" />
我们对文章标题进行分词查询。
4. 配置其它字段名和类型,否则会查询出集合类型的数据。
<field name="comment_num" type="string"/>
<field name="downvote" type="string"/>
<field name="upvote" type="string"/>
<field name="nick_name" type="string"/>
<field name="img_url" type="string"/>
<field name="rpt_time" type="pdate"/>
<field name="content" type="text_general"/>
<field name="category" type="string"/>
<field name="u_id" type="string"/>
<field name="personal" type="string"/>
注意:content 字段不能设置为 String 类型,否则内容过多会超出范围,报异常。除了日期和 content 字段外其它都设置为 String类型。
5. 重新启动 Solr。
代码如下:
solr restart -p 8983
6. 刷新网页,点击 Analysis,输入查询内容,选择分词字段,然后点击 Analyse Values 开始分词,查看结果,如下图:
其中:
- Field Value (Index):索引分词的值;
- Field Value (Query):查询分词的值。
在 web.xml 中引入 applicationContext-solr.xml
配置文件
代码如下:
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>
classpath:spring-mybatis.xml,
classpath:applicationContext-redis.xml,
classpath:applicationContext-activemq.xml,
classpath:applicationContext-solr.xml
</param-value>
</context-param>
创建 SolrService 接口
在 wang.dreamland.www.service 包下新建 SolrService 接口,接口方法如下:
public interface SolrService {
/**
* 根据关键字搜索文章并分页
* @param keyword
* @return
*/
Page<UserContent> findByKeyWords(String keyword, Integer pageNum, Integer pageSize);
}
提供根据关键字搜索文章并分页的接口方法。
创建 SolrServiceImpl 实现类
代码如下:
@Autowired
HttpSolrClient solrClient;
@Override
public Page<UserContent> findByKeyWords(String keyword, Integer pageNum, Integer pageSize) {
SolrQuery solrQuery = new SolrQuery( );
//设置查询条件
solrQuery.setQuery( "title:"+keyword );
//设置高亮
solrQuery.setHighlight( true );
solrQuery.addHighlightField( "title" );
solrQuery.setHighlightSimplePre( "<span style='color:red'>" );
solrQuery.setHighlightSimplePost( "</span>" );
//分页
if (pageNum == null || pageNum < 1) {
pageNum = 1;
}
if (pageSize == null || pageSize < 1) {
pageSize = 7;
}
solrQuery.setStart( (pageNum-1)*pageSize );
solrQuery.setRows( pageSize );
solrQuery.addSort("rpt_time", SolrQuery.ORDER.desc);
//开始查询
try {
QueryResponse response = solrClient.query( solrQuery );
//获得高亮数据集合
Map<String, Map<String, List<String>>> highlighting = response.getHighlighting();
//获得结果集
SolrDocumentList resultList = response.getResults();
//获得总数量
long totalNum = resultList.getNumFound();
List<UserContent> list = new ArrayList<UserContent>( );
for(SolrDocument solrDocument:resultList){
//创建文章对象
UserContent content = new UserContent();
//文章id
String id = (String) solrDocument.get( "id" );
Object content1 = solrDocument.get( "content" );
Object commentNum = solrDocument.get( "comment_num" );
Object downvote = solrDocument.get( "downvote" );
Object upvote = solrDocument.get( "upvote" );
Object nickName = solrDocument.get( "nick_name" );
Object imgUrl = solrDocument.get( "img_url" );
Object uid = solrDocument.get( "u_id" );
Object rpt_time = solrDocument.get( "rpt_time" );
Object category = solrDocument.get( "category" );
Object personal = solrDocument.get( "personal" );
//取得高亮数据集合中的文章标题
Map<String, List<String>> map = highlighting.get( id );
String title = map.get( "title" ).get( 0 );
content.setId( Long.parseLong( id ) );
content.setCommentNum( Integer.parseInt( commentNum.toString() ) );
content.setDownvote( Integer.parseInt( downvote.toString() ) );
content.setUpvote( Integer.parseInt( upvote.toString() ) );
content.setNickName( nickName.toString() );
content.setImgUrl( imgUrl.toString() );
content.setuId( Long.parseLong( uid.toString() ) );
content.setTitle( title );
content.setPersonal( personal.toString() );
Date date = (Date)rpt_time;
content.setRptTime(date);
List<String> clist = (ArrayList)content1;
content.setContent( clist.get(0).toString() );
content.setCategory( category.toString() );
list.add( content );
}
PageHelper.startPage(pageNum, pageSize);//开始分页
PageHelper.Page page = PageHelper.endPage();//分页结束
page.setResult(list);
page.setTotal(totalNum);
return page;
} catch (SolrServerException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
return null;
}
代码解读如下:
(1)@Service
注解代表这是 Service 层。
(2)通过 @Autowired
注解,注入 Solr 客户端对象 HttpSolrClient。
(3)新建 SolrQuery 对象,然后设置查询条件,title 为要查询的字段,keyword 为要查询的字段值。
(4)高亮显示必须设置 highlight 属性为 true。
(5)设置高亮的字段 tilte。
(6)设置高亮的标签头,可看出 style 的 color 属性值为 red,即红色高亮显示,也可自定义别的颜色。
(7)设置高亮的标签尾。
(8)分页,设置开始索引和每页显示记录数,按照时间倒序。
(9)Solr 客户端对象根据查询条件查询 Solr 索引库,将查询结果放入 QueryResponse 对象中。
(10)下面就是根据 QueryResponse 对象获取高亮结果集和所有数据结果集,然后遍历所有数据结果集,获取 Solr 索引库中的数据,将数据设置到文章对象中;然后遍历高亮结果集,主要是 title 属性,将 title 设置到文章对象中,每遍历一次将结果添加到 list 集合,这样 list 集合就包含了所有的查询结果。
(11)使用 PageHelper 分页工具开始分页,将 list 集合和总记录数等设置到 Page 中,最后将 page 对象返回。
(12)如果发生异常则返回 null。
这样 Service 层方法就写完了,等待 Controller 层的调用。
事件源
index.jsp 页面的搜索对应的 form 表单,如下:
<form method="post" action="${ctx}/index_list" id="indexSearchForm" class="navbar-form navbar-right" role="search" style="margin-top: -35px;margin-right: 10px">
<div class="form-group">
<input type="text" id="keyword" name="keyword" value="${keyword}" class="form-control" placeholder="搜索">
</div>
<i onclick="searchForm();" class="icon icon-search" style="color: white"></i>
</form>
action 对应的映射 URL 为:/index_list
,搜索对应的点击事件 searchForm 方法如下:
//搜索
function searchForm(){
var keyword = $("#keyword").val();
if(keyword!=null && keyword.trim()!=""){
$("#indexSearchForm").submit();
}
}
如果查询条件不为空,则提交表单。
在 IndexJspController 中修改映射 URL 为 index_list
的方法
修改如下:
@RequestMapping("/index_list")
public String findAllList(Model model, @RequestParam(value = "keyword",required = false) String keyword,
@RequestParam(value = "pageNum",required = false) Integer pageNum ,
@RequestParam(value = "pageSize",required = false) Integer pageSize) {
log.info( "===========进入index_list=========" );
User user = (User)getSession().getAttribute("user");
if(user!=null){
model.addAttribute( "user",user );
}
if(StringUtils.isNotBlank(keyword)){
Page<UserContent> page = solrService.findByKeyWords( keyword ,pageNum,pageSize);
model.addAttribute("keyword", keyword);
model.addAttribute("page", page);
}else {
Page<UserContent> page = findAll(pageNum,pageSize);
model.addAttribute( "page",page );
}
return "../index";
}
代码解读如下:
(1)从 Session 获取用户信息,如果不为 null 则添加到 model 中。
(2)如果关键字不为空则根据关键字进行 Solr 高亮搜索,并将返回结果 page 添加到 model 中,将关键字 keyword 也添加到 model 中,用于回显和分页查询条件。
(3)如果关键字为空则进行普通的分页查询,将 page 添加到 model 中。
(4)最后返回到 index.jsp 页面。
运行 Tomcat,输入查询条件后,发现什么都没有,跟我们预期的结果不一样?
这是因为 Solr 索引库中现在还没有数据,所以什么都没查到。我们需要在添加、修改和删除文章时将信息同步到 Solr 索引库中,数据发生变化,Solr 索引库要跟着变化,否则会出现数据不统一的现象。
同步信息到 Solr 索引库
1. 在 SolrService 接口中增加增、删、改方法,如下:
/**
* 添加文章到solr索引库中
* @param userContent
*/
void addUserContent(UserContent userContent);
/**
* 根据solr索引库
* @param userContent
*/
void updateUserContent(UserContent userContent);
/**
* 根据文章id删除索引库
* @param userContent
*/
void deleteById(Long id);
2. 在 SolrServiceImpl 中实现上述方法:
@Override
public void addUserContent(UserContent cont) {
if(cont!=null){
addDocument(cont);
}
}
@Override
public void updateUserContent(UserContent cont) {
if(cont!=null){
addDocument(cont);
}
}
@Override
public void deleteById(Long id) {
try {
solrClient.deleteById(id.toString());
solrClient.commit();
} catch (SolrServerException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
public void addDocument(UserContent cont){
try {
SolrInputDocument inputDocument = new SolrInputDocument();
inputDocument.addField( "comment_num", cont.getCommentNum() );
inputDocument.addField( "downvote", cont.getDownvote() );
inputDocument.addField( "upvote", cont.getUpvote() );
inputDocument.addField( "nick_name", cont.getNickName());
inputDocument.addField( "img_url", cont.getImgUrl() );
inputDocument.addField( "rpt_time", cont.getRptTime() );
inputDocument.addField( "content", cont.getContent() );
inputDocument.addField( "category", cont.getCategory());
inputDocument.addField( "title", cont.getTitle() );
inputDocument.addField( "u_id", cont.getuId() );
inputDocument.addField( "id", cont.getId());
inputDocument.addField( "personal", cont.getPersonal());
solrClient.add( inputDocument );
solrClient.commit();
} catch (SolrServerException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
主要是通过 Solr 客户端对象 SolrCient 操作 Solr,这里的添加和更新方法一样,id 存在时就是根据 id 更新字段。还有就是别忘了 commit 提交。
3. 在 WriteController 中更新如下:
if(cid ==null){
userContent.setUpvote( 0 );
userContent.setDownvote( 0 );
userContent.setCommentNum( 0 );
userContentService.addContent( userContent );
solrService.addUserContent(userContent);
}else {
userContentService.updateById(userContent);
solrService.updateUserContent(userContent);
}
在添加和更新文章之后分别同步 Solr 索引库信息。注意记得注入 SolrService 对象。
4. 在 PersonalController 中更新如下:
userContentService.deleteById(cid);
solrService.deleteById(cid);
在删除文章的时候删除索引库对应的信息。注意记得注入 SolrService 对象。
首页关键词搜索高亮显示
现在 Solr 索引库没有数据,我们直接在单元测试中把所有文章都查询出来,然后批量添加到 Solr 索引库中。
在单元测试类 TestSolrJ 中新建方法 testSaveAll,并将所需要的配置文件都进行加载:
@ContextConfiguration(locations = {"classpath:applicationContext-redis.xml","classpath:spring-mybatis.xml","classpath:applicationContext-activemq.xml","classpath:applicationContext-solr.xml"})
具体方法如下:
@Autowired
private UserContentService userContentService;
@Test
public void testSaveAll() throws IOException, SolrServerException {
List<UserContent> list = userContentService.findAll();
if(list!=null && list.size()>0){
for (UserContent cont : list){
SolrInputDocument inputDocument = new SolrInputDocument();
inputDocument.addField( "comment_num", cont.getCommentNum() );
inputDocument.addField( "downvote", cont.getDownvote() );
inputDocument.addField( "upvote", cont.getUpvote() );
inputDocument.addField( "nick_name", cont.getNickName());
inputDocument.addField( "img_url", cont.getImgUrl() );
inputDocument.addField( "rpt_time", cont.getRptTime() );
inputDocument.addField( "content", cont.getContent() );
inputDocument.addField( "category", cont.getCategory());
inputDocument.addField( "title", cont.getTitle() );
inputDocument.addField( "u_id", cont.getuId() );
inputDocument.addField( "id", cont.getId());
inputDocument.addField( "personal", cont.getPersonal());
solrServer.add( inputDocument );
}
}
solrServer.commit();
}
上面代码将所有文章查询出来之后进行遍历,然后将每篇文章的信息都添加到文档对象中,然后通过 Solr 客户端对象将其添加到 Solr 索引库中,最后提交。
现在 Solr 索引库中已经有数据了,重新启动 Tomcat,然后输入查询条件进行搜索,比如搜索“Solr 高亮显示功能”,查询结果如下图:
先对搜索条件进行分词,然后根据分词后的结果进行查询并将结果高亮显示。
最后,如果查询结果不止一页,想要点击下一页或者指定页码后还能高亮显示,则要将查询条件带上,如下:
<div id="page-info" style="position: absolute;width:900px;background-color: #EBEBEB;height: 80px;left: 0px;">
<ul class="pager pager-loose">
<c:if test="${page.pageNum <= 1}">
<li><a href="void(0);">« 上一页</a></li>
</c:if>
<c:if test="${page.pageNum > 1}">
<li class="previous"><a href="${ctx}/index_list?pageNum=${page.pageNum-1}&&keyword=${keyword}">« 上一页</a></li>
</c:if>
<c:forEach begin="${page.startPage}" end="${page.endPage}" var="pn">
<c:if test="${page.pageNum==pn}">
<li class="active"><a href="void(0);">${pn}</a></li>
</c:if>
<c:if test="${page.pageNum!=pn}">
<li ><a href="${ctx}/index_list?pageNum=${pn}&&keyword=${keyword}">${pn}</a></li>
</c:if>
</c:forEach>
<c:if test="${page.pageNum>=page.pages}">
<li><a href="void(0);">下一页 »</a></li>
</c:if>
<c:if test="${page.pageNum<page.pages}">
<li><a href="${ctx}/index_list?pageNum=${page.pageNum+1}&&keyword=${keyword}">下一页 »</a></li>
</c:if>
</ul>
</div>
在请求 URL 上拼接 keyword:
href="${ctx}/index_list?pageNum=${page.pageNum-1}&&keyword=${keyword}"
Tomcat 服务器运行 Solr
上面的 Solr 是在 Jetty 服务器下运行的,下面介绍 Solr 如何在 Tomcat 服务器上运行。
准备
1. 将 solr-7.3.1\server\solr-webapp
下的 webapp 文件复制到 Tomcat 的 webapps 目录下,并重命名为 Solr,如下图:
2. 将 solr-7.3.1\server\lib\ext
目录下的所有 Jar 包复制到刚才重命名的 solr\WEB-INF\lib
下。
3. 将 solr-7.3.1\server\lib
下以 metrics 开头的5个 Jar 包也复制到刚才重命名的 solr\WEB-INF\lib
下。
4. 在刚才重命名的 solr\WEB-INF
下新建 classes 文件夹,并将 solr-7.3.1\server\resources
下的 log4j.properties 文件复制到刚刚新建的 classes 文件夹下。
5. 将 solr-7.3.1\server
目录下的 Solr 文件夹复制到自定义路径下,我这里直接放在了 D:/
下,然后重命名为 solr_home
。
6. 修改之前重命名的 solr\WEB-INF
下的 web.xml
文件。
找到如下图的注释,将其解开,并将路径替换成自己刚才重命名的 solr_home
的路径,如下
<env-entry>
<env-entry-name>solr/home</env-entry-name>
<env-entry-value>D:/solr_home</env-entry-value>
<env-entry-type>java.lang.String</env-entry-type>
</env-entry>
然后将最下面的 security-constraint
标签内的内容注释掉,如下图:
启动 Tomcat
先介绍下 Tomcat 下的 ROOT 文件夹和 Solr 文件夹。
以 ROOT 命名的文件夹,Tomcat 启动后可以通过 localhost:8080
直接访问项目,不用加项目名。
而其他要部署的项目如果不是以 ROOT 命名,比如 Solr,访问的时候需要通过 localhost:8080/solr
的方式访问,即需要加上项目名。
接下来把我们的 dreamland-web
项目打 War包,我是直接用 Maven 命令 install 并跳过测试,如下图:
如果出现 BUILD SUCCESS 即代表成功,然后在 dreamland\dreamland-web\target
目录下可以找到 dreamland-web.war
文件,这就是我们刚刚打包好的 War 包。
紧接着,我们将 dreamland-web.war
复制到 Tomcat 的 webapps 目录下,并重命名为 ROOT.war,将原来的 ROOT 文件夹删除,启动 Tomcat 后,会自动将 ROOT.war 文件解压。
启动Tomcat之前,需先启动 Redis 和 ActiveMQ,然后进入 Tomcat 安装目录下的 bin 目录,我的是:D:\softs\java\apache-tomcat-8.5.9\bin
,双击 startup.bat 文件启动 Tomcat,此时就可以通过下面链接访问 Solr 网页了:
http://localhost:8080/solr/index.html#/
访问我们自己的 Web 项目就是:http://localhost:8080,如果想通过 Solr 高亮搜索,则要将 applicationContext-solr.xml
中的端口修改成8080,然后重新打包部署。
<constructor-arg name="builder" value="http://localhost:8080/solr/mycore"/>
第14课百度网盘地址:
链接:https://pan.baidu.com/s/18rDZpLx-3x-4iOSoyEqxqw 密码:y192
本文来自博客园,作者:暗影月色程序猿,转载请注明原文链接:https://www.cnblogs.com/Geneling/p/15249202.html