[if !supportLists]1. [endif]综合案例
[if !supportLists]1.1. [endif]需求
使用Solr实现电商网站中商品信息搜索功能,可以根据关键字、分类、价格搜索商品信息,也可以根据价格进行排序,并且实现分页功能。
界面如下:
[if !vml]
[endif]
[if !supportLists]1.2. [endif]分析
开发人员需要的文档:静态页面(根据UI设计由美工给出)、数据库设计、原型设计
[if !supportLists]1.2.1. [endif]UI分析
[if !vml]
[endif]
[if !supportLists]1.2.2. [endif]架构分析
[if !vml]
[endif]
架构分为:
(1)、solr服务器。(已经做完,同入门示例)
(2)、自己开发的应用(重点)
(3)、数据库mysql
自己开发的应用
Controller 负责和前端页面进行请求和响应的交互
Service 封装查询条件,调用dao。
Dao 搜索索引库,返回搜索结果。
[if !supportLists]1.3. [endif]环境准备
Solr:4.10.3
Jdk环境:1.7.0_72(solr4.10 不能使用jdk1.7以下)
Ide环境:Eclipse
Web服务器(servlet容器):Tomcat 7+
[if !supportLists]1.4. [endif]代码实现
[if !supportLists]1.4.1. [endif]实现步骤
第一部分:SpringMVC框架搭建
第二部分:整合Spring与Solr (Solr服务已经搭建好了)
第三部分:实现功能
[if !supportLists]1.4.2. [endif]实现步骤
[if !supportLists]1.4.2.1. [endif]第一部分:SpringMVC框架搭建
[if !supportLists]1.4.2.1.1. [endif]第一步:导入SpringMVC依赖包
--新建一个动态网站项目导入SpringMVC的Jar包
[if !vml]
[endif]
[if !supportLists]1.4.2.1.2. [endif]第二步:创建一个请求页面
<%@pagelanguage="java"contentType="text/html;
charset=UTF-8"
pageEncoding="UTF-8"%>
"${pageContext.request.contextPath }/say">say hello
[if !supportLists]1.4.2.1.3. [endif]第三步:web.xml配置(入口)
"1.0"encoding="UTF-8"?>
xmlns="http://xmlns.jcp.org/xml/ns/javaee"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee
http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd"
id="WebApp_ID"version="3.1">
[if !supportLists]1.4.2.1.4. [endif]第四步:配置Spring配置文件
--mvc配置文件,spring-mvc.xml
"1.0"encoding="UTF-8"?>
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:mvc="http://www.springframework.org/schema/mvc"
xsi:schemaLocation="http://www.springframework.org/schema/mvc
http://www.springframework.org/schema/mvc/spring-mvc-4.3.xsd
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">
--context配置文件,spring-context.xml
"1.0"encoding="UTF-8"?>
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.3.xsd">
[if !supportLists]1.4.2.1.5. [endif]第五步:配置业务控制器
package org.chu.controller;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
@Controller
public class PageController {
@RequestMapping(value="/{page}")
public String showPage(@PathVariable String page) {
System.out.println("-HelloWorld:"+page);
return page;
}
}
[if !supportLists]1.4.2.1.6. [endif]第六步:配置返回页面
--返回页面为:/say.jsp
<%@pagelanguage="java"contentType="text/html;
charset=UTF-8"
pageEncoding="UTF-8"%>
你好世界
[if !supportLists]1.4.2.2. [endif]第二部分:整合Spring与Solr
注意事项:
必须要将Solr的Tomcat服务器的端口配置与项目运行的Tomcat的端口不一样。因为如果在同一个电脑上同时运行两个Tomcat,端口不修改就会冲突。
[if !supportLists]1.4.2.2.1. [endif]第一步:修改Solr服务器端口
前提:Solr服务器已经准备好。
--Tomcat的conf/server.xml文件中,修改端口
--tomcat端口说明:
8005:关机端口,修改为:8006
8080:默认服务端口,修改为:8888
8009:请求转向端口,修改为:8010
[if !supportLists]1.4.2.2.2. [endif]第二步:导入Solr的连接依赖包
--将以下的jar 加入到项目的WEB-INF/lib里面。
--日志处理包
[if !vml]
[endif]
--solrj依赖包
[if !vml]
[endif]
[if !supportLists]1.4.2.2.3. [endif]第三步:加入Log4j的支持
在classpath根目录加入lo4j.properties。该文件可以在solr的包里面找到
[if !vml]
[endif]
[if !supportLists]1.4.2.2.4. [endif]第四步:在spring-context.xml配置Solr
[if !supportLists]1.4.2.3. [endif]第三部分:功能实现
[if !supportLists]1.4.2.3.1. [endif]第一步:导入页面资源
前提:准备资料
[if !vml]
[endif]
--将准备的资料放在webapp,网站根目录。并且删除原来测试的页面,test.jsp以及say.jsp。
结果如下:
[if !vml]
[endif]
[if !supportLists]1.4.2.3.2. [endif]第二步:导入JSTL的支持
--我们发现页面报错。
[if !vml]
[endif]
--加入jstl的依赖包
[if !vml]
[endif]
[if !supportLists]1.4.2.3.3. [endif]第三步:编写JavaBean
--编写Product实体类
package org.chu.pojo;
public class Product {
// 商品编号
private String pid;
// 商品名称
private String name;
// 商品分类名称
private String catalogName;
// 价格
private double price;
// 商品描述
private String description;
// 图片名称
private String picture;
//补全get、set方法
}
--业务模型(Value Object VO),编写ResultModel业务模型
package org.chu.pojo;
import java.util.List;
public class ResultModel {
private List
// 商品总数
private Long recordCount;
// 总页数
private int pageCount;
// 当前页
private int currentPage;
//补全get、set方法
}
[if !supportLists]1.4.2.3.4. [endif]第四步:获得Solr的数据
package org.chu.dao.impl;
import java.util.ArrayList;
import java.util.List;
import org.apache.solr.client.solrj.SolrQuery;
import org.apache.solr.client.solrj.impl.HttpSolrServer;
import org.apache.solr.client.solrj.response.QueryResponse;
import org.apache.solr.common.SolrDocument;
import org.apache.solr.common.SolrDocumentList;
import org.chu.dao.ProductDAO;
import org.chu.pojo.Product;
import org.chu.pojo.ResultModel;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;
@Repository
public class ProductDAOImpl implements ProductDAO{
@Autowired
private HttpSolrServer solrServer;
@Override
public ResultModel queryProduct(SolrQuery query) throws Exception {
//创建一个返回的业务模型对象
ResultModelresultModel=new ResultModel();
//第一步:获得Solr响应对象
QueryResponseresponse = solrServer.query(query);
//第二步:获得返回的结果集
SolrDocumentListresults = response.getResults();
//第三步:将SolrDocumentList集合对象转成List
Listproducts=newArrayList<>();
//设置高亮信息
Map>> highlighting = response.getHighlighting();
for (SolrDocument solrDocument : results) {
Productproduct=new Product();
product.setPid((String)solrDocument.get("id"));
// 设置高亮信息
List list = highlighting.get(solrDocument.get("id")).get("product_name");
String prodName = (String) solrDocument.get("product_name");
if (list != null)prodName = list.get(0);
product.setName(prodName);
product.setCatalogName((String)
solrDocument.get("product_catalog_name"));
product.setPicture((String)
solrDocument.get("product_picture"));
product.setDescription((String)
solrDocument.get("product_description"));
product.setPrice((Double)
solrDocument.get("product_price"));
products.add(product);
}
//第四步:将数据封装到ResultModel
//总记录书
resultModel.setRecordCount(results.getNumFound());
//查询的的结果
resultModel.setProductList(products);
return resultModel;
}
}
[if !supportLists]1.4.2.3.5. [endif]第五步:构造Service
package org.chu.service.impl;
import org.apache.solr.client.solrj.SolrQuery;
import org.apache.solr.client.solrj.SolrQuery.ORDER;
import org.chu.dao.ProductDAO;
import org.chu.pojo.ResultModel;
import org.chu.service.ProductService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
@Service
public class ProductServiceImpl implements ProductService {
@Autowired
private ProductDAO productDAO;
@Override
public ResultModel queryProduct(String queryString,
String cataName, String price, String sort, Integer curPage)
throws Exception {
//构建查询的条件
SolrQueryquery=new SolrQuery();
//判断关键字不为空
if (queryString!=null&&!"".equals(queryString)) {
query.set("q", queryString);
}else {
query.set("q", "*:*");
}
//增加过滤条件
if (cataName!=null&&!"".equals(cataName)) {
query.addFilterQuery("product_catalog_name:"+cataName);
}
//价格过滤
if (price!=null&&!"".equals(price)) {
String[]prices = price.split("-");
query.addFilterQuery("product_price:[ "+prices[0]+"
TO "+prices[1]+" ]");
}
//排序,1:desc ,非1就,asc
if (sort!=null&&sort.equals("1")) {
query.setSort("product_price", ORDER.desc);
}else{
query.setSort("product_price", ORDER.asc);
}
//设置分页
//如果没有值,就为第一页
if (curPage==null) {
curPage=1;
}
//设置查询的开始位置
query.setStart((curPage-1)*20);
//设置每页记录数
query.setRows(20);
query.set("df", "product_name");
//高亮分词设置
query.setHighlight(true);
//设置高亮的字段
query.addHighlightField("product_name");
//通过标签设置颜色
//开始标签
query.setHighlightSimplePre("
style=\"color:red\">"); query.setHighlightSimplePost("
ResultModelresultModel = productDAO.queryProduct(query);
//返回结果后,封装请求的数据到业务模型里面
resultModel.setCurrentPage(curPage);
// 总页数 = 总数量 / 每页数据条数 结果向上取整
double ceil= Math.ceil(resultModel.getRecordCount().doubleValue()/20);
resultModel.setPageCount((int)ceil);
return resultModel;
}
}
[if !supportLists]1.4.2.3.6. [endif]第六步:构建Controller
package org.chu.controller;
import org.chu.pojo.ResultModel;
import org.chu.service.ProductService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
@Controller
public class ProductController {
@Autowired
private ProductService productService;
@RequestMapping(value="/list")
public String list(String queryString, @RequestParam("catalog_name") String catalogName,String price, String sort, Integer curPage, ModelMap model) {
try {
ResultModelresultModel = productService.queryProduct(queryString, catalogName, price, sort, curPage);
model.addAttribute("result", resultModel);
model.addAttribute("queryString", queryString);
model.addAttribute("catalog_name", catalogName);
model.addAttribute("price", price);
model.addAttribute("sort", sort);
model.addAttribute("page", curPage);
}catch (Exception e) {
e.printStackTrace();
}
return "product_list";
}
}
[if !supportLists]1.4.2.3.7. [endif]第七部:测试
[if !vml]
[endif]