Solr基础

单纯的对已有数据进行搜索时,Solr更快。

建立索引时,搜索效率下降,实时索引搜索效率不高。Solr的架构不适合实时搜索的应用

 

1.solr目录结构

- bin:该目录下存放了Solr的工具命令。
   - contrib:该目录下存放了Solr所依赖的第三方JAR包
   - dist:该目录下存放了Solr本身的JAR包。
           其中solrj-lib的JAR包是Java客户端需要的JAR包。
           SolrJ、SolrPHP、SolrC、SolrXxx……
   - docs:该目录下存放了Solr的文档。
   - example:该目录下存放了Solr的各种示例。
             其中exampledocs和films目录下存放了Solr的示例文档。
   - server:Solr自带的Web应用。            
            server\lib的JAR包其实就是Jetty服务器+Servlet规范包。
            保证Solr可以在不需要部署到任何Web服务器时即可运行(其实是用Jetty作为服务器)
   - solr-webapp:该目录下存放了Solr的Web应用——该应用可拿来部署

 

2. 配置在tomcat

https://blog.csdn.net/qq_40580023/article/details/83866303
初始化solr_home的数据,在solr_home文件下建一个core1(名字随意取),复制solr_home/configsets/_default/下的conf文件夹,到新建的core1下,在core1下创建文件夹data(空文件加即可)和core.properties文件(内容只配置name=core1即可,这里的name的值也就是再页面要显示的solr_home名称)

 

3. 后台界面介绍

启动tomcat访问solr'后台

http://192.168.233.133:8983/solr/index.html#/new_core/query

https://blog.csdn.net/qq1031893936/article/details/80229757

官网停止了ik分词器的更新,这个版本可以兼容7.x的solr

 

4. 配置中文分词器

将IK分词器的jar包放在tomcat下solr应用下的lib文件夹下,比如:

solr7/solr-tomcat/webapps/solr/WEB-INF/lib,然后找到managed-schema

vim solr7/solr_home/new_core/managed-schema
# 末尾添加
<fieldType name="text_ik" class="solr.TextField">
     <analyzer class="org.wltea.analyzer.lucene.IKAnalyzer"/>
</fieldType>
# 配置查询类型
# Indexed=true   就是可以查询 
# Stored=true    就是内容存储 
<field name="item_title" type="text_ik" indexed="true" stored="true"/>
<field name="item_sell_point" type="text_ik" indexed="true" stored="true"/>
<field name="item_price"  type="plong" indexed="true" stored="true"/>

启动solr测试,可以看到设置的查询类型

 

5. 获取数据

这里以数据库5.x版本为例,8.x需更改配置,linux连接windows需要windows的ip地址,并使用户支持远程连接,详情百度全都有。

1、 引入jar依赖:
          -1 在apache-tomcat-8.5.23/webapps/solr/WEB-INF/lib/引入mysql的驱 动(mysql-connector-java-5.1.32.jar);          
          -2 复制solr-7.3.0/dist/的solr-dataimporthandler-7.3.0.jar和solr-dataimporthandler-extras-7.3.0.jar,
              到apache-tomcat-8.5.23/webapps/solr/WEB-INF/lib/的下面
2、 复制solr-7.3.0/example/example-DIH/solr/db/conf/下的db-data-config.xml到solr_home/core1/conf/下,
           此处改名为data-config.xml(可以不改名)。修改内容的结果为:

<dataConfig>
	  <dataSource type="JdbcDataSource" 
	                                      driver="com.mysql.jdbc.Driver"
	                                      url="jdbc:mysql://127.0.0.1:3306/shopping" 
	                                      user="root" 
	                                      password="123"/>
	  <document>
		      <entity name="ec_article" 
		                   query="select id,title,price,locality,create_date from ec_article">
	              </entity>
          </document>
</dataConfig>

3、修改solrconfig文件,添加导入信息。该信息必须放在requestHandler标签的同级位置。

<requestHandler name="/dataimport" class="org.apache.solr.handler.dataimport.DataImportHandler">
        <lst name="defaults">
          <str name="config">data-config.xml</str>
        </lst>
</requestHandler>

4、自定义solr的字段,在managed-schema文件中添加filed字段。(位置放在 text 字段后面即可)

<field name="title" type="text_ik" indexed="true" stored="true" multiValued="false"/>
<field name="content" type="string" indexed="false" stored="true" multiValued="false"/>
<field name="create_user_name" type="string" indexed="true" stored="true" multiValued="false"/>
<field name="create_time" type="pdate" indexed="true" stored="true" multiValued="false"/> 

5、添加IK分词器,引入IK分词器的依赖到apache-tomcat-8.5.23/webapps/solr/WEB-INF/lib/下,配置IK分词器(注意:放在fieldType同级附近)。

<fieldType name="text_ik" class="solr.TextField">
    <analyzer class="org.wltea.analyzer.lucene.IKAnalyzer"/>
</fieldType>

启动solr,以下为运行成功后界面:

 

6. 数据操作

来到Documents页面

# 新增数据
{id:0,title:"高露洁"}
# 修改数据
{id:0,title:"牙牙乐"}
# 删除,格式选为xml
<delete>
  <query>id:0</query>
</delete>
<commit/>

Query查询页面

默认查询locality为深圳的id和title

过滤价格3000以下商品并升序排序

 查询locality like `美国`并将locality为`美国`的标红

 

7.solrj实现

利用java代码实现增删查改

commons-io-2.5.jar
commons-math3-3.6.1.jar
httpclient-4.5.3.jar
httpcore-4.4.6.jar
httpmime-4.5.3.jar
jcl-over-slf4j-1.7.24.jar
noggit-0.8.jar
slf4j-api-1.7.24.jar
solr-solrj-7.5.0.jar
stax2-api-3.1.4.jar
woodstox-core-asl-4.4.1.jar
zookeeper-3.4.11.jar
public class Solrj_index_crud {
	public static void main(String[] args) throws SolrServerException, IOException {
		// 添加或更新索引 根据id值来进行添加或更新
		// addOrUpdate();

		// 通过solr进行索引的删除
		// delete();

		// 通过solrj进行全文检索
		search();
	}

	private static void search() throws SolrServerException, IOException {

		HttpSolrClient client = new HttpSolrClient.Builder("http://192.168.233.133:8983/solr/test_core")
				.withConnectionTimeout(10000).build();
		// 创建solrjquery实例,通过这个对象可以设置查询的关键字 设置fl dl 高亮信息 分页等等
		SolrQuery solrQuery = new SolrQuery();
		// 设置查询关键字
		solrQuery.setQuery("中国");
		// 设置查询属性
		solrQuery.set("df", "locality");
		// 过滤条件,设置要显示的属性
		solrQuery.set("fl", "id,title,price,locality,create_date");
		// 设置分页
		// solrQuery.setStart(0);
		// solrQuery.setRows(2);
		// 设置过滤条件
		solrQuery.set("fq", "price:[3000 TO *]");
		// 设置高亮
		solrQuery.setHighlight(true);
		// 制定高亮的字段
		solrQuery.addHighlightField("locality");
		// 设置高亮相关格式
		solrQuery.setHighlightSimplePre("<font color='red'>");
		solrQuery.setHighlightSimplePost("</font>");
		// 将solrQuery传入client进行查询
		QueryResponse queryResponse = client.query(solrQuery);
		// 获取普通结果集
		SolrDocumentList solrDocumentList = queryResponse.getResults();
		// 获取高亮后的结果集
		Map<String, Map<String, List<String>>> highlighting = queryResponse.getHighlighting();
		/*
		 * key:存放记录的id value:文档信息 key:字段(id,title,price) value:字段对应的值
		 */

		// 获取得分最高的记录分数
		Float float1 = solrDocumentList.getMaxScore();
		System.out.println("最高得分" + float1);
		// 获取总记录数
		long num = solrDocumentList.getNumFound();
		System.out.println("num" + num);
		// 通过forEach遍历获取每一条记录数
		for (SolrDocument doc : solrDocumentList) {
			// 高亮前的效果
			String id = (String) doc.get("id");
			String title = (String) doc.get("title");
			float PRICE = (float) doc.get("price");
			Date CREATE_DATE = (Date) doc.get("create_date");
			String LOCALITY = (String) doc.get("locality");
			System.out.println("id:" + id + "title" + title + "price" + PRICE + "create_date" + CREATE_DATE + "locality"
					+ LOCALITY);

			// 获取高亮后的数据
			Map<String, List<String>> docMaps = highlighting.get(id);
			String LOCALITY1 = docMaps.get("locality").get(0);
			System.out.println("locality" + LOCALITY1);
		}
	}

	private static void delete() throws SolrServerException, IOException {
		// 创建solrj客户端对象,通过该对象与solr应用交互
		HttpSolrClient client = new HttpSolrClient.Builder("http://192.168.233.133:8983/solr/test_core")
				.withConnectionTimeout(10000).build();
		client.deleteById("0");
		client.commit();
		client.close();
	}

	private static void addOrUpdate() throws SolrServerException, IOException {
		// 创建solrj客户端对象,通过该对象与solr应用交互
		HttpSolrClient client = new HttpSolrClient.Builder("http://192.168.233.133:8983/solr/test_core")
				.withConnectionTimeout(10000).build();
		// 创建文档实例,一个文档实例代表一条记录
		SolrInputDocument document = new SolrInputDocument();
		// 通过SolrInputDocument指定列以及值的信息
		// 通过UUID生成id值(id已存在,则更新)
		// String id = UUID.randomUUID().toString();
		document.addField("id", 0);
		document.addField("title", "立白");
		document.addField("locality", "中国");
		document.addField("price", 6);
		document.addField("create_date", new Date());
		client.add(document);
		client.commit();
		client.close();
	}
}

 

8. 在web中的应用 

addArticle.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
	pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
	<center>
		<h2>添加商品</h2>
		<form action="${pageContext.request.contextPath}/AddArticle" method="post">
			<table>
				<tr><td>商品名</td><td><input type="text" name="title"/></td></tr>
				<tr><td>商品价格</td><td><input type="number" name="price"/></td></tr>
				<tr><td>商品产地</td><td><input type="text" name="locality"/></td></tr>
				<tr><td><input type="submit" value="添加"/></td><td><input type="button" value="跳转到列表页面" onclick="window.location='${pageContext.request.contextPath}/listArticle.jsp'"/>
				</td></tr>
			</table>
		</form>
	</center>
</body>
</html>

listArticle.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
  
      <center>
         <h2>商品列表</h2>
         <form action="${pageContext.request.contextPath}/ListArticleController" method="post">
             <input type="text" name="keyword" value="${keyword}"/>
             <input type="submit" value="检索"/><input type="button" onclick="window.location='addArticle.jsp'" value="跳转至添加商品页面"/>
         </form>
            <c:choose>
              <c:when test="${not empty articles}">
                  <table>
                  <tr><td>商品名</td><td>商品价格</td><td>商品产地</td><td>商品日期</td></tr>
                   <c:forEach items="${articles}" var="article">
                       <tr><td>${article.title}</td><td>${article.price}</td><td>${article.locality}</td><td>${article.create_date}</td></tr>
                   </c:forEach>
               </table>
              </c:when>
              <c:otherwise>
                                                  未查询到相关信息!
              </c:otherwise>
            </c:choose>
            
      </center>
</body>
</html>

 bean

public class Article {
	private String id;
	private String title;
	private float price;
	private String locality;
	private Date create_date;
}

AddArticleController.java

protected void service(HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException{
		request.setCharacterEncoding("utf-8");
		//获取商品的信息
		String locality=request.getParameter("locality");
		String title=request.getParameter("title");
		float price=Float.valueOf(request.getParameter("price"));
		Date create_date=new Date();
	
		Article article=new Article();
		article.setLocality(locality);
		article.setPrice(price);
		article.setTitle(title);
		article.setCreate_date(create_date);
		//创建Service层实例
		ArticleService service=new ArticleService();
		try {
			service.addArticle(article);
		} catch (SolrServerException e) {
			e.printStackTrace();
		}
		request.getRequestDispatcher("/addArticle.jsp").forward(request, response);
	}

ListArticleController.java

protected void service(HttpServletRequest request, HttpServletResponse response)
			throws ServletException, IOException {
		// 设置编码防止中文乱码
		request.setCharacterEncoding("utf-8");
		// 获取查询关键字
		String keyword = request.getParameter("keyword");
		request.setAttribute("keyword", keyword);
		// 创建服务层实例
		ArticleService service = new ArticleService();
		// 根据用户输入的关键字进行检索
		List<Article> articles = null;
		try {
			articles = service.getAllArticleBykeyWork(keyword);
		} catch (SolrServerException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}

		// 将查询到的数据进行存储
		request.setAttribute("articles", articles);

		// 跳转至列表页面
		request.getRequestDispatcher("/listArticle.jsp").forward(request, response);
	}

ArticleService.java

public class ArticleService {

	private ArticleDao articleDao=new ArticleDao();
	private SolrjDao solrjDao=new SolrjDao();
	/**
	 * @param artilce
	 * 添加商品
	 * 1、添加商品的时候,先将数据保存至数据库
	 * 2、将数据信息保存至索引库
	 * 3、如果数据保存时数据库以及索引库都正常的时候就提交事务
	 * @throws IOException 
	 * @throws SolrServerException 
	 */
	public void addArticle(Article article) throws SolrServerException, IOException {
		//将数据保存至数据库,并获取该记录生成主键id值
		String id = articleDao.saveArticle(article);
		article.setId(id);	
		//将数据保存至索引库
		solrjDao.saveArticle(article);
	}
	
	public List<Article> getAllArticleBykeyWork(String keyword) throws SolrServerException, IOException {
		List<Article>  articles = solrjDao.getAllArticleBykeyWork(keyword);
		return articles;
	}

}

SolrjDao.java

public class SolrjDao {

	public void saveArticle(Article article) throws SolrServerException, IOException {
		// 创建solrj客户端对象,通过该对象与solr应用交互
		HttpSolrClient client = new HttpSolrClient.Builder("http://192.168.233.133:8983/solr/test_core")
				.withConnectionTimeout(10000).build();
		// 创建文档实例,一个文档实例代表一条记录
		SolrInputDocument document = new SolrInputDocument();
		// 通过SolrInputDocument指定列以及值的信息
		// 通过UUID生成id值(id已存在,则更新)
		String id = UUID.randomUUID().toString();
		document.addField("id", id);
		document.addField("title", article.getTitle());
		document.addField("locality", article.getLocality());
		document.addField("price", article.getPrice());
		document.addField("create_date", article.getCreate_date());
		client.add(document);
		client.commit();
		client.close();
	}

	public List<Article> getAllArticleBykeyWork(String keyword) throws SolrServerException, IOException {
		HttpSolrClient client = new HttpSolrClient.Builder("http://192.168.233.133:8983/solr/test_core")
				.withConnectionTimeout(10000).build();
		// 创建solrjquery实例,通过这个对象可以设置查询的关键字 设置fl dl 高亮信息 分页等等
		SolrQuery solrQuery = new SolrQuery();
		// 设置查询关键字
		solrQuery.setQuery(keyword);
		// 设置查询属性
		solrQuery.set("df", "locality");
		// 过滤条件,设置要显示的属性
		solrQuery.set("fl", "id,title,price,locality,create_date");
		// 设置分页
		// solrQuery.setStart(0);
		// solrQuery.setRows(2);
		// 设置过滤条件
		solrQuery.set("fq", "price:[3000 TO *]");
		// 设置高亮
		solrQuery.setHighlight(true);
		// 制定高亮的字段
		solrQuery.addHighlightField("locality");
		// 设置高亮相关格式
		solrQuery.setHighlightSimplePre("<font color='red'>");
		solrQuery.setHighlightSimplePost("</font>");
		// 将solrQuery传入client进行查询
		QueryResponse queryResponse = client.query(solrQuery);
		// 获取普通结果集
		SolrDocumentList solrDocumentList = queryResponse.getResults();
		// 获取高亮后的结果集
		Map<String, Map<String, List<String>>> highlighting = queryResponse.getHighlighting();

		// 将查出的结果装入集合
		List<Article> articles = new ArrayList<>();

		// 通过forEach遍历获取每一条记录数
		for (SolrDocument doc : solrDocumentList) {
			Article article = new Article();
			// 高亮前的效果
			String id = (String) doc.get("id");
			article.setId(id);
			String title = (String) doc.get("title");
			article.setTitle(title);
			float PRICE = (float) doc.get("price");
			article.setPrice(PRICE);
			Date CREATE_DATE = (Date) doc.get("create_date");
			article.setCreate_date(CREATE_DATE);
			String LOCALITY = (String) doc.get("locality");
			System.out.println("id:" + id + "title" + title + "price" + PRICE + "create_date" + CREATE_DATE + "locality"
					+ LOCALITY);

			// 获取高亮后的数据
			Map<String, List<String>> docMaps = highlighting.get(id);
			String LOCALITY1 = docMaps.get("locality").get(0);
			article.setLocality(LOCALITY == null ? LOCALITY : LOCALITY1);
			articles.add(article);
			
		}
		return articles;
	}

}

ArticleDao.java

public class ArticleDao {

	public String saveArticle(Article article) {
		// TODO Auto-generated method stub
		// 将数据保存至数据库 可以通过 jdbc mybatis Hibernate等技术来实现,再返回主键id值
		// 生成id值
		String id = UUID.randomUUID().toString();
		return id;
	}

}

至此完结

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值