Merge pull request #1255 from influxdb/date-parsing

Add date-only parsing
pull/1256/head
Ben Johnson 2014-12-21 11:02:12 -07:00
commit 6a19a8130d
5 changed files with 30 additions and 13 deletions

View File

@ -810,7 +810,7 @@ type TimeLiteral struct {
// String returns a string representation of the literal. // String returns a string representation of the literal.
func (l *TimeLiteral) String() string { func (l *TimeLiteral) String() string {
return `"` + l.Val.UTC().Format(TimeFormat) + `"` return `"` + l.Val.UTC().Format(DateTimeFormat) + `"`
} }
// DurationLiteral represents a duration literal. // DurationLiteral represents a duration literal.

View File

@ -199,11 +199,11 @@ func TestTimeRange(t *testing.T) {
min, max := influxql.TimeRange(expr) min, max := influxql.TimeRange(expr)
// Compare with expected min/max. // Compare with expected min/max.
if min := min.Format(influxql.TimeFormat); tt.min != min { if min := min.Format(influxql.DateTimeFormat); tt.min != min {
t.Errorf("%d. %s: unexpected min:\n\nexp=%s\n\ngot=%s\n\n", i, tt.expr, tt.min, min) t.Errorf("%d. %s: unexpected min:\n\nexp=%s\n\ngot=%s\n\n", i, tt.expr, tt.min, min)
continue continue
} }
if max := max.Format(influxql.TimeFormat); tt.max != max { if max := max.Format(influxql.DateTimeFormat); tt.max != max {
t.Errorf("%d. %s: unexpected max:\n\nexp=%s\n\ngot=%s\n\n", i, tt.expr, tt.max, max) t.Errorf("%d. %s: unexpected max:\n\nexp=%s\n\ngot=%s\n\n", i, tt.expr, tt.max, max)
continue continue
} }

View File

@ -60,7 +60,7 @@ func (p *Planner) Plan(stmt *SelectStatement) (*Executor, error) {
max = now max = now
} }
if max.Before(min) { if max.Before(min) {
return nil, fmt.Errorf("invalid time range: %s - %s", min.Format(TimeFormat), max.Format(TimeFormat)) return nil, fmt.Errorf("invalid time range: %s - %s", min.Format(DateTimeFormat), max.Format(DateTimeFormat))
} }
e.min, e.max = min, max e.min, e.max = min, max

View File

@ -10,8 +10,13 @@ import (
"time" "time"
) )
// TimeFormat represents the format for time literals. const (
const TimeFormat = "2006-01-02 15:04:05.999999" // DateFormat represents the format for date literals.
DateFormat = "2006-01-02"
// DateTimeFormat represents the format for date time literals.
DateTimeFormat = "2006-01-02 15:04:05.999999"
)
// Parser represents an InfluxQL parser. // Parser represents an InfluxQL parser.
type Parser struct { type Parser struct {
@ -852,10 +857,16 @@ func (p *Parser) parseUnaryExpr() (Expr, error) {
} }
case STRING: case STRING:
// If literal looks like a date time then parse it as a time literal. // If literal looks like a date time then parse it as a time literal.
if isTimeString(lit) { if isDateTimeString(lit) {
t, err := time.Parse(TimeFormat, lit) t, err := time.Parse(DateTimeFormat, lit)
if err != nil { if err != nil {
return nil, &ParseError{Message: "unable to parse time", Pos: pos} return nil, &ParseError{Message: "unable to parse datetime", Pos: pos}
}
return &TimeLiteral{Val: t}, nil
} else if isDateString(lit) {
t, err := time.Parse(DateFormat, lit)
if err != nil {
return nil, &ParseError{Message: "unable to parse date", Pos: pos}
} }
return &TimeLiteral{Val: t}, nil return &TimeLiteral{Val: t}, nil
} }
@ -1034,10 +1045,14 @@ func split(s string) (a []rune) {
return return
} }
// isTimeString returns true if the string looks like a time literal. // isDateString returns true if the string looks like a datetime literal.
func isTimeString(s string) bool { return timeStringRegexp.MatchString(s) } func isDateString(s string) bool { return dateStringRegexp.MatchString(s) }
var timeStringRegexp = regexp.MustCompile(`^\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2}(?:\.\d+)?$`) // isDateTimeString returns true if the string looks like a datetime literal.
func isDateTimeString(s string) bool { return dateTimeStringRegexp.MatchString(s) }
var dateStringRegexp = regexp.MustCompile(`^\d{4}-\d{2}-\d{2}$`)
var dateTimeStringRegexp = regexp.MustCompile(`^\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2}(?:\.\d+)?$`)
// ErrInvalidDuration is returned when parsing a malformatted duration. // ErrInvalidDuration is returned when parsing a malformatted duration.
var ErrInvalidDuration = errors.New("invalid duration") var ErrInvalidDuration = errors.New("invalid duration")

View File

@ -349,7 +349,9 @@ func TestParser_ParseExpr(t *testing.T) {
{s: `false`, expr: &influxql.BooleanLiteral{Val: false}}, {s: `false`, expr: &influxql.BooleanLiteral{Val: false}},
{s: `my_ident`, expr: &influxql.VarRef{Val: "my_ident"}}, {s: `my_ident`, expr: &influxql.VarRef{Val: "my_ident"}},
{s: `"2000-01-01 00:00:00"`, expr: &influxql.TimeLiteral{Val: mustParseTime("2000-01-01T00:00:00Z")}}, {s: `"2000-01-01 00:00:00"`, expr: &influxql.TimeLiteral{Val: mustParseTime("2000-01-01T00:00:00Z")}},
{s: `"2000-01-32 00:00:00"`, err: `unable to parse time at line 1, char 1`}, {s: `"2000-01-32 00:00:00"`, err: `unable to parse datetime at line 1, char 1`},
{s: `"2000-01-01"`, expr: &influxql.TimeLiteral{Val: mustParseTime("2000-01-01T00:00:00Z")}},
{s: `"2000-01-99"`, err: `unable to parse date at line 1, char 1`},
// Simple binary expression // Simple binary expression
{ {