Package org.jahia.services.search

Source Code of org.jahia.services.search.SearchCriteriaFactory

/**
* This file is part of Jahia, next-generation open source CMS:
* Jahia's next-generation, open source CMS stems from a widely acknowledged vision
* of enterprise application convergence - web, search, document, social and portal -
* unified by the simplicity of web content management.
*
* For more information, please visit http://www.jahia.com.
*
* Copyright (C) 2002-2011 Jahia Solutions Group SA. All rights reserved.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*
* As a special exception to the terms and conditions of version 2.0 of
* the GPL (or any later version), you may redistribute this Program in connection
* with Free/Libre and Open Source Software ("FLOSS") applications as described
* in Jahia's FLOSS exception. You should have received a copy of the text
* describing the FLOSS exception, and it is also available here:
* http://www.jahia.com/license
*
* Commercial and Supported Versions of the program (dual licensing):
* alternatively, commercial and supported versions of the program may be used
* in accordance with the terms and conditions contained in a separate
* written agreement between you and Jahia Solutions Group SA.
*
* If you are unsure which license is appropriate for your use,
* please contact the sales department at sales@jahia.com.
*/

package org.jahia.services.search;

import java.lang.reflect.InvocationTargetException;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.Locale;
import java.util.Map;

import javax.jcr.PropertyType;
import javax.jcr.RepositoryException;
import javax.jcr.Value;
import javax.jcr.nodetype.PropertyDefinition;
import javax.servlet.http.HttpServletRequest;

import org.apache.commons.beanutils.BeanUtilsBean;
import org.apache.commons.beanutils.ConvertUtilsBean;
import org.apache.commons.beanutils.Converter;
import org.apache.commons.beanutils.PropertyUtilsBean;
import org.apache.commons.beanutils.converters.ArrayConverter;
import org.apache.commons.beanutils.converters.StringConverter;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.jahia.services.content.JCRContentUtils;
import org.jahia.services.content.nodetypes.ExtendedItemDefinition;
import org.jahia.services.content.nodetypes.ExtendedNodeType;
import org.jahia.services.content.nodetypes.ExtendedPropertyDefinition;
import org.jahia.services.content.nodetypes.NodeTypeRegistry;
import org.jahia.services.content.nodetypes.SelectorType;
import org.jahia.services.render.RenderContext;
import org.jahia.services.search.SearchCriteria.DateValue;
import org.jahia.services.search.SearchCriteria.NodeProperty;
import org.jahia.services.search.SearchCriteria.NodePropertyDescriptor;
import org.jahia.services.search.SearchCriteria.Term;

/**
* Factory for retrieving {@link SearchCriteria} object data.
*
* @author Sergiy Shyrkov
*/
public class SearchCriteriaFactory {

    private static final String ATTR_QUERY_PARAMS = SearchCriteria.class
            .getName();

    private static final ConvertUtilsBean CONVERTER_UTILS_BEAN = new ConvertUtilsBean();

    private static Converter ENUM_CONVERTER = new Converter() {
        public Object convert(Class type, Object value) {
            return Enum.valueOf(type, String.valueOf(value).toUpperCase());
        }
    };

    private static Logger logger = LoggerFactory
            .getLogger(SearchCriteriaFactory.class);

    private static final String PARAM_NAME_PREFIX = "src_";

    static {
        CONVERTER_UTILS_BEAN.register(ENUM_CONVERTER, DateValue.Type.class);
        CONVERTER_UTILS_BEAN.register(ENUM_CONVERTER,
                NodeProperty.Type.class);
        CONVERTER_UTILS_BEAN.register(ENUM_CONVERTER, Term.MatchType.class);
       
        ArrayConverter converter = new ArrayConverter(String[].class, new StringConverter());
        converter.setAllowedChars(new char[] {'.', '-', '_'});
        CONVERTER_UTILS_BEAN.register(converter, String[].class);
    }

    /**
     * Looks up the {@link SearchCriteria} object in the request scope. If it is
     * not found, instantiates it and populates it using current request
     * parameters.
     *
     * @param ctx
     *            current context object
     * @return the {@link SearchCriteria} bean with the current search
     *         parameters
     */
    @SuppressWarnings("unchecked")
    public static SearchCriteria getInstance(RenderContext ctx) {

        SearchCriteria searchParams = (SearchCriteria) ctx.getRequest().getAttribute(ATTR_QUERY_PARAMS);

        if (null == searchParams && isRequestDataPresent(ctx.getRequest())) {
            searchParams = new SearchCriteria();
            try {
                Map<String, Object> properties = new HashMap<String, Object>();
                Enumeration<String> params = ctx.getRequest().getParameterNames();
                while (params.hasMoreElements()) {
                    String param = params.nextElement();
                    if (param.startsWith(PARAM_NAME_PREFIX)) {
                        properties.put(param.substring(
                                PARAM_NAME_PREFIX.length()), ctx.getRequest().getParameter(param));
                    }
                }
               
                new BeanUtilsBean(CONVERTER_UTILS_BEAN, new PropertyUtilsBean())
                        .populate(searchParams, properties);

            } catch (Exception e) {
                Throwable cause = e.getCause() != null ? e.getCause() : e;
                if (cause instanceof InvocationTargetException
                        && ((InvocationTargetException) cause)
                                .getTargetException() != null) {
                    cause = ((InvocationTargetException) cause)
                            .getTargetException();
                }
                logger.warn("Error parsing search parameters", cause);
            }

            if (logger.isDebugEnabled()) {
                logger.debug(searchParams.toString());
            }

            // initialize node properties
            initNodeProperties(searchParams, ctx.getMainResource().getLocale());

            ctx.getRequest().setAttribute(ATTR_QUERY_PARAMS, searchParams);
        }

        return searchParams;
    }

    private static NodePropertyDescriptor getPropertyDescriptor(
            ExtendedItemDefinition itemDef, ExtendedNodeType nodeType,
            Locale locale) throws RepositoryException {

        ExtendedPropertyDefinition propDefExt = (ExtendedPropertyDefinition) itemDef;
        PropertyDefinition propDef = JCRContentUtils.getPropertyDefinition(
                nodeType, propDefExt.getName());

        NodeProperty.Type type = NodeProperty.Type.TEXT;
        switch (propDef.getRequiredType()) {
        case PropertyType.BOOLEAN:
            type = NodeProperty.Type.BOOLEAN;
            break;
        case PropertyType.DATE:
            type = NodeProperty.Type.DATE;
            break;
        case PropertyType.STRING:
            if (SelectorType.CATEGORY == (propDefExt.getSelector())) {
                type = NodeProperty.Type.CATEGORY;
            }
            break;
        }

        NodePropertyDescriptor descriptor = new NodePropertyDescriptor(itemDef.getName(), itemDef
                .getLabel(locale != null ? locale : Locale.ENGLISH, nodeType), type);

        descriptor.setMultiple(propDef.isMultiple());
        if (propDef.getValueConstraints().length > 0) {
            descriptor.setConstrained(true);
            descriptor.setAllowedValues(propDef.getValueConstraints());
        }
        descriptor.setSelectorOptions(propDefExt.getSelectorOptions());

        // TODO handle multiple default values
        Value[] defaultValues = propDef.getDefaultValues();
        if (defaultValues != null && defaultValues.length > 0) {
            descriptor.setDefaultValue(defaultValues[0].getString());
        }

        return descriptor;
    }

    public static NodePropertyDescriptor getPropertyDescriptor(
            String nodeType, String propertyName, Locale locale)
            throws RepositoryException {
        PropertyDefinition propDef = JCRContentUtils.getPropertyDefinition(
                nodeType, propertyName);
        NodePropertyDescriptor descriptor = null;
        if (propDef != null) {
            descriptor = getPropertyDescriptor(
                    (ExtendedItemDefinition) propDef, NodeTypeRegistry
                            .getInstance().getNodeType(nodeType), locale);
        }

        return descriptor;
    }

    private static void initNodeProperties(SearchCriteria searchParams,
            Locale locale) {

        List<NodeProperty> props = new LinkedList<NodeProperty>();
        for (Map.Entry<String, Map<String, NodeProperty>> docTypeEntry : searchParams
                .getProperties().entrySet()) {
            for (Map.Entry<String, NodeProperty> propEntry : docTypeEntry
                    .getValue().entrySet()) {
                NodeProperty prop = propEntry.getValue();
                // set node type and property name
                prop.setNodeType(docTypeEntry.getKey());
                prop.setName(propEntry.getKey());
                if (!prop.isAllEmpty()) {
                    try {
                        // retrieve property descriptor
                        NodePropertyDescriptor descriptor = getPropertyDescriptor(
                                prop.getNodeType(), prop.getName(), locale);
                        // set additional properties
                        prop.setConstrained(descriptor.isConstrained());
                        prop.setMultiple(descriptor.isMultiple());
                        prop.setType(descriptor.getType());
                    } catch (RepositoryException e) {
                        logger.error(
                                "Error retrieving property descriptor for node type '"
                                        + prop.getNodeType()
                                        + "' and property name '"
                                        + prop.getName() + "'", e);
                    }

                }
                props.add(prop);
            }
        }

    }

    @SuppressWarnings("unchecked")
    private static boolean isRequestDataPresent(HttpServletRequest request) {
        boolean present = false;
        Enumeration<String> params = request.getParameterNames();
        while (params.hasMoreElements()) {
            if (params.nextElement().startsWith(PARAM_NAME_PREFIX)) {
                present = true;
                break;
            }
        }

        return present;
    }
}
TOP

Related Classes of org.jahia.services.search.SearchCriteriaFactory

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.