diff --git a/EvaluableExpression.go b/EvaluableExpression.go index a5fe50d..2b0e7cc 100644 --- a/EvaluableExpression.go +++ b/EvaluableExpression.go @@ -37,6 +37,32 @@ type EvaluableExpression struct { inputExpression string } +// An Option is used to define the behavior of the expression parser. +type Option func(*options) + +type options struct { + skipDateParsing bool +} + +func getOpts(o ...Option) (res options) { + for _, f := range o { + f(&res) + } + return +} + +var ( + // The SkipDateParsing disables the automatic attempt to parse strings as dates. + // By default, date parsing is automatically tried with any string constant + SkipDateParsing Option = skipDateParsing +) + +var ( + skipDateParsing = func(o *options) { + o.skipDateParsing = true + } +) + /* Parses a new EvaluableExpression from the given [expression] string. Returns an error if the given expression has invalid syntax. @@ -87,16 +113,17 @@ func NewEvaluableExpressionFromTokens(tokens []ExpressionToken) (*EvaluableExpre Similar to [NewEvaluableExpression], except enables the use of user-defined functions. Functions passed into this will be available to the expression. */ -func NewEvaluableExpressionWithFunctions(expression string, functions map[string]ExpressionFunction) (*EvaluableExpression, error) { +func NewEvaluableExpressionWithFunctions(expression string, functions map[string]ExpressionFunction, opts ...Option) (*EvaluableExpression, error) { var ret *EvaluableExpression var err error + o := getOpts(opts...) ret = new(EvaluableExpression) ret.QueryDateFormat = isoDateFormat ret.inputExpression = expression - ret.tokens, err = parseTokens(expression, functions) + ret.tokens, err = parseTokens(expression, functions, o) if err != nil { return nil, err } diff --git a/parsing.go b/parsing.go index 40c7ed2..e8c3488 100644 --- a/parsing.go +++ b/parsing.go @@ -11,7 +11,7 @@ import ( "unicode" ) -func parseTokens(expression string, functions map[string]ExpressionFunction) ([]ExpressionToken, error) { +func parseTokens(expression string, functions map[string]ExpressionFunction, opts options) ([]ExpressionToken, error) { var ret []ExpressionToken var token ExpressionToken @@ -25,7 +25,7 @@ func parseTokens(expression string, functions map[string]ExpressionFunction) ([] for stream.canRead() { - token, err, found = readToken(stream, state, functions) + token, err, found = readToken(stream, state, functions, opts) if err != nil { return ret, err @@ -52,7 +52,7 @@ func parseTokens(expression string, functions map[string]ExpressionFunction) ([] return ret, nil } -func readToken(stream *lexerStream, state lexerState, functions map[string]ExpressionFunction) (ExpressionToken, error, bool) { +func readToken(stream *lexerStream, state lexerState, functions map[string]ExpressionFunction, opts options) (ExpressionToken, error, bool) { var function ExpressionFunction var ret ExpressionToken @@ -214,12 +214,13 @@ func readToken(stream *lexerStream, state lexerState, functions map[string]Expre stream.rewind(-1) // check to see if this can be parsed as a time. - tokenTime, found = tryParseTime(tokenValue.(string)) - if found { - kind = TIME - tokenValue = tokenTime - } else { - kind = STRING + kind = STRING + if !opts.skipDateParsing { + tokenTime, found = tryParseTime(tokenValue.(string)) + if found { + kind = TIME + tokenValue = tokenTime + } } break }