/** * Licensed to the Apache Software Foundation (ASF) under one or more * contributor license agreements. See the NOTICE file distributed with * this work for additional information regarding copyright ownership. * The ASF licenses this file to You under the Apache License, Version 2.0 * (the "License"); you may not use this file except in compliance with * the License. You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package org.apache.solr.client.solrj.util; import java.io.IOException; import java.io.StringWriter; import java.io.Writer; import java.net.URLEncoder; import java.text.DateFormat; import java.text.ParseException; import java.util.ArrayList; import java.util.Collection; import java.util.Date; import java.util.Iterator; import java.util.TimeZone; import java.nio.ByteBuffer; import org.apache.commons.httpclient.util.DateParseException; import org.apache.solr.common.SolrDocument; import org.apache.solr.common.SolrInputDocument; import org.apache.solr.common.SolrInputField; import org.apache.solr.common.params.SolrParams; import org.apache.solr.common.util.*; /** * TODO? should this go in common? * * @version $Id: ClientUtils.java 948008 2010-05-25 11:42:38Z koji $ * @since solr 1.3 */ public class ClientUtils { // Standard Content types public static final String TEXT_XML = "text/xml; charset=utf-8"; /** * Take a string and make it an iterable ContentStream */ public static Collection<ContentStream> toContentStreams( final String str, final String contentType ) { if( str == null ) return null; ArrayList<ContentStream> streams = new ArrayList<ContentStream>( 1 ); ContentStreamBase ccc = new ContentStreamBase.StringStream( str ); ccc.setContentType( contentType ); streams.add( ccc ); return streams; } /** * @param d SolrDocument to convert * @return a SolrInputDocument with the same fields and values as the * SolrDocument. All boosts are 1.0f */ public static SolrInputDocument toSolrInputDocument( SolrDocument d ) { SolrInputDocument doc = new SolrInputDocument(); for( String name : d.getFieldNames() ) { doc.addField( name, d.getFieldValue(name), 1.0f ); } return doc; } /** * @param d SolrInputDocument to convert * @return a SolrDocument with the same fields and values as the SolrInputDocument */ public static SolrDocument toSolrDocument( SolrInputDocument d ) { SolrDocument doc = new SolrDocument(); for( SolrInputField field : d ) { doc.setField( field.getName(), field.getValue() ); } return doc; } //------------------------------------------------------------------------ //------------------------------------------------------------------------ public static void writeXML( SolrInputDocument doc, Writer writer ) throws IOException { writer.write("<doc boost=\""+doc.getDocumentBoost()+"\">"); for( SolrInputField field : doc ) { float boost = field.getBoost(); String name = field.getName(); for( Object v : field ) { if (v instanceof Date) { v = DateUtil.getThreadLocalDateFormat().format( (Date)v ); }else if (v instanceof byte[]) { byte[] bytes = (byte[]) v; v = Base64.byteArrayToBase64(bytes, 0,bytes.length); } else if (v instanceof ByteBuffer) { ByteBuffer bytes = (ByteBuffer) v; v = Base64.byteArrayToBase64(bytes.array(), bytes.position(),bytes.limit() - bytes.position()); } if( boost != 1.0f ) { XML.writeXML(writer, "field", v.toString(), "name", name, "boost", boost ); } else if (v != null) { XML.writeXML(writer, "field", v.toString(), "name", name ); } // only write the boost for the first multi-valued field // otherwise, the used boost is the product of all the boost values boost = 1.0f; } } writer.write("</doc>"); } public static String toXML( SolrInputDocument doc ) { StringWriter str = new StringWriter(); try { writeXML( doc, str ); } catch( Exception ex ){} return str.toString(); } //--------------------------------------------------------------------------------------- /** * @deprecated Use {@link org.apache.solr.common.util.DateUtil#DEFAULT_DATE_FORMATS} */ public static final Collection<String> fmts = DateUtil.DEFAULT_DATE_FORMATS; /** * Returns a formatter that can be use by the current thread if needed to * convert Date objects to the Internal representation. * @throws ParseException * @throws DateParseException * * @deprecated Use {@link org.apache.solr.common.util.DateUtil#parseDate(String)} */ public static Date parseDate( String d ) throws ParseException, DateParseException { return DateUtil.parseDate(d); } /** * Returns a formatter that can be use by the current thread if needed to * convert Date objects to the Internal representation. * * @deprecated use {@link org.apache.solr.common.util.DateUtil#getThreadLocalDateFormat()} */ public static DateFormat getThreadLocalDateFormat() { return DateUtil.getThreadLocalDateFormat(); } /** * @deprecated Use {@link org.apache.solr.common.util.DateUtil#UTC}. */ public static TimeZone UTC = DateUtil.UTC; /** * See: <a href="http://lucene.apache.org/java/docs/nightly/queryparsersyntax.html#Escaping%20Special%20Characters">Escaping Special Characters</a> */ public static String escapeQueryChars(String s) { StringBuilder sb = new StringBuilder(); for (int i = 0; i < s.length(); i++) { char c = s.charAt(i); // These characters are part of the query syntax and must be escaped if (c == '\\' || c == '+' || c == '-' || c == '!' || c == '(' || c == ')' || c == ':' || c == '^' || c == '[' || c == ']' || c == '\"' || c == '{' || c == '}' || c == '~' || c == '*' || c == '?' || c == '|' || c == '&' || c == ';' || Character.isWhitespace(c)) { sb.append('\\'); } sb.append(c); } return sb.toString(); } public static String toQueryString( SolrParams params, boolean xml ) { StringBuilder sb = new StringBuilder(128); try { String amp = xml ? "&" : "&"; boolean first=true; Iterator<String> names = params.getParameterNamesIterator(); while( names.hasNext() ) { String key = names.next(); String[] valarr = params.getParams( key ); if( valarr == null ) { sb.append( first?"?":amp ); sb.append(key); first=false; } else { for (String val : valarr) { sb.append( first? "?":amp ); sb.append(key); if( val != null ) { sb.append('='); sb.append( URLEncoder.encode( val, "UTF-8" ) ); } first=false; } } } } catch (IOException e) {throw new RuntimeException(e);} // can't happen return sb.toString(); } }