fix duration parse for `never` and tests
Project: http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/repo Commit: http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/commit/a340dbc3 Tree: http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/tree/a340dbc3 Diff: http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/diff/a340dbc3 Branch: refs/heads/master Commit: a340dbc311c19aef84c6b98d4d91b7776932212a Parents: e92dd1e Author: Alex Heneveld <[email protected]> Authored: Thu Sep 10 13:52:27 2015 +0100 Committer: Alex Heneveld <[email protected]> Committed: Thu Sep 10 14:01:59 2015 +0100 ---------------------------------------------------------------------- .../org/apache/brooklyn/util/time/Duration.java | 4 +- .../org/apache/brooklyn/util/time/Time.java | 98 +++++++++++--------- .../org/apache/brooklyn/util/time/TimeTest.java | 8 +- 3 files changed, 64 insertions(+), 46 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/a340dbc3/utils/common/src/main/java/org/apache/brooklyn/util/time/Duration.java ---------------------------------------------------------------------- diff --git a/utils/common/src/main/java/org/apache/brooklyn/util/time/Duration.java b/utils/common/src/main/java/org/apache/brooklyn/util/time/Duration.java index b11c0b0..e8dee7d 100644 --- a/utils/common/src/main/java/org/apache/brooklyn/util/time/Duration.java +++ b/utils/common/src/main/java/org/apache/brooklyn/util/time/Duration.java @@ -28,6 +28,8 @@ import java.util.concurrent.TimeUnit; import javax.annotation.Nullable; +import org.apache.brooklyn.util.text.Strings; + import com.google.common.base.Function; import com.google.common.base.Preconditions; import com.google.common.base.Stopwatch; @@ -138,7 +140,7 @@ public class Duration implements Comparable<Duration>, Serializable { * also accepts "forever" (and for those who prefer things exceedingly accurate, "practically_forever"). * Also see {@link #of(Object)}. */ public static Duration parse(String textualDescription) { - if (textualDescription==null) return null; + if (Strings.isBlank(textualDescription)) return null; if ("null".equalsIgnoreCase(textualDescription)) return null; if ("forever".equalsIgnoreCase(textualDescription)) return Duration.PRACTICALLY_FOREVER; http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/a340dbc3/utils/common/src/main/java/org/apache/brooklyn/util/time/Time.java ---------------------------------------------------------------------- diff --git a/utils/common/src/main/java/org/apache/brooklyn/util/time/Time.java b/utils/common/src/main/java/org/apache/brooklyn/util/time/Time.java index b1ab8f3..25bd9de 100644 --- a/utils/common/src/main/java/org/apache/brooklyn/util/time/Time.java +++ b/utils/common/src/main/java/org/apache/brooklyn/util/time/Time.java @@ -440,63 +440,73 @@ public class Time { * * @throws NumberFormatException if cannot be parsed (or if null) */ - public static double parseElapsedTimeAsDouble(String timeString) { + public static double parseElapsedTimeAsDouble(final String timeStringOrig) { + String timeString = timeStringOrig; if (timeString==null) throw new NumberFormatException("GeneralHelper.parseTimeString cannot parse a null string"); try { double d = Double.parseDouble(timeString); return d; } catch (NumberFormatException e) { - //look for a type marker - timeString = timeString.trim(); - String s = Strings.getLastWord(timeString).toLowerCase(); - timeString = timeString.substring(0, timeString.length()-s.length()).trim(); - int i=0; - while (s.length()>i) { - char c = s.charAt(i); - if (c=='.' || Character.isDigit(c)) i++; - else break; - } - String num = s.substring(0, i); - if (i==0) { - num = Strings.getLastWord(timeString).toLowerCase(); - timeString = timeString.substring(0, timeString.length()-num.length()).trim(); - } else { - s = s.substring(i); - } - long multiplier = 0; - if (num.length()==0) { - //must be never or something - if (s.equalsIgnoreCase("never") || s.equalsIgnoreCase("off") || s.equalsIgnoreCase("false")) - return -1; - throw new NumberFormatException("unrecognised word '"+s+"' in time string"); - } - if (s.equalsIgnoreCase("ms") || s.equalsIgnoreCase("milli") || s.equalsIgnoreCase("millis") + try { + //look for a type marker + timeString = timeString.trim(); + String s = Strings.getLastWord(timeString).toLowerCase(); + timeString = timeString.substring(0, timeString.length()-s.length()).trim(); + int i=0; + while (s.length()>i) { + char c = s.charAt(i); + if (c=='.' || Character.isDigit(c)) i++; + else break; + } + String num = s.substring(0, i); + if (i==0) { + if (Strings.isNonBlank(timeString)) { + num = Strings.getLastWord(timeString).toLowerCase(); + timeString = timeString.substring(0, timeString.length()-num.length()).trim(); + } + } else { + s = s.substring(i); + } + long multiplier = 0; + if (num.length()==0) { + //must be never or something + // TODO does 'never' work? + if (s.equalsIgnoreCase("never") || s.equalsIgnoreCase("off") || s.equalsIgnoreCase("false")) + return -1; + throw new NumberFormatException("unrecognised word '"+s+"' in time string"); + } + if (s.equalsIgnoreCase("ms") || s.equalsIgnoreCase("milli") || s.equalsIgnoreCase("millis") || s.equalsIgnoreCase("millisec") || s.equalsIgnoreCase("millisecs") || s.equalsIgnoreCase("millisecond") || s.equalsIgnoreCase("milliseconds")) - multiplier = 1; - else if (s.equalsIgnoreCase("s") || s.equalsIgnoreCase("sec") || s.equalsIgnoreCase("secs") + multiplier = 1; + else if (s.equalsIgnoreCase("s") || s.equalsIgnoreCase("sec") || s.equalsIgnoreCase("secs") || s.equalsIgnoreCase("second") || s.equalsIgnoreCase("seconds")) - multiplier = 1000; - else if (s.equalsIgnoreCase("m") || s.equalsIgnoreCase("min") || s.equalsIgnoreCase("mins") + multiplier = 1000; + else if (s.equalsIgnoreCase("m") || s.equalsIgnoreCase("min") || s.equalsIgnoreCase("mins") || s.equalsIgnoreCase("minute") || s.equalsIgnoreCase("minutes")) - multiplier = 60*1000; - else if (s.equalsIgnoreCase("h") || s.equalsIgnoreCase("hr") || s.equalsIgnoreCase("hrs") + multiplier = 60*1000; + else if (s.equalsIgnoreCase("h") || s.equalsIgnoreCase("hr") || s.equalsIgnoreCase("hrs") || s.equalsIgnoreCase("hour") || s.equalsIgnoreCase("hours")) - multiplier = 60*60*1000; - else if (s.equalsIgnoreCase("d") || s.equalsIgnoreCase("day") || s.equalsIgnoreCase("days")) - multiplier = 24*60*60*1000; - else - throw new NumberFormatException("unknown unit '"+s+"' in time string"); - double d = Double.parseDouble(num); - double dd = 0; - if (timeString.length()>0) { - dd = parseElapsedTimeAsDouble(timeString); - if (dd==-1) { - throw new NumberFormatException("cannot combine '"+timeString+"' with '"+num+" "+s+"'"); + multiplier = 60*60*1000; + else if (s.equalsIgnoreCase("d") || s.equalsIgnoreCase("day") || s.equalsIgnoreCase("days")) + multiplier = 24*60*60*1000; + else + throw new NumberFormatException("Unknown unit '"+s+"' in time string '"+timeStringOrig+"'"); + double d = Double.parseDouble(num); + double dd = 0; + if (timeString.length()>0) { + dd = parseElapsedTimeAsDouble(timeString); + if (dd==-1) { + throw new NumberFormatException("Cannot combine '"+timeString+"' with '"+num+" "+s+"'"); + } } + return d*multiplier + dd; + } catch (Exception ex) { + if (ex instanceof NumberFormatException) throw ex; + log.trace("Details of parse failure:", ex); + throw new NumberFormatException("Cannot parse time string '"+timeStringOrig+"'"); } - return d*multiplier + dd; } } http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/a340dbc3/utils/common/src/test/java/org/apache/brooklyn/util/time/TimeTest.java ---------------------------------------------------------------------- diff --git a/utils/common/src/test/java/org/apache/brooklyn/util/time/TimeTest.java b/utils/common/src/test/java/org/apache/brooklyn/util/time/TimeTest.java index 2cce436..60945cf 100644 --- a/utils/common/src/test/java/org/apache/brooklyn/util/time/TimeTest.java +++ b/utils/common/src/test/java/org/apache/brooklyn/util/time/TimeTest.java @@ -152,7 +152,13 @@ public class TimeTest { Assert.assertFalse(Time.hasElapsedSince(aFewSecondsAgo, Duration.TEN_SECONDS)); Assert.assertTrue(Time.hasElapsedSince(-1, Duration.TEN_SECONDS)); } - + + @Test + public void testParseTime() { + Assert.assertEquals(Time.parseElapsedTime("1s"), 1000); + Assert.assertEquals(Time.parseElapsedTime("never"), -1); + } + @Test public void testMakeDateString() { String in1 = "2015-06-15T12:34:56";
