Github user ahgittin commented on a diff in the pull request:

    https://github.com/apache/incubator-brooklyn/pull/682#discussion_r32332569
  
    --- Diff: utils/common/src/main/java/brooklyn/util/time/Time.java ---
    @@ -443,36 +500,466 @@ else if (s.equalsIgnoreCase("d") || 
s.equalsIgnoreCase("day") || s.equalsIgnoreC
             }
         }
     
    +    public static Calendar newCalendarFromMillisSinceEpochUtc(long 
timestamp) {
    +        GregorianCalendar cal = new GregorianCalendar();
    +        cal.setTimeInMillis(timestamp);
    +        return cal;
    +    }
    +
    +    public static Calendar newCalendarFromDate(Date date) {
    +        return newCalendarFromMillisSinceEpochUtc(date.getTime());
    +    }
    +    
    +    /** As {@link #parseCalendar(String)} but returning a {@link Date},
    +     * (i.e. a record where the time zone has been applied and forgotten). 
*/
    +    public static Date parseDate(String input) {
    +        if (input==null) return null;
    +        return parseCalendarMaybe(input).get().getTime();
    +    }
    +
    +    /** Parses dates from string, accepting many formats including 
ISO-8601 and http://yaml.org/type/timestamp.html, 
    +     * e.g. 2015-06-15 16:00:00 +0000.
    +     * <p>
    +     * Millis since epoch (1970) is also supported to represent the epoch 
(0) or dates in this millenium,
    +     * but to prevent ambiguity of e.g. "20150615", any other dates prior 
to the year 2001 are not accepted.
    +     * (However if a type Long is supplied, e.g. from a YAML parse, it 
will always be treated as millis since epoch.) 
    +     * <p>
    +     * Other formats including locale-specific variants, e.g. recognising 
month names,
    +     * are supported but this may vary from platform to platform and may 
change between versions. */
    +    public static Calendar parseCalendar(String input) {
    +        if (input==null) return null;
    +        return parseCalendarMaybe(input).get();
    +    }
    +    
    +    /** as {@link #parseCalendar(String)} but returning a {@link Maybe} 
rather than throwing or returning null */
    +    public static Maybe<Calendar> parseCalendarMaybe(String input) {
    +        if (input==null) return Maybe.absent("value is null");
    +        input = input.trim();
    +        Maybe<Calendar> result;
    +
    +        result = parseCalendarUtc(input);
    +        if (result.isPresent()) return result;
    +
    +        result = parseCalendarSimpleFlexibleFormatParser(input);
    +        if (result.isPresent()) return result;
    +        // return the error from this method
    +        Maybe<Calendar> returnResult = result;
    +
    +//        // see natty method comments below
    +//        Maybe<Date> result = parseDateNatty(input);
    +//        if (result.isPresent()) return result;
    +
    +        result = parseCalendarFormat(input, new 
SimpleDateFormat(DATE_FORMAT_OF_DATE_TOSTRING));
    +        if (result.isPresent()) return result;
    +        result = parseCalendarDefaultParse(input);
    +        if (result.isPresent()) return result;
    +
    +        return returnResult;
    +    }
    +
    +    @SuppressWarnings("deprecation")
    +    private static Maybe<Calendar> parseCalendarDefaultParse(String input) 
{
    +        try {
    +            long ms = Date.parse(input);
    +            if (ms>=new Date(1999, 12, 25).getTime() && ms <= new 
Date(2200, 1, 2).getTime()) {
    +                // accept default date parse for this century and next
    +                GregorianCalendar c = new GregorianCalendar();
    +                c.setTimeInMillis(ms);
    +                return Maybe.of((Calendar)c);
    +            }
    +        } catch (Exception e) {
    +            Exceptions.propagateIfFatal(e);
    +        }
    +        return Maybe.absent();
    +    }
    +
    +    private static Maybe<Calendar> parseCalendarUtc(String input) {
    +        input = input.trim();
    +        if (input.matches("\\d+")) {
    +            if ("0".equals(input)) {
    +                // accept 0 as epoch UTC
    +                return Maybe.of(newCalendarFromMillisSinceEpochUtc(0));
    +            }
    +            Maybe<Calendar> result = 
Maybe.of(newCalendarFromMillisSinceEpochUtc(Long.parseLong(input)));
    +            if (result.isPresent()) {
    +                int year = result.get().get(Calendar.YEAR);
    +                if (year >= 2000 && year < 2200) {
    +                    // only applicable for dates in this century
    +                    return result;
    +                } else {
    +                    return Maybe.absent("long is probably not millis since 
epoch UTC; millis as string is not in acceptable range");
    +                }
    +            }
    +        }
    +        return Maybe.absent("not long millis since epoch UTC");
    +    }
    +
    +    private final static String DIGIT = "\\d";
    +    private final static String LETTER = "\\p{L}";
    +    private final static String COMMON_SEPARATORS = "-\\.";
    +    private final static String TIME_SEPARATOR = COMMON_SEPARATORS+":";
    +    private final static String DATE_SEPARATOR = COMMON_SEPARATORS+"/ ";
    +    private final static String DATE_TIME_ANY_ORDER_GROUP_SEPARATOR = 
COMMON_SEPARATORS+":/ ";
    +
    +    private final static String DATE_ONLY_WITH_INNER_SEPARATORS = 
    +            namedGroup("year", DIGIT+DIGIT+DIGIT+DIGIT)
    +            + anyChar(DATE_SEPARATOR)
    +            + namedGroup("month", options(optionally(DIGIT)+DIGIT, 
anyChar(LETTER)+"+"))
    +            + anyChar(DATE_SEPARATOR)
    +            + namedGroup("day", optionally(DIGIT)+DIGIT);
    +    private final static String DATE_WORDS_2 = 
    +        namedGroup("month", anyChar(LETTER)+"+")
    +        + anyChar(DATE_SEPARATOR)
    +        + namedGroup("day", optionally(DIGIT)+DIGIT)
    +        + ",?"+anyChar(DATE_SEPARATOR)+"+"
    +        + namedGroup("year", DIGIT+DIGIT+DIGIT+DIGIT);
    +    // we could parse NN-NN-NNNN as DD-MM-YYYY always, but could be 
confusing for MM-DD-YYYY oriented people, so require month named
    +    private final static String DATE_WORDS_3 = 
    +        namedGroup("day", optionally(DIGIT)+DIGIT)
    +        + anyChar(DATE_SEPARATOR)
    +        + namedGroup("month", anyChar(LETTER)+"+")
    --- End diff --
    
    agree


---
If your project is set up for it, you can reply to this email and have your
reply appear on GitHub as well. If your project does not have this feature
enabled and wishes so, or if the feature is enabled but not working, please
contact infrastructure at [email protected] or file a JIRA ticket
with INFRA.
---

Reply via email to