mirror of
https://github.com/featurebasedb/featurebase.git
synced 2026-08-28 02:44:59 +00:00
parent
26747362e1
commit
df7e813f01
8 changed files with 1138 additions and 1041 deletions
|
|
@ -32,7 +32,7 @@ const (
|
|||
|
||||
var (
|
||||
ErrNoFieldSpec = errors.New("no field spec in this header")
|
||||
ErrInvalidFieldName = errors.New("field name must match [a-z][a-z0-9_-]{0,229}")
|
||||
ErrInvalidFieldName = errors.New("field name must match [a-z][a-z0-9Θ_-]{0,229}")
|
||||
ErrParsingEpoch = "parsing epoch for "
|
||||
ErrDecodingConfig = "decoding config for field "
|
||||
)
|
||||
|
|
|
|||
|
|
@ -351,6 +351,11 @@ func TestHeaderToField(t *testing.T) {
|
|||
input: "a__LookupText",
|
||||
exp: LookupTextField{NameVal: "a", DestNameVal: "a"},
|
||||
},
|
||||
{
|
||||
name: "theta",
|
||||
input: "fldΘnameΘ__String",
|
||||
exp: StringField{NameVal: "fldΘnameΘ", DestNameVal: "fldΘnameΘ"},
|
||||
},
|
||||
}
|
||||
|
||||
for _, test := range tests {
|
||||
|
|
|
|||
|
|
@ -47,7 +47,7 @@ var (
|
|||
ErrInvalidView = errors.New("invalid view")
|
||||
ErrInvalidCacheType = errors.New("invalid cache type")
|
||||
|
||||
ErrName = errors.New("invalid index or field name, must match [a-z][a-z0-9_-]* and contain at most 230 characters")
|
||||
ErrName = errors.New("invalid index or field name, must match [a-z][a-z0-9Θ_-]* and contain at most 230 characters")
|
||||
|
||||
// ErrFragmentNotFound is returned when a fragment does not exist.
|
||||
ErrFragmentNotFound = errors.New("fragment not found")
|
||||
|
|
@ -135,7 +135,7 @@ func newPreconditionFailedError(err error) PreconditionFailedError {
|
|||
}
|
||||
|
||||
// Regular expression to validate index and field names.
|
||||
var nameRegexp = regexp.MustCompile(`^[a-z][a-z0-9_-]{0,229}$`)
|
||||
var nameRegexp = regexp.MustCompile(`^[a-z][a-z0-9Θ_-]{0,229}$`)
|
||||
|
||||
// TimeFormat is the go-style time format used to parse string dates.
|
||||
const TimeFormat = "2006-01-02T15:04"
|
||||
|
|
|
|||
|
|
@ -3,6 +3,7 @@
|
|||
package pilosa_test
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"strings"
|
||||
"testing"
|
||||
|
||||
|
|
@ -43,3 +44,28 @@ func TestAddressWithDefaults(t *testing.T) {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestValidateName(t *testing.T) {
|
||||
tests := []struct {
|
||||
name string
|
||||
err error
|
||||
}{
|
||||
{name: "a_name", err: nil},
|
||||
{name: "a-name", err: nil},
|
||||
{name: "a-name-10", err: nil},
|
||||
{name: "A-name", err: fmt.Errorf("'A-name': %s", pilosa.ErrName)},
|
||||
{name: "-a-name", err: fmt.Errorf("'-a-name': %s", pilosa.ErrName)},
|
||||
{name: "8th_name", err: fmt.Errorf("'8th_name': %s", pilosa.ErrName)},
|
||||
{name: "Θ_name", err: fmt.Errorf("'Θ_name': %s", pilosa.ErrName)},
|
||||
{name: "a_NaMe", err: fmt.Errorf("'a_NaMe': %s", pilosa.ErrName)},
|
||||
{name: "indexΘname", err: nil},
|
||||
}
|
||||
for _, test := range tests {
|
||||
err := pilosa.ValidateName(test.name)
|
||||
if !(err == nil && test.err == nil) {
|
||||
if err.Error() != test.err.Error() {
|
||||
t.Errorf("expected error: %v, but got: %v", test.err, err)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -307,6 +307,20 @@ func TestParser_Parse(t *testing.T) {
|
|||
}
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("ParseTheta", func(t *testing.T) {
|
||||
q, err := pql.ParseString(`Row(fldΘname=fldΘval)`)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
} else if !reflect.DeepEqual(q.Calls[0],
|
||||
&pql.Call{
|
||||
Name: "Row",
|
||||
Args: map[string]interface{}{"fldΘname": "fldΘval"},
|
||||
},
|
||||
) {
|
||||
t.Fatalf("unexpected call: %#v", q.Calls[0])
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
func TestUnquote(t *testing.T) {
|
||||
|
|
|
|||
10
pql/pql.peg
10
pql/pql.peg
|
|
@ -20,7 +20,7 @@ Call <- "Set" {p.startCall("Set")} open col comma args (comma time)? close {p.e
|
|||
/ "Sum" {p.startCall("Sum")} open posfield (comma allargs)? close {p.endCall()}
|
||||
/ "Range" {p.startCall("Range")} open field eq value comma 'from='? {p.addField("from")} timefmt {p.addVal(text)} comma 'to='? sp {p.addField("to")} timefmt {p.addVal(text)} close {p.endCall()}
|
||||
/ < IDENT > { p.startCall(text) } open allargs comma? close { p.endCall() }
|
||||
ivyExpr <- ( '(' / '_' / '/' / '[' / ']' /'.' / '=' / '&' / '<'/ '>' /',' / ')' / '^' / '!' / '|' / [*+] / '-' / '?' / [[A-Z]] / [0-9] / '#' / [ \t\n] )*
|
||||
ivyExpr <- ( '(' / '_' / '/' / '[' / ']' /'.' / '=' / '&' / '<'/ '>' /',' / ')' / '^' / '!' / '|' / [*+] / '-' / '?' / [[A-Z]] / [0-9] / '#' / [ \t\n] / 'Θ')*
|
||||
ivyprogram <- '"'? <ivyExpr> '"' { p.addPosStr("_ivy", text) }
|
||||
ivyprogram2 <- '"'? <ivyExpr> '"' { p.addPosStr("_ivyReduce", text) }
|
||||
|
||||
|
|
@ -55,16 +55,16 @@ item <- 'null' &(comma / close) { p.addVal(nil) }
|
|||
/ timestampfmt { p.addTimestampVal(text) }
|
||||
/ < decimal > { p.addNumVal(text) }
|
||||
/ < IDENT > { p.startCall(text) } open allargs comma? close { p.addVal(p.endCall()) }
|
||||
/ < ([[A-Z]] / [0-9] / '-' / '_' / ':')+ > { p.addVal(text) }
|
||||
/ < ([[A-Z]] / [0-9] / '-' / '_' / ':' / 'Θ')+ > { p.addVal(text) }
|
||||
/ < '"' doublequotedstring '"' > { p.addVal(text) }
|
||||
/ < '\'' singlequotedstring '\'' > { p.addVal(text) }
|
||||
|
||||
doublequotedstring <- ( '\\"' / '\\\\' / '\\n' / '\\t' / [^"\\] )*
|
||||
singlequotedstring <- ( '\\\'' / '\\\\' / '\\n' / '\\t' / [^'\\] )*
|
||||
|
||||
variable <- ( [[A-Z]] / '_' ) ( [[A-Z]] / [0-9] / '_' / '-' )*
|
||||
variable <- ( [[A-Z]] / '_' ) ( [[A-Z]] / [0-9] / '_' / '-' / 'Θ')*
|
||||
|
||||
fieldExpr <- ( [[A-Z]] / '_' / '$' ) ( [[A-Z]] / [0-9] / '_' / '-' )*
|
||||
fieldExpr <- ( [[A-Z]] / '_' / '$' ) ( [[A-Z]] / [0-9] / '_' / '-' / 'Θ')*
|
||||
field <- <fieldExpr / reserved> { p.addField(text) }
|
||||
reserved <- '_row' / '_col' / '_start' / '_end' / '_timestamp' / '_field'
|
||||
posfield <- 'field='? <fieldExpr> { p.addPosStr("_field", text) }
|
||||
|
|
@ -79,7 +79,7 @@ eq <- sp '=' sp
|
|||
comma <- sp ',' sp
|
||||
lbrack <- '[' sp
|
||||
rbrack <- sp ']' sp
|
||||
IDENT <- [[A-Z]] ([[A-Z]] / [0-9])*
|
||||
IDENT <- [[A-Z]] ([[A-Z]] / [0-9] / 'Θ')*
|
||||
digits <- [0-9]+
|
||||
signedDigits <- '-'? digits
|
||||
decimal <- signedDigits ('.' digits?)?
|
||||
|
|
|
|||
2107
pql/pql.peg.go
2107
pql/pql.peg.go
File diff suppressed because it is too large
Load diff
|
|
@ -353,7 +353,7 @@ func TestPQLDeepEquality(t *testing.T) {
|
|||
},
|
||||
}},
|
||||
{
|
||||
name: "RowWithUnicode",
|
||||
name: "RowValWithUnicode",
|
||||
call: `Row(unicode="Æ漢д ☮♬ ♞🜻💣")`,
|
||||
exp: &Call{
|
||||
Name: "Row",
|
||||
|
|
@ -361,6 +361,15 @@ func TestPQLDeepEquality(t *testing.T) {
|
|||
"unicode": `Æ漢д ☮♬ ♞🜻💣`,
|
||||
},
|
||||
}},
|
||||
{
|
||||
name: "RowWithUnicode",
|
||||
call: `Row(uniΘcode="Æ漢д ☮♬ ♞🜻💣")`,
|
||||
exp: &Call{
|
||||
Name: "Row",
|
||||
Args: map[string]interface{}{
|
||||
"uniΘcode": `Æ漢д ☮♬ ♞🜻💣`,
|
||||
},
|
||||
}},
|
||||
{
|
||||
name: "RowsWithUnicode",
|
||||
call: `Rows(job, previous="💣")`,
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue