1   /**
2    * Copyright (c) 2000-2010 Liferay, Inc. All rights reserved.
3    *
4    * This library is free software; you can redistribute it and/or modify it under
5    * the terms of the GNU Lesser General Public License as published by the Free
6    * Software Foundation; either version 2.1 of the License, or (at your option)
7    * any later version.
8    *
9    * This library is distributed in the hope that it will be useful, but WITHOUT
10   * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
11   * FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
12   * details.
13   */
14  
15  package com.liferay.portal.servlet;
16  
17  import com.liferay.portal.kernel.log.Log;
18  import com.liferay.portal.kernel.log.LogFactoryUtil;
19  import com.liferay.portal.kernel.scheduler.SchedulerEngineUtil;
20  import com.liferay.portal.kernel.scheduler.SchedulerEntry;
21  import com.liferay.portal.kernel.scheduler.SchedulerEntryImpl;
22  import com.liferay.portal.kernel.scheduler.TimeUnit;
23  import com.liferay.portal.kernel.scheduler.TriggerType;
24  import com.liferay.portal.kernel.util.GetterUtil;
25  import com.liferay.portal.kernel.util.ObjectValuePair;
26  import com.liferay.portal.kernel.util.PortalClassLoaderUtil;
27  import com.liferay.portal.kernel.util.PropsKeys;
28  import com.liferay.portal.search.lucene.LuceneIndexer;
29  import com.liferay.portal.search.lucene.messaging.CleanUpMessageListener;
30  import com.liferay.portal.util.PortalInstances;
31  import com.liferay.portal.util.PropsUtil;
32  import com.liferay.portal.util.PropsValues;
33  
34  import java.util.ArrayList;
35  import java.util.List;
36  
37  import javax.servlet.ServletConfig;
38  import javax.servlet.ServletException;
39  import javax.servlet.http.HttpServlet;
40  
41  /**
42   * <a href="LuceneServlet.java.html"><b><i>View Source</i></b></a>
43   *
44   * @author Brian Wing Shun Chan
45   * @author Jorge Ferrer
46   */
47  public class LuceneServlet extends HttpServlet {
48  
49      public void init(ServletConfig servletConfig) throws ServletException {
50          super.init(servletConfig);
51  
52          long[] companyIds = PortalInstances.getCompanyIds();
53  
54          for (int i = 0; i < companyIds.length; i++) {
55              long companyId = companyIds[i];
56  
57              if (GetterUtil.getBoolean(
58                      PropsUtil.get(PropsKeys.INDEX_ON_STARTUP))) {
59  
60                  if (_log.isInfoEnabled()) {
61                      _log.info("Indexing Lucene on startup");
62                  }
63  
64                  LuceneIndexer indexer = new LuceneIndexer(companyId);
65                  Thread indexerThread = null;
66  
67                  if (GetterUtil.getBoolean(
68                          PropsUtil.get(PropsKeys.INDEX_WITH_THREAD))) {
69  
70                      indexerThread = new Thread(
71                          indexer, THREAD_NAME + "." + companyId);
72  
73                      indexerThread.setPriority(THREAD_PRIORITY);
74  
75                      indexerThread.start();
76                  }
77                  else {
78                      indexer.reindex();
79                  }
80  
81                  _indexers.add(
82                      new ObjectValuePair<LuceneIndexer, Thread>(
83                          indexer, indexerThread));
84              }
85  
86              if (PropsValues.LUCENE_STORE_JDBC_AUTO_CLEAN_UP_ENABLED) {
87                  SchedulerEntry schedulerEntry = new SchedulerEntryImpl();
88  
89                  schedulerEntry.setEventListenerClass(
90                      CleanUpMessageListener.class.getName());
91                  schedulerEntry.setTimeUnit(TimeUnit.MINUTE);
92                  schedulerEntry.setTriggerType(TriggerType.SIMPLE);
93                  schedulerEntry.setTriggerValue(
94                      PropsValues.LUCENE_STORE_JDBC_AUTO_CLEAN_UP_INTERVAL);
95  
96                  try {
97                      SchedulerEngineUtil.schedule(
98                          schedulerEntry, PortalClassLoaderUtil.getClassLoader());
99                  }
100                 catch (Exception e) {
101                     _log.error(e, e);
102                 }
103             }
104         }
105     }
106 
107     public void destroy() {
108 
109         // Wait for indexer to be gracefully interrupted
110 
111         for (int i = 0; i < _indexers.size(); i++) {
112             ObjectValuePair<LuceneIndexer, Thread> ovp = _indexers.get(i);
113 
114             LuceneIndexer indexer = ovp.getKey();
115             Thread indexerThread = ovp.getValue();
116 
117             if ((indexer != null) && (!indexer.isFinished()) &&
118                 (indexerThread != null)) {
119 
120                 if (_log.isWarnEnabled()) {
121                     _log.warn("Waiting for Lucene indexer to shutdown");
122                 }
123 
124                 indexer.halt();
125 
126                 try {
127                     indexerThread.join(THREAD_TIMEOUT);
128                 }
129                 catch (InterruptedException e) {
130                     _log.error("Lucene indexer shutdown interrupted", e);
131                 }
132             }
133         }
134 
135         // Parent
136 
137         super.destroy();
138     }
139 
140     private static final String THREAD_NAME = LuceneIndexer.class.getName();
141 
142     private static final int THREAD_PRIORITY = Thread.MIN_PRIORITY;
143 
144     private static final int THREAD_TIMEOUT = 60000;
145 
146     private static Log _log = LogFactoryUtil.getLog(LuceneServlet.class);
147 
148     private List<ObjectValuePair<LuceneIndexer, Thread>> _indexers =
149         new ArrayList<ObjectValuePair<LuceneIndexer, Thread>>();
150 
151 }