Changeset 32656 for main/trunk


Ignore:
Timestamp:
2018-12-04T14:40:38+13:00 (5 years ago)
Author:
kjdon
Message:

oh dearsvn diff service/CrossCollectionSearch.java I mistakenly deleted half this file and then committed. I have got back the missing parts. hope I hadn't had any changes in this part of the file...

File:
1 edited

Legend:

Unmodified
Added
Removed
  • main/trunk/greenstone3/src/java/org/greenstone/gsdl3/service/CrossCollectionSearch.java

    r32655 r32656  
    1 
     1/*
     2 *    CrossCollectionSearch.java
     3 *    Copyright (C) 2002 New Zealand Digital Library, http://www.nzdl.org
     4 *
     5 *    This program is free software; you can redistribute it and/or modify
     6 *    it under the terms of the GNU General Public License as published by
     7 *    the Free Software Foundation; either version 2 of the License, or
     8 *    (at your option) any later version.
     9 *
     10 *    This program is distributed in the hope that it will be useful,
     11 *    but WITHOUT ANY WARRANTY; without even the implied warranty of
     12 *    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     13 *    GNU General Public License for more details.
     14 *
     15 *    You should have received a copy of the GNU General Public License
     16 *    along with this program; if not, write to the Free Software
     17 *    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
     18 */
     19package org.greenstone.gsdl3.service;
     20
     21import java.util.ArrayList;
     22import java.util.HashMap;
     23import java.util.Iterator;
     24import java.util.Map;
     25import java.util.Set;
     26
     27import org.apache.log4j.Logger;
     28import org.greenstone.gsdl3.util.GSPath;
     29import org.greenstone.gsdl3.util.GSXML;
     30import org.greenstone.gsdl3.util.UserContext;
     31import org.greenstone.gsdl3.util.XMLConverter;
     32import org.w3c.dom.Document;
     33import org.w3c.dom.Element;
     34import org.w3c.dom.Node;
     35import org.w3c.dom.NodeList;
     36
     37/**
     38 * This ServiceRack gets specified in siteConfig.xml. So it is loaded by the MessaegRouter, and two services get activated: TextQuery, DocumentMetadataRetrieve.
     39These are located at MR level, not inside a collection. QueryAction will send messages to "TextQuery", rather than eg "mgppdemo/TextQuery".
     40These two services will requery the MR for search results/document metadata based on collections or documents listed.
     41 */
     42
     43public class CrossCollectionSearch extends ServiceRack
     44{
     45
     46    static Logger logger = Logger.getLogger(org.greenstone.gsdl3.service.CrossCollectionSearch.class.getName());
     47    protected static final String QUERY_PARAM = "query";
     48    protected static final String COLLECTION_PARAM = "collection";
     49    protected static final String GROUP_PARAM = "group";
     50  protected static final String MAXDOCS_PARAM = "maxDocs"; // matches standard maxDocs, but in this case, means max docs per collection
     51  protected static final String HITS_PER_PAGE_PARAM = "hitsPerPage";
     52  protected static final String MAXDOCS_DEFAULT = "20";
     53    // the services on offer - these proxy the actual collection ones
     54    protected static final String TEXT_QUERY_SERVICE = "TextQuery";
     55    protected static final String DOCUMENT_METADATA_RETRIEVE_SERVICE = "DocumentMetadataRetrieve";
     56
     57    protected String[] coll_ids_list = null;
     58    protected String[] coll_ids_list_no_all = null;
     59    // maps lang to coll names list
     60    protected HashMap<String, String[]> coll_names_map = null;
     61
     62    //protected String[] coll_names_list = null;
     63
     64    /** constructor */
     65    public CrossCollectionSearch()
     66    {
     67    }
     68
     69    public boolean configure(Element info, Element extra_info)
     70    {
     71        // any parameters? colls to include??
     72        logger.info("Configuring CrossCollectionSearch...");
     73        // query service
     74        Element ccs_service = this.desc_doc.createElement(GSXML.SERVICE_ELEM);
     75        ccs_service.setAttribute(GSXML.TYPE_ATT, GSXML.SERVICE_TYPE_QUERY);
     76        ccs_service.setAttribute(GSXML.NAME_ATT, TEXT_QUERY_SERVICE);
     77        this.short_service_info.appendChild(ccs_service);
     78
     79        // metadata service
     80        Element dmr_service = this.desc_doc.createElement(GSXML.SERVICE_ELEM);
     81        dmr_service.setAttribute(GSXML.TYPE_ATT, GSXML.SERVICE_TYPE_RETRIEVE);
     82        dmr_service.setAttribute(GSXML.NAME_ATT, DOCUMENT_METADATA_RETRIEVE_SERVICE);
     83        this.short_service_info.appendChild(dmr_service);
     84
     85
     86        // what params do we want saved in the session?
     87        this.save_params.add(QUERY_PARAM);
     88        this.save_params.add(COLLECTION_PARAM);
     89        this.save_params.add(GROUP_PARAM);
     90        this.save_params.add(MAXDOCS_PARAM);
     91        this.save_params.add(HITS_PER_PAGE_PARAM);
     92       
     93        // get any format info
     94        Element format_info = (Element) GSXML.getChildByTagName(info, GSXML.FORMAT_ELEM);
     95        if (format_info != null)
     96        {
     97            this.format_info_map.put(TEXT_QUERY_SERVICE, this.desc_doc.importNode(format_info, true));
     98        }
     99        else
     100        {
     101            // add in a default format statement
     102          //"xmlns:gsf='" + GSXML.GSF_NAMESPACE + "' xmlns:xsl='" + GSXML.XSL_NAMESPACE + "
     103          String format_string = "<format "+GSXML.STD_NAMESPACES_ATTS + "><gsf:template match='documentNode'><td><a><xsl:attribute name='href'>?a=d&amp;c=<xsl:value-of select='@collection'/>&amp;d=<xsl:value-of select='@nodeID'/><xsl:if test=\"@nodeType='leaf'\">&amp;sib=1</xsl:if>&amp;dt=<xsl:value-of select='@docType'/>&amp;p.a=q&amp;p.s=" + TEXT_QUERY_SERVICE + "&amp;p.c=";
     104            if (this.cluster_name != null)
     105            {
     106                format_string += this.cluster_name;
     107            }
     108            format_string += "</xsl:attribute><gsf:icon/></a></td><td><gsf:metadata name='Title'/> (<xsl:value-of select='@collection'/>) </td></gsf:template></format>";
     109            this.format_info_map.put(TEXT_QUERY_SERVICE, this.desc_doc.importNode(this.converter.getDOM(format_string).getDocumentElement(), true));
     110        }
     111        return true;
     112    }
     113
     114  protected Element getServiceDescription(Document doc, String service, String lang, String subset)
     115    {
     116        if (service.equals(TEXT_QUERY_SERVICE))
     117        {
     118
     119            Element ccs_service = doc.createElement(GSXML.SERVICE_ELEM);
     120            ccs_service.setAttribute(GSXML.TYPE_ATT, GSXML.SERVICE_TYPE_QUERY);
     121            ccs_service.setAttribute(GSXML.NAME_ATT, TEXT_QUERY_SERVICE);
     122
     123            // display info
     124            if (subset == null || subset.equals(GSXML.DISPLAY_TEXT_ELEM + GSXML.LIST_MODIFIER))
     125            {
     126                ccs_service.appendChild(GSXML.createDisplayTextElement(doc, GSXML.DISPLAY_TEXT_NAME, getTextString(TEXT_QUERY_SERVICE + ".name", lang)));
     127                ccs_service.appendChild(GSXML.createDisplayTextElement(doc, GSXML.DISPLAY_TEXT_SUBMIT, getTextString(TEXT_QUERY_SERVICE + ".submit", lang)));
     128                ccs_service.appendChild(GSXML.createDisplayTextElement(doc, GSXML.DISPLAY_TEXT_DESCRIPTION, getTextString(TEXT_QUERY_SERVICE + ".description", lang)));
     129            }
     130            // param info
     131            if (subset == null || subset.equals(GSXML.PARAM_ELEM + GSXML.LIST_MODIFIER))
     132            {
     133                Element param_list = doc.createElement(GSXML.PARAM_ELEM + GSXML.LIST_MODIFIER);
     134                // collection list
     135                if (coll_ids_list == null)
     136                {
     137                    initCollectionList(lang);
     138                }
     139                if (!coll_names_map.containsKey(lang))
     140                {
     141                    addCollectionNames(lang);
     142                }
     143                Element param = GSXML.createParameterDescription(doc, COLLECTION_PARAM, getTextString("param." + COLLECTION_PARAM, lang), GSXML.PARAM_TYPE_ENUM_MULTI, "all", coll_ids_list, coll_names_map.get(lang));
     144                param_list.appendChild(param);
     145                // max docs param
     146                param = GSXML.createParameterDescription(doc, MAXDOCS_PARAM, getTextString("param." + MAXDOCS_PARAM, lang), GSXML.PARAM_TYPE_INTEGER, MAXDOCS_DEFAULT, null, null);
     147                param_list.appendChild(param);
     148                // query param
     149                param = GSXML.createParameterDescription(doc, QUERY_PARAM, getTextString("param." + QUERY_PARAM, lang), GSXML.PARAM_TYPE_STRING, null, null, null);
     150                param_list.appendChild(param);
     151                ccs_service.appendChild(param_list);
     152            }
     153
     154            logger.debug("service description=" + this.converter.getPrettyString(ccs_service));
     155            return ccs_service;
     156        }
     157        // these ones are probably never called, but put them here just in case
     158        Element service_elem = doc.createElement(GSXML.SERVICE_ELEM);
     159        service_elem.setAttribute(GSXML.TYPE_ATT, GSXML.SERVICE_TYPE_RETRIEVE);
     160        service_elem.setAttribute(GSXML.NAME_ATT, service);
     161        return service_elem;
     162
     163    }
     164
     165    protected Element processTextQuery(Element request)
     166    {
     167        // Create a new (empty) result message
     168      Document result_doc = XMLConverter.newDOM();
     169        Element result = result_doc.createElement(GSXML.RESPONSE_ELEM);
     170        result.setAttribute(GSXML.FROM_ATT, TEXT_QUERY_SERVICE);
     171        result.setAttribute(GSXML.TYPE_ATT, GSXML.REQUEST_TYPE_PROCESS);
     172
     173        UserContext userContext = new UserContext(request);
     174
     175        // Get the parameters of the request
     176        Element param_list = (Element) GSXML.getChildByTagName(request, GSXML.PARAM_ELEM + GSXML.LIST_MODIFIER);
     177        if (param_list == null)
     178        {
     179            logger.error("TextQuery request had no paramList.");
     180            return result; // Return the empty result
     181        }
     182        // get the collection list
     183        String[] colls_list = coll_ids_list_no_all;
     184        Element coll_param = GSXML.getNamedElement(param_list, GSXML.PARAM_ELEM, GSXML.NAME_ATT, COLLECTION_PARAM);
     185        if (coll_param != null)
     186        {
     187            String coll_list = GSXML.getValue(coll_param);
     188            if (!coll_list.equals("all") && !coll_list.equals(""))
     189            {
     190                colls_list = coll_list.split(",");
     191            }
     192        }
     193           
     194        colls_list = mergeGroups(userContext, param_list, colls_list);
     195       
     196        String maxdocs = MAXDOCS_DEFAULT;
     197        Element maxdocs_param = GSXML.getNamedElement(param_list, GSXML.PARAM_ELEM, GSXML.NAME_ATT, MAXDOCS_PARAM);
     198        if (maxdocs_param != null) {
     199          maxdocs = GSXML.getValue(maxdocs_param);
     200        }
     201       
     202        Document msg_doc = XMLConverter.newDOM();
     203        Element query_message = msg_doc.createElement(GSXML.MESSAGE_ELEM);
     204        // we are sending the same request to each collection - build up the to
     205        // attribute for the request
     206        StringBuffer to_att = new StringBuffer();
     207        for (int i = 0; i < colls_list.length; i++)
     208        {
     209            if (i > 0)
     210            {
     211                to_att.append(",");
     212            }
     213            to_att.append(GSPath.appendLink(colls_list[i], "TextQuery"));
     214
     215        }
     216        // send the query to all colls
     217        Element query_request = GSXML.createBasicRequest(msg_doc, GSXML.REQUEST_TYPE_PROCESS, to_att.toString(), userContext);
     218        query_message.appendChild(query_request);
     219        // should we add params individually?
     220        Element new_param_list = msg_doc.createElement(GSXML.PARAM_ELEM + GSXML.LIST_MODIFIER);
     221        query_request.appendChild(new_param_list);
     222        new_param_list.appendChild(msg_doc.importNode(GSXML.getNamedElement(param_list, GSXML.PARAM_ELEM, GSXML.NAME_ATT, QUERY_PARAM), true));
     223
     224        // for cross coll search, we only want maxdocs from each collection
     225        // some colls use maxdocs, some use hits per page so lets send both
     226        new_param_list.appendChild(GSXML.createParameter(msg_doc, MAXDOCS_PARAM, maxdocs));
     227        new_param_list.appendChild(GSXML.createParameter(msg_doc, HITS_PER_PAGE_PARAM, maxdocs));
     228        Element query_result = (Element) this.router.process(query_message);
     229        // create the doc list for the response
     230        Element doc_node_list = result_doc.createElement(GSXML.DOC_NODE_ELEM + GSXML.LIST_MODIFIER);
     231        result.appendChild(doc_node_list);
     232        Element result_snippet_list = result_doc.createElement(GSXML.HL_SNIPPET_ELEM + GSXML.LIST_MODIFIER);
     233        result.appendChild(result_snippet_list);
     234
     235        NodeList responses = query_result.getElementsByTagName(GSXML.RESPONSE_ELEM);
     236        int num_docs = 0;
     237        for (int k = 0; k < responses.getLength(); k++)
     238        {
     239            String coll_name = GSPath.removeLastLink(((Element) responses.item(k)).getAttribute(GSXML.FROM_ATT));
     240            NodeList nodes = ((Element) responses.item(k)).getElementsByTagName(GSXML.DOC_NODE_ELEM);
     241            if (nodes == null || nodes.getLength() == 0)
     242                continue;
     243            num_docs += nodes.getLength();
     244            Element last_node = null;
     245            Element this_node = null;
     246            for (int n = 0; n < nodes.getLength(); n++)
     247            {
     248                this_node = (Element) nodes.item(n);
     249                this_node.setAttribute("collection", coll_name);
     250   
     251                if (k == 0)
     252                {
     253
     254                    doc_node_list.appendChild(result_doc.importNode(this_node, true));
     255                }
    2256                else
    3257                {
     
    11265            }
    12266            NodeList hl_snippet_list = ((Element) responses.item(k)).getElementsByTagName(GSXML.HL_SNIPPET_ELEM);
    13             if (hl_snippet_list != null) {
    14               for (int hls = 0; hls < hl_snippet_list.getLength(); hls++) {
     267            if (hl_snippet_list != null){
     268              for (int hls = 0; hls < hl_snippet_list.getLength(); hls++){
    15269                Element this_hls = (Element) hl_snippet_list.item(hls);
    16270                this_hls.setAttribute("collection", coll_name);
    17271                result_snippet_list.appendChild(result_doc.importNode(this_hls, true));
    18               }
    19             }
    20            
     272            }
     273        }
     274
    21275        }
    22276        // just send back num docs returned. Too hard to work out number of matches etc as each index type
     
    326580                String value = groupParam.getAttribute(GSXML.VALUE_ATT);
    327581                String group = collectionParam.substring(prefix.length() - 1 );
    328                 group=group.replace('.', '/'); // we use . instead of / in args
    329                 value += "," + group;
     582                group=group.replace('.', '/'); // we use . instead of / in args
     583                value += "," + group;
    330584                groupParam.setAttribute(GSXML.VALUE_ATT, value);
    331585            }
Note: See TracChangeset for help on using the changeset viewer.