Differentiate between IDENT and EXPR in SQL

Previously it was possible to CREATE/UPDATE/DELETE path expressions as this would satisfy an IDENT in the SQL parser.

Now however, there is a difference between an IDENT and an EXPR…

IDENT: person | person_main | person123
EXPR: person | person.path | person[0].path

As a result, path expressions are only possible when setting data or setting conditional conditions.
This commit is contained in:
Tobie Morgan Hitchcock 2017-02-24 13:05:07 +00:00
parent 79812544e8
commit e4bef0c4b7
3 changed files with 14 additions and 5 deletions

View file

@ -519,7 +519,7 @@ func (p *parser) parseExpr() (exp Expr, err error) {
func (p *parser) parsePart() (exp Expr, err error) {
toks := []Token{
MUL, ID, IDENT, THING,
MUL, ID, EXPR, IDENT, THING,
NULL, VOID, EMPTY, MISSING,
TRUE, FALSE, STRING, REGION, NUMBER, DOUBLE,
NOW, DATE, TIME, DURATION, JSON, ARRAY, PARAM, LPAREN,

View file

@ -395,11 +395,14 @@ func (s *scanner) scanIdent(chp ...rune) (tok Token, lit string, val interface{}
for {
if ch := s.next(); ch == eof {
break
} else if !isIdentChar(ch) {
} else if isIdentChar(ch) {
buf.WriteRune(ch)
} else if isExprsChar(ch) {
tok = EXPR
buf.WriteRune(ch)
} else {
s.undo()
break
} else {
buf.WriteRune(ch)
}
}
@ -839,7 +842,7 @@ func isLetter(ch rune) bool {
// isIdentChar returns true if the rune is allowed in a IDENT.
func isIdentChar(ch rune) bool {
return isLetter(ch) || isNumber(ch) || ch == '.' || ch == '_' || ch == '*' || ch == '[' || ch == ']'
return isLetter(ch) || isNumber(ch) || ch == '_'
}
// isThingChar returns true if the rune is allowed in a THING.
@ -847,5 +850,10 @@ func isThingChar(ch rune) bool {
return isLetter(ch) || isNumber(ch) || ch == '_'
}
// isExprsChar returns true if the rune is allowed in a IDENT.
func isExprsChar(ch rune) bool {
return isLetter(ch) || isNumber(ch) || ch == '.' || ch == '_' || ch == '*' || ch == '[' || ch == ']'
}
// eof represents a marker rune for the end of the reader.
var eof = rune(0)

View file

@ -32,6 +32,7 @@ const (
DATE // 1970-01-01
TIME // 1970-01-01T00:00:00+00:00
JSON // {"test":true}
EXPR // something[0].value
IDENT // something
THING // @class:id
STRING // "something"