001
014
015 package com.liferay.portal.kernel.search;
016
017 import com.liferay.portal.kernel.search.facet.Facet;
018 import com.liferay.portal.kernel.util.GetterUtil;
019 import com.liferay.portal.kernel.util.SetUtil;
020 import com.liferay.portal.kernel.util.UnicodeProperties;
021 import com.liferay.portal.kernel.util.Validator;
022 import com.liferay.portal.model.Group;
023 import com.liferay.portal.service.GroupLocalServiceUtil;
024 import com.liferay.portlet.expando.model.ExpandoBridge;
025 import com.liferay.portlet.expando.model.ExpandoColumnConstants;
026 import com.liferay.portlet.expando.util.ExpandoBridgeFactoryUtil;
027 import com.liferay.portlet.expando.util.ExpandoBridgeIndexerUtil;
028
029 import java.util.List;
030 import java.util.Locale;
031 import java.util.Map;
032 import java.util.Set;
033
034 import javax.portlet.PortletURL;
035
036
039 public class FacetedSearcher extends BaseIndexer {
040
041 public static Indexer getInstance() {
042 return new FacetedSearcher();
043 }
044
045 @Override
046 public String[] getClassNames() {
047 return null;
048 }
049
050 @Override
051 public IndexerPostProcessor[] getIndexerPostProcessors() {
052 throw new UnsupportedOperationException();
053 }
054
055 @Override
056 public String getPortletId() {
057 return null;
058 }
059
060 @Override
061 public void registerIndexerPostProcessor(
062 IndexerPostProcessor indexerPostProcessor) {
063
064 throw new UnsupportedOperationException();
065 }
066
067 @Override
068 public void unregisterIndexerPostProcessor(
069 IndexerPostProcessor indexerPostProcessor) {
070
071 throw new UnsupportedOperationException();
072 }
073
074 protected void addSearchExpandoKeywords(
075 BooleanQuery searchQuery, SearchContext searchContext,
076 String keywords, String className)
077 throws Exception {
078
079 ExpandoBridge expandoBridge = ExpandoBridgeFactoryUtil.getExpandoBridge(
080 searchContext.getCompanyId(), className);
081
082 Set<String> attributeNames = SetUtil.fromEnumeration(
083 expandoBridge.getAttributeNames());
084
085 for (String attributeName : attributeNames) {
086 UnicodeProperties properties = expandoBridge.getAttributeProperties(
087 attributeName);
088
089 int indexType = GetterUtil.getInteger(
090 properties.getProperty(ExpandoColumnConstants.INDEX_TYPE));
091
092 if (indexType != ExpandoColumnConstants.INDEX_TYPE_NONE) {
093 String fieldName = ExpandoBridgeIndexerUtil.encodeFieldName(
094 attributeName);
095
096 if (searchContext.isAndSearch()) {
097 searchQuery.addRequiredTerm(fieldName, keywords);
098 }
099 else {
100 searchQuery.addTerm(fieldName, keywords);
101 }
102 }
103 }
104 }
105
106 @Override
107 protected BooleanQuery createFullQuery(
108 BooleanQuery contextQuery, SearchContext searchContext)
109 throws Exception {
110
111 BooleanQuery searchQuery = BooleanQueryFactoryUtil.create(
112 searchContext);
113
114 String keywords = searchContext.getKeywords();
115
116 if (Validator.isNotNull(keywords)) {
117 addSearchLocalizedTerm(
118 searchQuery, searchContext, Field.ASSET_CATEGORY_TITLES, false);
119
120 searchQuery.addExactTerm(Field.ASSET_TAG_NAMES, keywords);
121 searchQuery.addTerms(Field.KEYWORDS, keywords);
122
123 int groupId = GetterUtil.getInteger(
124 searchContext.getAttribute(Field.GROUP_ID));
125
126 if (groupId == 0) {
127 searchQuery.addTerm(
128 Field.STAGING_GROUP, "true", false,
129 BooleanClauseOccur.MUST_NOT);
130 }
131 }
132
133 List<Group> inactiveGroups = GroupLocalServiceUtil.getActiveGroups(
134 searchContext.getCompanyId(), false);
135
136 for (Group inactiveGroup : inactiveGroups) {
137 searchQuery.addTerm(
138 Field.GROUP_ID, String.valueOf(inactiveGroup.getGroupId()),
139 false, BooleanClauseOccur.MUST_NOT);
140 }
141
142 for (String entryClassName : searchContext.getEntryClassNames()) {
143 Indexer indexer = IndexerRegistryUtil.getIndexer(entryClassName);
144
145 if (indexer == null) {
146 continue;
147 }
148
149 String searchEngineId = searchContext.getSearchEngineId();
150
151 if (!searchEngineId.equals(indexer.getSearchEngineId())) {
152 continue;
153 }
154
155 if (Validator.isNotNull(keywords)) {
156 addSearchExpandoKeywords(
157 searchQuery, searchContext, keywords, entryClassName);
158 }
159
160 indexer.postProcessSearchQuery(searchQuery, searchContext);
161
162 for (IndexerPostProcessor indexerPostProcessor :
163 indexer.getIndexerPostProcessors()) {
164
165 indexerPostProcessor.postProcessSearchQuery(
166 searchQuery, searchContext);
167 }
168 }
169
170 Map<String, Facet> facets = searchContext.getFacets();
171
172 for (Facet facet : facets.values()) {
173 BooleanClause facetClause = facet.getFacetClause();
174
175 if (facetClause != null) {
176 contextQuery.add(
177 facetClause.getQuery(),
178 facetClause.getBooleanClauseOccur());
179 }
180 }
181
182 BooleanQuery fullQuery = BooleanQueryFactoryUtil.create(searchContext);
183
184 fullQuery.add(contextQuery, BooleanClauseOccur.MUST);
185
186 if (searchQuery.hasClauses()) {
187 fullQuery.add(searchQuery, BooleanClauseOccur.MUST);
188 }
189
190 BooleanClause[] booleanClauses = searchContext.getBooleanClauses();
191
192 if (booleanClauses != null) {
193 for (BooleanClause booleanClause : booleanClauses) {
194 fullQuery.add(
195 booleanClause.getQuery(),
196 booleanClause.getBooleanClauseOccur());
197 }
198 }
199
200 for (String entryClassName : searchContext.getEntryClassNames()) {
201 Indexer indexer = IndexerRegistryUtil.getIndexer(entryClassName);
202
203 if (indexer == null) {
204 continue;
205 }
206
207 String searchEngineId = searchContext.getSearchEngineId();
208
209 if (!searchEngineId.equals(indexer.getSearchEngineId())) {
210 continue;
211 }
212
213 for (IndexerPostProcessor indexerPostProcessor :
214 indexer.getIndexerPostProcessors()) {
215
216 indexerPostProcessor.postProcessFullQuery(
217 fullQuery, searchContext);
218 }
219 }
220
221 return fullQuery;
222 }
223
224 @Override
225 protected void doDelete(Object obj) throws Exception {
226 throw new UnsupportedOperationException();
227 }
228
229 @Override
230 protected Document doGetDocument(Object obj) throws Exception {
231 throw new UnsupportedOperationException();
232 }
233
234 @Override
235 protected Summary doGetSummary(
236 Document document, Locale locale, String snippet,
237 PortletURL portletURL)
238 throws Exception {
239
240 throw new UnsupportedOperationException();
241 }
242
243 @Override
244 protected void doReindex(Object obj) throws Exception {
245 throw new UnsupportedOperationException();
246 }
247
248 @Override
249 protected void doReindex(String className, long classPK) throws Exception {
250 throw new UnsupportedOperationException();
251 }
252
253 @Override
254 protected void doReindex(String[] ids) throws Exception {
255 throw new UnsupportedOperationException();
256 }
257
258 @Override
259 protected Hits doSearch(SearchContext searchContext)
260 throws SearchException {
261
262 try {
263 searchContext.setSearchEngineId(getSearchEngineId());
264
265 BooleanQuery contextQuery = BooleanQueryFactoryUtil.create(
266 searchContext);
267
268 contextQuery.addRequiredTerm(
269 Field.COMPANY_ID, searchContext.getCompanyId());
270
271 BooleanQuery fullQuery = createFullQuery(
272 contextQuery, searchContext);
273
274 QueryConfig queryConfig = searchContext.getQueryConfig();
275
276 fullQuery.setQueryConfig(queryConfig);
277
278 return SearchEngineUtil.search(searchContext, fullQuery);
279 }
280 catch (Exception e) {
281 throw new SearchException(e);
282 }
283 }
284
285 @Override
286 protected String getPortletId(SearchContext searchContext) {
287 return null;
288 }
289
290
294 protected boolean isFilterSearch(SearchContext searchContext) {
295 return isUseSearchResultPermissionFilter(searchContext);
296 }
297
298 @Override
299 protected boolean isUseSearchResultPermissionFilter(
300 SearchContext searchContext) {
301
302 if (searchContext.getEntryClassNames() == null) {
303 return super.isFilterSearch();
304 }
305
306 for (String entryClassName : searchContext.getEntryClassNames()) {
307 Indexer indexer = IndexerRegistryUtil.getIndexer(entryClassName);
308
309 if (indexer == null) {
310 continue;
311 }
312
313 if (indexer.isFilterSearch()) {
314 return true;
315 }
316 }
317
318 return super.isFilterSearch();
319 }
320
321 }