/* * Copyright (2012) Schibsted ASA * This file is part of Possom. * * Possom is free software: you can redistribute it and/or modify * it under the terms of the GNU Lesser General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * Possom 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 Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public License * along with Possom. If not, see <http://www.gnu.org/licenses/>. */ package no.sesat.search.mode.command; import java.io.BufferedReader; import java.io.IOException; import java.io.Serializable; import java.net.SocketTimeoutException; import java.text.MessageFormat; import java.util.List; import no.sesat.search.result.BasicResultItem; import no.sesat.search.result.BasicResultList; import no.sesat.search.result.ResultItem; import no.sesat.search.result.ResultList; import net.sf.json.JSONSerializer; import no.sesat.search.mode.config.GoogleCommandConfig; import org.apache.commons.beanutils.DynaBean; import org.apache.commons.beanutils.DynaProperty; import org.apache.log4j.Logger; /** * @xxx very little has been done on this * @todo extract out a AbstractJsonSearchCommand * @see GoogleCommandConfig * @version $Id$ */ public class GoogleSearchCommand extends AbstractRestfulSearchCommand { // Constants ----------------------------------------------------- private static final Logger LOG = Logger.getLogger(GoogleSearchCommand.class); private static final String COMMAND_URL_QUERY = "?q={0}&rsz={1}&start={2}&v=1.0"; // Static -------------------------------------------------------- // Attributes ---------------------------------------------------- private final Context cxt; private final GoogleCommandConfig conf; // Constructors ------------------------------------------------- public GoogleSearchCommand(final Context cxt) { super(cxt); this.cxt = cxt; conf = (GoogleCommandConfig) cxt.getSearchConfiguration(); final String commandPath = cxt.getDataModel().getSite().getSiteConfiguration().getProperty(conf.getPath()); setRestful( new AbstractRestful(cxt) { @Override public String createRequestURL() { return MessageFormat.format( commandPath + COMMAND_URL_QUERY, cxt.getDataModel().getQuery().getUtf8UrlEncoded(), conf.getLargeResults() ? "large" : "small", GoogleSearchCommand.this.getOffset()); } }); } // Public -------------------------------------------------------- @Override public ResultList<ResultItem> execute() { final ResultList<ResultItem> result = new BasicResultList<ResultItem>(); final BufferedReader reader; try { reader = getRestful().getHttpReader("UTF8"); if(null != reader) { final StringBuilder builder = new StringBuilder(); String line; while(null != (line = reader.readLine())){ builder.append(line); } final DynaBean bean = (DynaBean) JSONSerializer.toJava(JSONSerializer.toJSON(builder.toString())); final DynaBean data = (DynaBean)bean.get("responseData"); final String totalResults = ((DynaBean)data.get("cursor")).get("estimatedResultCount").toString(); result.setHitCount(Integer.parseInt(totalResults)); final List<DynaBean> results = (List<DynaBean>)data.get("results"); for(DynaBean r : results) { result.addResult(createItem(r)); } } } catch (SocketTimeoutException ste) { LOG.error(getSearchConfiguration().getName() + " --> " + ste.getMessage()); return new BasicResultList<ResultItem>(); } catch (IOException ex) { throw new SearchCommandException(ex); } return result; } // Protected -------------------------------------------------------- protected ResultItem createItem(final DynaBean entry) { ResultItem resItem = new BasicResultItem(); final DynaProperty[] descriptors = entry.getDynaClass().getDynaProperties(); for(DynaProperty d : descriptors){ if(entry.get(d.getName()) instanceof Serializable){ resItem = resItem.addObjectField(d.getName(), (Serializable) entry.get(d.getName())); } } return resItem; } @Override protected int getOffset() { return super.getOffset(); } // Private -------------------------------------------------------- }