前言:上面我们已经搭建好了Solr服务器,现在我们要利用这个Solr服务来搭建我们的搜素服务工程
1.创建搜索服务工程
可以参考taotao-manager创建
https://www.jianshu.com/p/4f7893163c7f
创建完了记得改一下Tomcat插件的端口号
Taotao-search(聚合工程pom)
- taotao-search-interface(jar)
-
taotao-search-Service(war)
image.png
2.使用SolrJ管理索引库
我们如何在java代码中管理我们的索引库呢。一般我们用SolrJ,使用SolrJ可以实现索引库的增删改查的操作
下面介绍基本的SolrJ的操作
2.1添加文档
第一步:把solrJ的jar包添加到工程中。
<!-- solr客户端 -->
<dependency>
<groupId>org.apache.solr</groupId>
<artifactId>solr-solrj</artifactId>
</dependency>
第二步:创建一个SolrServer,使用HttpSolrServer创建对象。
第三步:创建一个文档对象SolrInputDocument对象。
第四步:向文档中添加域。必须有id域,域的名称必须在schema.xml中定义。
第五步:把文档添加到索引库中。
第六步:提交。
@Test
public void TestAddSolr() throws IOException, SolrServerException {
//创建一个SolrServer对象;SolrServer是一个接口,单机版的话用他的实现类HttpSolrServer
//指定对应的URL
SolrServer solrServer = new HttpSolrServer("http://192.168.208.40:8080/solr/collection1");
//创建一个文档对象SolrInputDocument
SolrInputDocument solrInputFields = new SolrInputDocument();
//向文档对象中添加域的名称前提:必须在schema.xml中定义
solrInputFields.addField("id","123");
solrInputFields.addField("item_title","测试商品1");
//把文档对象写入索引库
solrServer.add(solrInputFields);
//提交
solrServer.commit();
}
solr单机版测试.png
.2.2删除文档
第一步:创建一个SolrServer对象。
第二步:调用SolrServer对象的根据id删除的方法。
第三步:提交。
@Test
public void deleteDocumentById() throws Exception {
// 第一步:创建一个SolrServer对象。
SolrServer solrServer = new HttpSolrServer("http://192.168.208.40:8080/solr");
// 第二步:调用SolrServer对象的根据id删除的方法。
solrServer.deleteById("1");
// 第三步:提交。
solrServer.commit();
}
根据查询删除
@Test
public void deleteDocumentByQuery() throws Exception {
SolrServer solrServer = new HttpSolrServer("http://192.168.208.40:8080/solr");
solrServer.deleteByQuery("title:change.me");
solrServer.commit();
}
2.3查询索引库
查询步骤:
第一步:创建一个SolrServer对象
第二步:创建一个SolrQuery对象。
第三步:向SolrQuery中添加查询条件、过滤条件。。。
第四步:执行查询。得到一个Response对象。
第五步:取查询结果。
第六步:遍历结果并打印
简单的查询
@Test
public void queryDocument() throws Exception {
// 第一步:创建一个SolrServer对象
SolrServer solrServer = new HttpSolrServer("http://192.168.25.154:8080/solr");
// 第二步:创建一个SolrQuery对象。
SolrQuery query = new SolrQuery();
// 第三步:向SolrQuery中添加查询条件、过滤条件。。。
query.setQuery("*:*");
// 第四步:执行查询。得到一个Response对象。
QueryResponse response = solrServer.query(query);
// 第五步:取查询结果。
SolrDocumentList solrDocumentList = response.getResults();
System.out.println("查询结果的总记录数:" + solrDocumentList.getNumFound());
// 第六步:遍历结果并打印。
for (SolrDocument solrDocument : solrDocumentList) {
System.out.println(solrDocument.get("id"));
System.out.println(solrDocument.get("item_title"));
System.out.println(solrDocument.get("item_price"));
}
}
带高亮
@Test
public void queryDocumentWithHighLighting() throws Exception {
// 第一步:创建一个SolrServer对象
SolrServer solrServer = new HttpSolrServer("http://192.168.25.154:8080/solr");
// 第二步:创建一个SolrQuery对象。
SolrQuery query = new SolrQuery();
// 第三步:向SolrQuery中添加查询条件、过滤条件。。。
query.setQuery("测试");
//指定默认搜索域
query.set("df", "item_keywords");
//开启高亮显示
query.setHighlight(true);
//高亮显示的域
query.addHighlightField("item_title");
query.setHighlightSimplePre("<em>");
query.setHighlightSimplePost("</em>");
// 第四步:执行查询。得到一个Response对象。
QueryResponse response = solrServer.query(query);
// 第五步:取查询结果。
SolrDocumentList solrDocumentList = response.getResults();
System.out.println("查询结果的总记录数:" + solrDocumentList.getNumFound());
// 第六步:遍历结果并打印。
for (SolrDocument solrDocument : solrDocumentList) {
System.out.println(solrDocument.get("id"));
//取高亮显示
Map<String, Map<String, List<String>>> highlighting = response.getHighlighting();
List<String> list = highlighting.get(solrDocument.get("id")).get("item_title");
String itemTitle = null;
if (list != null && list.size() > 0) {
itemTitle = list.get(0);
} else {
itemTitle = (String) solrDocument.get("item_title");
}
System.out.println(itemTitle);
System.out.println(solrDocument.get("item_price"));
}
}
QQ图片20180707095427.png
3.在工程中使用SolrJ
我们可以看到我们设置的域需要7个字段,在这里我们最好用个类来封装这些数据
public class SearchItem implements Serializable{
private String id;
private String title;
private String sell_point;
private String image;
private long price;
private String category_name;
private String item_desc;
//对应的get,set方法
}
在这里要解释一下为什么我们设的id是String类型的,因为我们在设置schema.xml的时候id的属性为String,数据库中的为long。为了避免long和String转换带来的问题,我直接使用String类型来表示。
Dao层
我们可以发现我们所需要的数据域已经不是简单的单表查询了,这个时候就要我们自己创建一个新的Mapper接口和xml,如下:
接口定义:
public interface SearchItemMapper {
List<SearchItem> getItemList();
SearchItem getItemById(Long itemId);
}
Mapper映射文件:
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.taotao.search.mapper.SearchItemMapper">
<select id="getItemList" resultType="com.taotao.common.pojo.SearchItem">
SELECT
a.id,
a.title,
a.sell_point,
a.price,
a.image,
b. NAME category_name,
c.item_desc
FROM
tb_item a
LEFT JOIN tb_item_cat b ON a.cid = b.id
LEFT JOIN tb_item_desc c ON a.id = c.item_id
WHERE
a.`status` = 1
</select>
</mapper>
service层
参数:无
业务逻辑:taotao-search中实现
1、查询所有商品数据。
2、创建一个SolrServer对象。
3、为每个商品创建一个SolrInputDocument对象。
4、为文档添加域
5、向索引库中添加文档。
6、返回TaotaoResult。
在applicationContext-solr.xml中配置SolrServer对象。
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:context="http://www.springframework.org/schema/context" xmlns:p="http://www.springframework.org/schema/p"
xmlns:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx"
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-4.2.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.2.xsd
http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-4.2.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-4.2.xsd
http://www.springframework.org/schema/util http://www.springframework.org/schema/util/spring-util-4.2.xsd">
<!-- 单机版solr的连接 -->
<bean id="httpSolrServer" class="org.apache.solr.client.solrj.impl.HttpSolrServer">
<constructor-arg name="baseURL" value="http://192.168.208.40:8080/solr/collection1"/>
</bean>
@Service
public class SearchItemServiceImpl implements SearchItemService {
@Autowired
private SearchItemMapper searchItemMapper;
@Autowired
private SolrServer solrServer;
@Override
public TaotaoResult importAllItems() throws Exception{
// 1、查询所有商品数据。
List<SearchItem> itemList = searchItemMapper.getItemList();
// 2、创建一个SolrServer对象。
// 3、为每个商品创建一个SolrInputDocument对象。
for (SearchItem searchItem : itemList) {
SolrInputDocument document = new SolrInputDocument();
// 4、为文档添加域
document.addField("id", searchItem.getId());
document.addField("item_title", searchItem.getTitle());
document.addField("item_sell_point", searchItem.getSell_point());
document.addField("item_price", searchItem.getPrice());
document.addField("item_image", searchItem.getImage());
document.addField("item_category_name", searchItem.getCategory_name());
document.addField("item_desc", searchItem.getItem_desc());
// 5、向索引库中添加文档。
solrServer.add(document);
}
//提交修改
solrServer.commit();
// 6、返回TaotaoResult。
return TaotaoResult.ok();
}
}
发布服务
接收服务
我们是taoato-manager-web中调用服务的,因此我们在这个工程中配置接收的服务
image.png
同时记得在pom.xml中加入依赖
image.png
Controller
我们知道我们前台是没有导入索引库这个功能的,这就需要我们写一管理界面
在taotao-manager-web中的index.jsp中添加
新增一个jsp
image.png
然后写业务代码
@Controller
public class SearchItemController {
@SuppressWarnings("SpringJavaInjectionPointsAutowiringInspection")
@Autowired
private SearchItemService searchItemService;
@RequestMapping("/index/import")
@ResponseBody
public TaotaoResult importSearchItem() {
try {
return searchItemService.addSerchItem();
} catch (Exception e) {
e.printStackTrace();
return TaotaoResult.build(500,"导入数据失败");
}
}
}
同时我们要在taotao-search-service的pom文件中添加以下配置语句。因为默认情况下mybatis所对应的mapper.xml文件是不被加载的,这个问题我们以前遇到过。
taotao-search-service工程的pom文件中添加如下配置:
<!-- 如果不添加此节点mybatis的mapper.xml文件都会被漏掉。 -->
<build>
<resources>
<resource>
<directory>src/main/java</directory>
<includes>
<include>**/*.properties</include>
<include>**/*.xml</include>
</includes>
<filtering>false</filtering>
</resource>
<!-- 如果没有此节点,src/main/resources目录下的配置文件将被忽略 -->
<resource>
<directory>src/main/resources</directory>
<includes>
<include>**/*.properties</include>
<include>**/*.xml</include>
</includes>
<filtering>false</filtering>
</resource>
</resources>
</build>
启动服务
PS:记得启动
QQ图片20180707085209.png
在管理界面点击Query——>Execute Query,可以看到上面截图的结果就说明成功了!
网友评论