001/*
002 *  Copyright 2016 Anyware Services
003 *
004 *  Licensed under the Apache License, Version 2.0 (the "License");
005 *  you may not use this file except in compliance with the License.
006 *  You may obtain a copy of the License at
007 *
008 *      http://www.apache.org/licenses/LICENSE-2.0
009 *
010 *  Unless required by applicable law or agreed to in writing, software
011 *  distributed under the License is distributed on an "AS IS" BASIS,
012 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 *  See the License for the specific language governing permissions and
014 *  limitations under the License.
015 */
016package org.ametys.cms.search.solr;
017
018import java.util.Arrays;
019import java.util.HashMap;
020import java.util.HashSet;
021import java.util.List;
022import java.util.Map;
023import java.util.Set;
024
025import org.apache.avalon.framework.container.ContainerUtil;
026import org.apache.avalon.framework.parameters.Parameters;
027import org.apache.avalon.framework.service.ServiceException;
028import org.apache.avalon.framework.service.ServiceManager;
029import org.apache.cocoon.environment.ObjectModelHelper;
030import org.apache.cocoon.environment.Redirector;
031import org.apache.cocoon.environment.Request;
032import org.apache.cocoon.environment.SourceResolver;
033import org.apache.commons.lang3.StringUtils;
034
035import org.ametys.cms.contenttype.ContentTypesHelper;
036import org.ametys.cms.search.cocoon.SearchAction;
037import org.ametys.cms.search.ui.model.SearchUIColumn;
038import org.ametys.cms.search.ui.model.SearchUIModel;
039import org.ametys.cms.search.ui.model.SearchUIModelHelper;
040import org.ametys.core.cocoon.JSonReader;
041import org.ametys.core.util.AvalonLoggerAdapter;
042
043/**
044 * Create a dynamic model with the given columns and facets and return the model columns if valid.
045 */
046public class GetSolrSearchModelAction extends SearchAction
047{
048    
049    /** The content types helper. */
050    protected ContentTypesHelper _contentTypesHelper;
051    
052    /** The search model helper. */
053    protected SearchUIModelHelper _searchModelHelper;
054    
055    @Override
056    public void service(ServiceManager serviceManager) throws ServiceException
057    {
058        super.service(serviceManager);
059        _contentTypesHelper = (ContentTypesHelper) serviceManager.lookup(ContentTypesHelper.ROLE);
060        _searchModelHelper = (SearchUIModelHelper) serviceManager.lookup(SearchUIModelHelper.ROLE);
061    }
062    
063    @SuppressWarnings("unchecked")
064    @Override
065    public Map act(Redirector redirector, SourceResolver resolver, Map objectModel, String source, Parameters parameters) throws Exception
066    {
067        Request request = ObjectModelHelper.getRequest(objectModel);
068        
069        Map<String, Object> results = new HashMap<>();
070        request.setAttribute(JSonReader.OBJECT_TO_READ, results);
071        
072        Map<String, Object> jsParameters = _serverCommHelper.getJsParameters();
073        
074        String modelId = (String) jsParameters.get("model");
075        SearchUIModel model = _searchModelManager.getExtension(modelId);
076        
077        Map<String, Object> values = (Map<String, Object>) jsParameters.get("values");
078        
079        String columnsStr = StringUtils.defaultString((String) values.get("columns"));
080        List<String> columns = Arrays.asList(StringUtils.split(columnsStr, ", "));
081        
082        Object facetObj = values.get("facets");
083        List<String> facets = null;
084        if (facetObj != null && facetObj instanceof List<?>)
085        {
086            facets = (List<String>) facetObj;
087        }
088        
089        Object cTypesObj = values.get("contentTypes");
090        String baseContentType = null;
091        if (cTypesObj != null && cTypesObj instanceof List<?>)
092        {
093            Set<String> contentTypes = new HashSet<>((List<String>) cTypesObj);
094            baseContentType = _contentTypesHelper.getCommonAncestor(contentTypes);
095        }
096        
097        CriteriaSearchUIModelWrapper modelWrapper = new CriteriaSearchUIModelWrapper(model, manager, _context, new AvalonLoggerAdapter(getLogger()));
098        ContainerUtil.service(modelWrapper, manager);
099        
100        Map<String, Object> contextualParameters = (Map<String, Object>) jsParameters.get("contextualParameters");
101        
102        boolean success = true;
103        try
104        {
105            modelWrapper.setFacetedCriteria(baseContentType, facets, contextualParameters);
106        }
107        catch (Exception e)
108        {
109            getLogger().warn("Error setting facets for solr query search.", e);
110            
111            success = false;
112            results.put("error", "facet-error");
113            results.put("message", e.getMessage());
114        }
115        
116        try
117        {
118            modelWrapper.setResultColumns(baseContentType, columns, contextualParameters);
119        }
120        catch (Exception e)
121        {
122            getLogger().warn("Error setting columns for solr query search.", e);
123            
124            success = false;
125            results.put("error", "column-error");
126            results.put("message", e.getMessage());
127        }
128        
129        results.put("success", success);
130        
131        if (success)
132        {
133            Map<String, SearchUIColumn> resultFields = modelWrapper.getResultFields(contextualParameters);
134            results.put("columns", _searchModelHelper.getColumnListInfo(resultFields));
135        }
136        
137        return EMPTY_MAP;
138    }
139    
140}