Index: solr/core/src/java/org/apache/solr/search/SolrQueryParser.java =================================================================== --- solr/core/src/java/org/apache/solr/search/SolrQueryParser.java (Revision 1227548) +++ solr/core/src/java/org/apache/solr/search/SolrQueryParser.java (Arbeitskopie) @@ -19,14 +19,16 @@ import java.util.HashMap; import java.util.Map; -import java.util.Map.Entry; +import org.apache.lucene.analysis.Analyzer; import org.apache.lucene.index.Term; import org.apache.lucene.queryParser.ParseException; import org.apache.lucene.queryParser.QueryParser; -import org.apache.lucene.search.*; -import org.apache.lucene.analysis.Analyzer; -import org.apache.solr.analysis.*; +import org.apache.lucene.search.Query; +import org.apache.solr.analysis.ReversedWildcardFilter; +import org.apache.solr.analysis.ReversedWildcardFilterFactory; +import org.apache.solr.analysis.TokenFilterFactory; +import org.apache.solr.analysis.TokenizerChain; import org.apache.solr.common.SolrException; import org.apache.solr.schema.FieldType; import org.apache.solr.schema.IndexSchema; @@ -176,10 +178,7 @@ checkNullField(field); SchemaField sf = schema.getField(field); - return sf.getType().getRangeQuery(parser, sf, - "*".equals(part1) ? null : part1, - "*".equals(part2) ? null : part2, - inclusive, inclusive); + return sf.getType().getRangeQuery(parser, sf, part1, part2, inclusive, inclusive); } @Override Index: lucene/contrib/queryparser/src/java/org/apache/lucene/queryParser/analyzing/AnalyzingQueryParser.java =================================================================== Index: lucene/src/java/org/apache/lucene/queryParser/QueryParser.java =================================================================== --- lucene/src/java/org/apache/lucene/queryParser/QueryParser.java (Revision 1227548) +++ lucene/src/java/org/apache/lucene/queryParser/QueryParser.java (Arbeitskopie) @@ -16,24 +16,23 @@ import org.apache.lucene.analysis.Analyzer; import org.apache.lucene.analysis.CachingTokenFilter; import org.apache.lucene.analysis.TokenStream; -import org.apache.lucene.analysis.tokenattributes.PositionIncrementAttribute; import org.apache.lucene.analysis.tokenattributes.CharTermAttribute; +import org.apache.lucene.analysis.tokenattributes.PositionIncrementAttribute; import org.apache.lucene.document.DateField; import org.apache.lucene.document.DateTools; import org.apache.lucene.index.Term; import org.apache.lucene.search.BooleanClause; import org.apache.lucene.search.BooleanQuery; import org.apache.lucene.search.FuzzyQuery; -import org.apache.lucene.search.MultiTermQuery; import org.apache.lucene.search.MatchAllDocsQuery; import org.apache.lucene.search.MultiPhraseQuery; +import org.apache.lucene.search.MultiTermQuery; import org.apache.lucene.search.PhraseQuery; import org.apache.lucene.search.PrefixQuery; import org.apache.lucene.search.Query; -import org.apache.lucene.search.TermRangeQuery; import org.apache.lucene.search.TermQuery; +import org.apache.lucene.search.TermRangeQuery; import org.apache.lucene.search.WildcardQuery; -import org.apache.lucene.util.BytesRef; import org.apache.lucene.util.Version; import org.apache.lucene.util.VirtualMethod; @@ -764,7 +763,8 @@ /** - * @exception ParseException throw in overridden method to disallow + * + * @exception org.apache.lucene.queryParser.ParseException */ protected Query getRangeQuery(String field, String part1, @@ -772,13 +772,28 @@ boolean inclusive) throws ParseException { if (lowercaseExpandedTerms) { - part1 = part1.toLowerCase(); - part2 = part2.toLowerCase(); + part1 = part1==null ? null : part1.toLowerCase(); + part2 = part2==null ? null : part2.toLowerCase(); } - try { + + DateFormat df = DateFormat.getDateInstance(DateFormat.SHORT, locale); df.setLenient(true); + DateTools.Resolution resolution = getDateResolution(field); + + try { Date d1 = df.parse(part1); + if (resolution == null) { + // no default or field specific date resolution has been set, + // use deprecated DateField to maintain compatibility with + // pre-1.9 Lucene versions. + part1 = DateField.dateToString(d1); + } else { + part1 = DateTools.dateToString(d1, resolution); + } + } catch (Exception e) { } + + try { Date d2 = df.parse(part2); if (inclusive) { // The user can only specify the date, not the time, so make sure @@ -792,19 +807,15 @@ cal.set(Calendar.MILLISECOND, 999); d2 = cal.getTime(); } - DateTools.Resolution resolution = getDateResolution(field); if (resolution == null) { // no default or field specific date resolution has been set, // use deprecated DateField to maintain compatibility with // pre-1.9 Lucene versions. - part1 = DateField.dateToString(d1); part2 = DateField.dateToString(d2); } else { - part1 = DateTools.dateToString(d1, resolution); part2 = DateTools.dateToString(d2, resolution); } - } - catch (Exception e) { } + } catch (Exception e) { } return newRangeQuery(field, part1, part2, inclusive); } @@ -1501,13 +1512,19 @@ jj_la1[15] = jj_gen; ; } + boolean startOpen=false; + boolean endOpen=false; if (goop1.kind == RANGEIN_QUOTED) { goop1.image = goop1.image.substring(1, goop1.image.length()-1); + } else if ("*".equals(goop1.image)) { + startOpen=true; } if (goop2.kind == RANGEIN_QUOTED) { goop2.image = goop2.image.substring(1, goop2.image.length()-1); + } else if ("*".equals(goop2.image)) { + endOpen=true; } - q = getRangeQuery(field, discardEscapeChar(goop1.image), discardEscapeChar(goop2.image), true); + q = getRangeQuery(field, startOpen ? null : discardEscapeChar(goop1.image), endOpen ? null : discardEscapeChar(goop2.image), true); break; case RANGEEX_START: jj_consume_token(RANGEEX_START); Index: lucene/src/java/org/apache/lucene/queryParser/QueryParser.jj =================================================================== --- lucene/src/java/org/apache/lucene/queryParser/QueryParser.jj (Revision 1227548) +++ lucene/src/java/org/apache/lucene/queryParser/QueryParser.jj (Arbeitskopie) @@ -1381,13 +1381,19 @@ ) [ boost= ] { + boolean startOpen=false; + boolean endOpen=false; if (goop1.kind == RANGEIN_QUOTED) { goop1.image = goop1.image.substring(1, goop1.image.length()-1); + } else if ("*".equals(goop1.image)) { + startOpen=true; } if (goop2.kind == RANGEIN_QUOTED) { goop2.image = goop2.image.substring(1, goop2.image.length()-1); + } else if ("*".equals(goop2.image)) { + endOpen=true; } - q = getRangeQuery(field, discardEscapeChar(goop1.image), discardEscapeChar(goop2.image), true); + q = getRangeQuery(field, startOpen ? null : discardEscapeChar(goop1.image), endOpen ? null : discardEscapeChar(goop2.image), true); } | ( ( goop1=|goop1= ) [ ] ( goop2=|goop2= ) Index: lucene/src/java/org/apache/lucene/search/TermRangeQuery.java =================================================================== --- lucene/src/java/org/apache/lucene/search/TermRangeQuery.java (Revision 1227548) +++ lucene/src/java/org/apache/lucene/search/TermRangeQuery.java (Arbeitskopie) @@ -145,9 +145,9 @@ buffer.append(":"); } buffer.append(includeLower ? '[' : '{'); - buffer.append(lowerTerm != null ? lowerTerm : "*"); + buffer.append(lowerTerm != null ? ("*".equals(lowerTerm) ? "\\*" : lowerTerm) : "*"); buffer.append(" TO "); - buffer.append(upperTerm != null ? upperTerm : "*"); + buffer.append(upperTerm != null ? ("*".equals(upperTerm) ? "\\*" : upperTerm) : "*"); buffer.append(includeUpper ? ']' : '}'); buffer.append(ToStringUtils.boost(getBoost())); return buffer.toString(); Index: lucene/src/test-framework/java/org/apache/lucene/queryParser/QueryParserTestBase.java =================================================================== --- lucene/src/test-framework/java/org/apache/lucene/queryParser/QueryParserTestBase.java (Revision 1227548) +++ lucene/src/test-framework/java/org/apache/lucene/queryParser/QueryParserTestBase.java (Arbeitskopie) @@ -524,6 +524,11 @@ assertQueryEquals("[ a TO z] AND bar", null, "+[a TO z] +bar"); assertQueryEquals("( bar blar { a TO z}) ", null, "bar blar {a TO z}"); assertQueryEquals("gack ( bar blar { a TO z}) ", null, "gack (bar blar {a TO z})"); + + assertQueryEquals("[* TO Z]",null,"[* TO z]"); + assertQueryEquals("[A TO *]",null,"[a TO *]"); + assertQueryEquals("[* TO *]",null,"[* TO *]"); + assertQueryEquals("[\\* TO \"*\"]",null,"[\\* TO \\*]"); } public void testFarsiRangeCollating() throws Exception {