You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@lucene.apache.org by mk...@apache.org on 2019/01/27 18:45:56 UTC
[lucene-solr] branch master updated: LUCENE-8640: date range syntax
validation
This is an automated email from the ASF dual-hosted git repository.
mkhl pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/lucene-solr.git
The following commit(s) were added to refs/heads/master by this push:
new 8e69d12 LUCENE-8640: date range syntax validation
8e69d12 is described below
commit 8e69d12dd7e2b6d2341322e4ac7e5c33b789507a
Author: Mikhail Khludnev <mk...@apache.org>
AuthorDate: Sat Jan 26 23:25:41 2019 +0300
LUCENE-8640: date range syntax validation
---
lucene/CHANGES.txt | 2 +
.../spatial/prefix/tree/DateRangePrefixTree.java | 46 ++++++++++++++++++----
.../prefix/tree/DateRangePrefixTreeTest.java | 43 ++++++++++++++++++++
3 files changed, 84 insertions(+), 7 deletions(-)
diff --git a/lucene/CHANGES.txt b/lucene/CHANGES.txt
index 04f4960..fd35d8e 100644
--- a/lucene/CHANGES.txt
+++ b/lucene/CHANGES.txt
@@ -324,6 +324,8 @@ Improvements
* LUCENE-8527: Upgrade JFlex dependency to 1.7.0; in StandardTokenizer and UAX29URLEmailTokenizer,
increase supported Unicode version from 6.3 to 9.0, and support Unicode UTS#51 v11.0 Emoji tokenization.
+* LUCENE-8640: Date Range format validation (Lucky Sharma, David Smiley via Mikhail Khludnev)
+
Optimizations
* LUCENE-8552: FieldInfos.getMergedFieldInfos no longer does any merging if there is <= 1 segment.
diff --git a/lucene/spatial-extras/src/java/org/apache/lucene/spatial/prefix/tree/DateRangePrefixTree.java b/lucene/spatial-extras/src/java/org/apache/lucene/spatial/prefix/tree/DateRangePrefixTree.java
index cc47358..31e0a00 100644
--- a/lucene/spatial-extras/src/java/org/apache/lucene/spatial/prefix/tree/DateRangePrefixTree.java
+++ b/lucene/spatial-extras/src/java/org/apache/lucene/spatial/prefix/tree/DateRangePrefixTree.java
@@ -446,6 +446,7 @@ public class DateRangePrefixTree extends NumberRangePrefixTree {
if (str.equals("*"))
return cal;
int offset = 0;//a pointer
+ int parsedVal = 0;
try {
//year & era:
int lastOffset = str.charAt(str.length()-1) == 'Z' ? str.length() - 1 : str.length();
@@ -463,41 +464,72 @@ public class DateRangePrefixTree extends NumberRangePrefixTree {
// The str.substring()'s hopefully get optimized to be stack-allocated.
//month:
- cal.set(Calendar.MONTH, Integer.parseInt(str.substring(offset, offset+2)) - 1);//starts at 0
+ parsedVal = parseAndCheck( str, offset, 1, 12);
+ cal.set(Calendar.MONTH, parsedVal - 1);//starts at 0
offset += 3;
if (lastOffset < offset)
return cal;
//day:
- cal.set(Calendar.DAY_OF_MONTH, Integer.parseInt(str.substring(offset, offset+2)));
+ checkDelimeter(str, offset-1, '-');
+
+ parsedVal = parseAndCheck( str, offset, 1, 31);
+ cal.set(Calendar.DAY_OF_MONTH, parsedVal);
offset += 3;
if (lastOffset < offset)
return cal;
+ checkDelimeter(str, offset-1, 'T');
//hour:
- cal.set(Calendar.HOUR_OF_DAY, Integer.parseInt(str.substring(offset, offset+2)));
+
+ parsedVal = parseAndCheck( str, offset, 0, 24);
+ cal.set(Calendar.HOUR_OF_DAY, parsedVal);
offset += 3;
if (lastOffset < offset)
return cal;
+ checkDelimeter(str, offset-1, ':');
//minute:
- cal.set(Calendar.MINUTE, Integer.parseInt(str.substring(offset, offset+2)));
+
+ parsedVal = parseAndCheck( str, offset, 1, 60);
+ cal.set(Calendar.MINUTE, parsedVal);
offset += 3;
if (lastOffset < offset)
return cal;
+ checkDelimeter(str, offset-1, ':');
//second:
- cal.set(Calendar.SECOND, Integer.parseInt(str.substring(offset, offset+2)));
+
+ parsedVal = parseAndCheck( str, offset, 1, 60);
+ cal.set(Calendar.SECOND, parsedVal);
offset += 3;
if (lastOffset < offset)
return cal;
+ checkDelimeter(str, offset-1, '.');
//ms:
+
cal.set(Calendar.MILLISECOND, Integer.parseInt(str.substring(offset, offset+3)));
offset += 3;//last one, move to next char
if (lastOffset == offset)
return cal;
} catch (Exception e) {
- ParseException pe = new ParseException("Improperly formatted date: "+str, offset);
+ ParseException pe = new ParseException("Improperly formatted datetime: "+str, offset);
pe.initCause(e);
throw pe;
}
- throw new ParseException("Improperly formatted date: "+str, offset);
+ throw new ParseException("Improperly formatted datetime: "+str, offset);
+ }
+
+ private void checkDelimeter(String str, int offset, char delim) {
+ if (str.charAt(offset) != delim) {
+ throw new IllegalArgumentException("Invalid delimeter: '"+str.charAt(offset)+
+ "', expecting '"+delim+"'");
+ }
+ }
+
+ private int parseAndCheck(String str, int offset, int min, int max) {
+ int val = Integer.parseInt(str.substring(offset, offset+2));
+ if (val < min || val > max) {
+ throw new IllegalArgumentException("Invalid value: "+val+"," +
+ " expecting from "+min+" to "+max+"]");
+ }
+ return val;
}
}
diff --git a/lucene/spatial-extras/src/test/org/apache/lucene/spatial/prefix/tree/DateRangePrefixTreeTest.java b/lucene/spatial-extras/src/test/org/apache/lucene/spatial/prefix/tree/DateRangePrefixTreeTest.java
index d29a192..f9f3d12 100644
--- a/lucene/spatial-extras/src/test/org/apache/lucene/spatial/prefix/tree/DateRangePrefixTreeTest.java
+++ b/lucene/spatial-extras/src/test/org/apache/lucene/spatial/prefix/tree/DateRangePrefixTreeTest.java
@@ -210,4 +210,47 @@ public class DateRangePrefixTreeTest extends LuceneTestCase {
assertEquals("[* TO 2014-09-15]", tree.parseShape("[* TO 2014-09-15]").toString());
}
+ public void testInvalidDateException() throws ParseException {
+
+ expectThrows(ParseException.class, () -> {
+ tree.parseCalendar("2000-11T13");
+ });
+ expectThrows(ParseException.class, () -> {
+ tree.parseCalendar("2000-11-10T13-1");
+ });
+ {
+ String causeMessage = expectThrows(ParseException.class, () -> {
+ tree.parseCalendar("2000-11-10T13Z1");
+ }).getCause().getMessage();
+ assertTrue(causeMessage +" has actual delimeter", causeMessage.contains("Z"));
+ assertTrue(causeMessage +" has expected delimeter",causeMessage.contains(":"));
+ assertFalse(causeMessage +" has no input",causeMessage.contains("2000-11-10"));
+ }
+ expectThrows(ParseException.class, () -> {
+ tree.parseCalendar("2000T13Z");
+ });
+ expectThrows(ParseException.class, () -> {
+ tree.parseCalendar("2000-11T13Z");
+ });
+ {
+ String causeMessage = expectThrows(ParseException.class, () -> {
+ tree.parseCalendar("2000-13-12");
+ }).getCause().getMessage();
+ assertTrue(causeMessage +" has actual value",causeMessage.contains("13"));
+ assertFalse(causeMessage +" has no input",causeMessage.contains("2000-13-12"));
+ }
+ expectThrows(ParseException.class, () -> {
+ tree.parseCalendar("2000-13-41T13Z");
+ });
+ expectThrows(ParseException.class, () -> {
+ tree.parseCalendar("2000-11-12T25Z");
+ });
+ expectThrows(ParseException.class, () -> {
+ tree.parseCalendar("2000-11-12T25:61Z");
+ });
+ expectThrows(ParseException.class, () -> {
+ tree.parseCalendar("2000-11-12T25:14:61Z");
+ });
+ }
+
}
\ No newline at end of file