`
kwj
  • 浏览: 44731 次
  • 性别: Icon_minigender_1
  • 来自: 深圳
社区版块
存档分类
最新评论

第一次使用compass做全文搜索

    博客分类:
  • Java
阅读更多

由于是个资讯类的项目,加上把项目的结构进行了重新部署(基于Annotation spring 2.5 MVC + hibernate),所以也计划把compass也加进来,做个简单的全文搜索。可惜是时间比较紧,前台没有把url-rewrite也加入(考虑到前台经常变化,又不想经常reload,所以用jsp直接读取)。第一次使用compass,基本也上网找找资料,以下总结一下:

 

所需包:compass-2.2.0.jar,lucene-core.jar

 

application-compass.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
    xmlns:context="http://www.springframework.org/schema/context"
    xmlns:aop="http://www.springframework.org/schema/aop"
    xmlns:tx="http://www.springframework.org/schema/tx"
    xsi:schemaLocation="
            http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
            http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-2.5.xsd
            http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-2.5.xsd
            http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-2.5.xsd">
            
     <bean id="annotationConfiguration" class="org.compass.annotations.config.CompassAnnotationsConfiguration"></bean> 
     <bean id="compass" class="org.compass.spring.LocalCompassBean">
	 <!-- anontaition式设置 -->
		<property name="classMappings">
		<list>			
			<value>com.model.Book</value>			
			<value>com.model.News</value>
		</list>
		</property>
		<property name="compassConfiguration" ref="annotationConfiguration"/>
		<property name="compassSettings">
			<props>
				<prop key="compass.engine.connection">D:/javaWeb/lib-read/compass</prop> 
				<prop key="compass.transaction.factory">org.compass.spring.transaction.SpringSyncTransactionFactory</prop>
			</props>  
		</property>
		<property name="transactionManager" ref="transactionManager"/>
	</bean>

	<bean id="hibernateGpsDevice" class="org.compass.spring.device.hibernate.dep.SpringHibernate3GpsDevice">
		<property name="name">
		<value>hibernateDevice</value>
		</property>
		<property name="sessionFactory" ref="sessionFactory"/>
		<property name="mirrorDataChanges">  
            <value>true</value><!-- 同步更新索引 -->  
        </property>  
	</bean>

	<bean id="compassGps" class="org.compass.gps.impl.SingleCompassGps" init-method="start" destroy-method="stop">
		<property name="compass" ref="compass"/>
		<property name="gpsDevices">
			<bean id="hibernateGpsDevice2" class="org.compass.spring.device.hibernate.dep.SpringHibernate3GpsDevice">  
                    <property name="name" value="hibernateDevice"></property>  
                     <property name="sessionFactory" ref="sessionFactory"></property>  
              </bean>
		</property>
	</bean>
	<bean id="compassTemplate"  class="org.compass.core.CompassTemplate">  
	    <property name="compass" ref="compass" />  
	 </bean>
	 
	<!-- 定时重建索引(利用quartz)或随 Spring ApplicationContext启动而重建索引 -->  
   <bean id="compassIndexBuilder"  
       class="com.compass.CompassIndexBuilder"  
       lazy-init="false">  
       <property name="compassGps" ref="compassGps" />  
       <property name="buildIndex" value="true"/><!--   -->  
       <property name="lazyTime" value="10" />  
   </bean>              
</beans>

 

CompassIndexBuilder.java

public class CompassIndexBuilder implements InitializingBean {  
	  
    private static final Logger log = Logger.getLogger(CompassIndexBuilder.class);  

    // 是否需要建立索引,可被设置为false使本Builder失效.  
    private boolean buildIndex = true;  

    // 索引操作线程延时启动的时间,单位为秒  
    private int lazyTime = 50;  

     // Compass封装  
     private CompassGps compassGps;  

     // 索引线程  
     private Thread indexThread = new Thread() {  


             public void run() {  
                     try {  
                             Thread.sleep(lazyTime * 1000);  

                             log.info("begin compass index...");  
                             long beginTime = System.currentTimeMillis();  
                             // 重建索引.  
                             // 如果compass实体中定义的索引文件已存在,索引过程中会建立临时索引,  
                             // 索引完成后再进行覆盖.  
                             compassGps.index();  
                             long costTime = System.currentTimeMillis() - beginTime;  
                             log.info("compss index finished.");  
                             log.info("costed " + costTime + " milliseconds");  
                     } catch (InterruptedException e) {  
                             // simply proceed  
                     }  
             }  
     };  

     /** 
      * 实现<code>InitializingBean</code>接口,在完成注入后调用启动索引线程. 
      * 
      * @see org.springframework.beans.factory.InitializingBean#afterPropertiesSet() 
      */  
     public void afterPropertiesSet() throws Exception {  
             if (buildIndex) {  
                     Assert.notNull(compassGps, "CompassIndexBuilder not set CompassGps yet.");  
                     indexThread.setDaemon(true);  
                     indexThread.setName("Compass Indexer");  
                     indexThread.start();  
             }  
     }  

     public void setBuildIndex(boolean buildIndex) {  
             this.buildIndex = buildIndex;  
     }  

     public void setLazyTime(int lazyTime) {  
             this.lazyTime = lazyTime;  
     }  

     public void setCompassGps(CompassGps compassGps) {  
             this.compassGps = compassGps;  
     }  
}  
 

 

CompassSearchController.java

@Controller
public class CompassSearchController {
	
	@Autowired
	private Compass compass ;
	
	@RequestMapping("/search.do")
	public ModelAndView list(HttpServletRequest request, HttpServletResponse response) throws UnsupportedEncodingException
	{
		ModelAndView mav = new ModelAndView("search");
		int offsetStart = 0;
		int maxPageItems = 10;
		int maxIndexPages = 10;		
		
		String szOffsetStart = request.getParameter("pager.offset");
		if (szOffsetStart != null)
			offsetStart = Integer.valueOf(szOffsetStart).intValue();
		
		String keywords = "";	
		if (request.getParameter("keywords") != null)
		{
			keywords = request.getParameter("keywords");			
		}
		String keyStr = "";
		try
		{
			keywords = URLDecoder.decode(keywords, "UTF-8");
			keyStr = URLEncoder.encode(keywords, "UTF-8");
		}
		catch (UnsupportedEncodingException e)
		{
			e.printStackTrace();
		}		
	       //打开session会话

	       CompassSession session = compass.openSession();

	       //开启session事务

	       CompassTransaction tx = session.beginLocalTransaction();

	       //用session建立一个查询

	       CompassQueryBuilder queryBuilder = session.queryBuilder();

	       //得到查询结果

	       CompassQuery a = queryBuilder.queryString(keywords).toQuery();
	       CompassQuery b = queryBuilder.ge("isShow", "1");
	       CompassBooleanQueryBuilder CQB = queryBuilder.bool().addMust(a).addMust(b);

	       //按照postTime属性进行排列,默认是升序

	       //query.addSort(“postTime”,SortDirection.REVERSE);//是降序

	       //query.addSort("postTime");

	       //获得结果集

	       CompassHits hits = query.hits();
	       
	       int itemCount = hits.length();
	      

	       //为了防止角标越界,所以在结果集和要取得的内容之间取最小值

	       int end = Math.min(hits.length(),  offsetStart + maxPageItems);
	       
	       
	       List list = new ArrayList();
	       for (int i = offsetStart; i < end; i++){

	           //取得每一个结果

	          list.add(hits.data(i));

	          

	           //高亮  返回的是高亮后的字符串

	           /*String ht = hits.highlighter(i).fragment("content");

	           if(ht!=null){

	              aritcle.setContent(ht);

	           }

	          

	           list.add(aritcle);*/

	       }

	       tx.commit();

	       session.close();
	       
	       int currPage = ((offsetStart-1) + maxPageItems) / maxPageItems;
	       if((offsetStart-1) % maxPageItems != 0)
	           currPage++;

	       int totalPage = itemCount/maxPageItems;
	       if(itemCount % maxPageItems != 0)
	           totalPage++;
	       
	       mav.addObject("itemCount", itemCount);
	       mav.addObject("maxPageItems", maxPageItems);
	       mav.addObject("maxIndexPages", maxIndexPages);
	       mav.addObject("offsetStart", offsetStart);
	       mav.addObject("currPage", currPage);
	       mav.addObject("totalPage", totalPage);
	       mav.addObject("keywords", keywords);
	       mav.addObject("keyStr", keyStr);
	       mav.addObject("dataList", list);
	       return mav;
	    }  

 

search.jsp

 

<%@page contentType="text/html; charset=utf-8"%>
<%@include file="header.jsp"%>
<%@ include file="../common/taglibs.jsp"%>
<%@include file="menu.jsp"%>
	<div class="breadcrumbs">您的位置:<a href="./">首页</a> &gt; <span>搜索结果</span></div>
	<div class="content">
			<div class="pagebox_1">
				<h4 class="boxtitle"><strong>“${keywords}”的搜索结果${keystr},总共${itemCount}条记录</strong></h4>
				<div class="boxtext">
                    <c:if test="${not empty dataList}">
                      <ul class="newslist_1">
                      <c:forEach var="data" items="${dataList}">
                      <c:set var="content" value="${data.content}" />
                      <%
                        String content = (String)pageContext.getAttribute("content");
                      %>
                        
                          <li>
                            <c:choose>
                              <c:when test="${fn:contains(data.class, 'Book')}">
                              <h5><a href="bookshow.jsp?id=${data.id}" class="sort">[ 图书 ]</a><a href="bookshow.jsp?id=${data.id}" target="_blank">${data.title}</a></h5>
                              </c:when>

                              <c:when test="${fn:contains(data.class, 'News')}">
                              <c:set var="url" value="${data.url}" />
                              <c:if test="${empty data.url}">
                                <c:set var="url" value="newsshow.jsp?id=${data.id}" />
                              </c:if>
                              <h5><a href="newsshow.jsp?id=${data.id}" class="sort">[ 资讯与动态 ]</a><a href="${url}" target="_blank">${data.title}</a></h5>
                              </c:when>                   

                            </c:choose>
                              <div class="text"><%=StringExtract.extractText2(StringUtils.abbreviate(content,150))%></div>
                          </li>
                      </c:forEach>    
                      </ul>
                      <!--<c:if test="${totalPage > 1}">
                      <div class="turnpage">
                      <c:forEach begin="0" end="${totalPage - 1}" step="1" varStatus="status">
                          <a href="search.do?keywords=${keywords}&pager.offset=${status.index * maxPageItems}" <c:if test="${status.index == (currPage-1)}">class="cur"</c:if>>${status.index + 1}</a> 
                       </c:forEach>
                      </div>
                      </c:if>-->
                      <div class="turnpage"> <pg:pager items="${itemCount}" maxPageItems="${maxPageItems}" maxIndexPages="${maxIndexPages}" export="offset,currentPageNumber=pageNumber" scope="request" url="search.do"><pg:index><jsp:include page="pager/searchPagerControl.jsp" flush="true"/></pg:index></pg:pager></div>
                    </c:if>
                    <c:if test="${empty dataList}">
                      暂时没有您要查找的信息!
                    </c:if>										
				</div>
			</div><!-- pagebox_1 -->
	</div>


<%@include file="footer.jsp"%>

 

searchPageControl.jsp

<%@page contentType="text/html;charset=utf-8"%>
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<%@ taglib uri="http://java.sun.com/jsp/jstl/fmt" prefix="fmt" %>
<%@ taglib uri="http://java.sun.com/jsp/jstl/functions" prefix="fn" %>
<%@ page session="false" %>
<%@ taglib uri="http://jsptags.com/tags/navigation/pager" prefix="pg" %>
<pg:param name="keywords" value="${keyStr}" />
<jsp:useBean id="currentPageNumber" type="java.lang.Integer" scope="request"/>
<pg:prev export="pageUrl" ifnull="<%= true %>">
	<c:if test="${not empty pageUrl }"><a href="${pageUrl }">上一页</a></c:if>
</pg:prev>
<pg:pages>
	<c:if test="${pageNumber == currentPageNumber }"><a href="#" class="cur">${pageNumber }</a></c:if>
	<c:if test="${pageNumber != currentPageNumber }"><a href="${pageUrl }">${pageNumber }</a></c:if>
</pg:pages>
<pg:next export="pageUrl" ifnull="<%= true %>">
  <c:if test="${not empty pageUrl }"> <a href="${pageUrl }">下一页</a></c:if>
</pg:next>
分享到:
评论
1 楼 wangjianjun852 2012-05-26  
请问一下楼主, 用过compass+spring+hibernate的组合吗?

相关推荐

    compass_hibernate_spring2.zip

    Compass 是一个全文搜索引擎,Hibernate 是一个流行的 Java ORM(对象关系映射)框架,而 Spring 是一个全面的企业级应用开发框架,尤其在依赖注入和事务管理方面表现卓越。这三者的结合可以实现高效的搜索功能以及...

    大学文献检索资料 DOC

    第一章 信息检索的基本知识 第一节 信息、知识、文献、情报 信息: 应用文字、数据和信号形式通过一定的传递和处理,来表现各种相互联系的客观事物在运动变化中所具有特征性的内容的总称。 知识: 人们通过实践对...

    java开源包8

    nfs-rpc是一个集成了各种知名通信框架的高性能RPC框架,目前其最好的性能为在采用grizzly作为通信框架,采用pb作为序列化/反序列化时,tps为168k次/秒。 其支持的功能主要为: 1、透明的调用远端服务器提供的功能...

    java开源包11

    nfs-rpc是一个集成了各种知名通信框架的高性能RPC框架,目前其最好的性能为在采用grizzly作为通信框架,采用pb作为序列化/反序列化时,tps为168k次/秒。 其支持的功能主要为: 1、透明的调用远端服务器提供的功能...

    java源码包---java 源码 大量 实例

     当用户发送第一次请求的时候,验证用户登录,创建一个该qq号和服务器端保持通讯连接得线程,启动该通讯线程,通讯完毕,关闭Scoket。  QQ客户端登录界面,中部有三个JPanel,有一个叫选项卡窗口管理。还可以更新...

    java开源包1

    nfs-rpc是一个集成了各种知名通信框架的高性能RPC框架,目前其最好的性能为在采用grizzly作为通信框架,采用pb作为序列化/反序列化时,tps为168k次/秒。 其支持的功能主要为: 1、透明的调用远端服务器提供的功能...

    java开源包2

    nfs-rpc是一个集成了各种知名通信框架的高性能RPC框架,目前其最好的性能为在采用grizzly作为通信框架,采用pb作为序列化/反序列化时,tps为168k次/秒。 其支持的功能主要为: 1、透明的调用远端服务器提供的功能...

    java开源包3

    nfs-rpc是一个集成了各种知名通信框架的高性能RPC框架,目前其最好的性能为在采用grizzly作为通信框架,采用pb作为序列化/反序列化时,tps为168k次/秒。 其支持的功能主要为: 1、透明的调用远端服务器提供的功能...

    java开源包6

    nfs-rpc是一个集成了各种知名通信框架的高性能RPC框架,目前其最好的性能为在采用grizzly作为通信框架,采用pb作为序列化/反序列化时,tps为168k次/秒。 其支持的功能主要为: 1、透明的调用远端服务器提供的功能...

    java开源包5

    nfs-rpc是一个集成了各种知名通信框架的高性能RPC框架,目前其最好的性能为在采用grizzly作为通信框架,采用pb作为序列化/反序列化时,tps为168k次/秒。 其支持的功能主要为: 1、透明的调用远端服务器提供的功能...

    java开源包10

    nfs-rpc是一个集成了各种知名通信框架的高性能RPC框架,目前其最好的性能为在采用grizzly作为通信框架,采用pb作为序列化/反序列化时,tps为168k次/秒。 其支持的功能主要为: 1、透明的调用远端服务器提供的功能...

    java开源包4

    nfs-rpc是一个集成了各种知名通信框架的高性能RPC框架,目前其最好的性能为在采用grizzly作为通信框架,采用pb作为序列化/反序列化时,tps为168k次/秒。 其支持的功能主要为: 1、透明的调用远端服务器提供的功能...

    java开源包7

    nfs-rpc是一个集成了各种知名通信框架的高性能RPC框架,目前其最好的性能为在采用grizzly作为通信框架,采用pb作为序列化/反序列化时,tps为168k次/秒。 其支持的功能主要为: 1、透明的调用远端服务器提供的功能...

    java开源包9

    nfs-rpc是一个集成了各种知名通信框架的高性能RPC框架,目前其最好的性能为在采用grizzly作为通信框架,采用pb作为序列化/反序列化时,tps为168k次/秒。 其支持的功能主要为: 1、透明的调用远端服务器提供的功能...

    java开源包101

    nfs-rpc是一个集成了各种知名通信框架的高性能RPC框架,目前其最好的性能为在采用grizzly作为通信框架,采用pb作为序列化/反序列化时,tps为168k次/秒。 其支持的功能主要为: 1、透明的调用远端服务器提供的功能...

    Java资源包01

    nfs-rpc是一个集成了各种知名通信框架的高性能RPC框架,目前其最好的性能为在采用grizzly作为通信框架,采用pb作为序列化/反序列化时,tps为168k次/秒。 其支持的功能主要为: 1、透明的调用远端服务器提供的功能...

    java源码包2

     当用户发送第一次请求的时候,验证用户登录,创建一个该qq号和服务器端保持通讯连接得线程,启动该通讯线程,通讯完毕,关闭Scoket。  QQ客户端登录界面,中部有三个JPanel,有一个叫选项卡窗口管理。还可以更新...

    java源码包3

     当用户发送第一次请求的时候,验证用户登录,创建一个该qq号和服务器端保持通讯连接得线程,启动该通讯线程,通讯完毕,关闭Scoket。  QQ客户端登录界面,中部有三个JPanel,有一个叫选项卡窗口管理。还可以更新...

    java源码包4

     当用户发送第一次请求的时候,验证用户登录,创建一个该qq号和服务器端保持通讯连接得线程,启动该通讯线程,通讯完毕,关闭Scoket。  QQ客户端登录界面,中部有三个JPanel,有一个叫选项卡窗口管理。还可以更新...

    weather_dashboard:一个用于查看多个城市的天气预报的应用程序。 使用OpenWeather API

    如果您是第一次访问该页面,那么将显示北卡罗来纳州罗利的天气。 如果您不喜欢罗利的天气,则可以。 寻找新城市 要查找新城市的天气,只需在搜索栏中输入该城市的名称,然后按Enter键或按蓝色的搜索按钮即可。 您...

Global site tag (gtag.js) - Google Analytics