Skip to content

Commit

Permalink
Merge pull request #1010 from Cali0707/sync-tck-tests
Browse files Browse the repository at this point in the history
Sync CESQL tck tests
  • Loading branch information
lionelvillard committed Feb 1, 2024
2 parents f1f87df + 06b0321 commit 04ed212
Show file tree
Hide file tree
Showing 5 changed files with 242 additions and 1 deletion.
3 changes: 3 additions & 0 deletions sql/v2/expression/like_expression.go
Expand Up @@ -70,6 +70,9 @@ func convertLikePatternToRegex(pattern string) (*regexp.Regexp, error) {
chunk.Reset()
i++
continue
} else {
// if there is an actual literal \ character, we need to include that in the string
chunk.WriteRune('\\')
}
} else if pattern[i] == '_' {
// replace with .
Expand Down
28 changes: 28 additions & 0 deletions sql/v2/test/tck/README.md
@@ -0,0 +1,28 @@
# CloudEvents Expression Language TCK

Each file of this TCK contains a set of test cases, testing one or more specific features of the language.

The root file structure is composed by:

* `name`: Name of the test suite contained in the file
* `tests`: List of tests

Each test definition includes:

* `name`: Name of the test case
* `expression`: Expression to test.
* `result`: Expected result (OPTIONAL). Can be a boolean, an integer or a string.
* `error`: Expected error (OPTIONAL). If absent, no error is expected.
* `event`: Input event (OPTIONAL). If present, this is a valid event serialized in JSON format. If absent, when testing
the expression, any valid event can be passed.
* `eventOverrides`: Overrides to the input event (OPTIONAL). This might be used when `event` is missing, in order to
define only some specific values, while the other (REQUIRED) attributes can be any value.

The `error` values could be any of the following:

* `parse`: Error while parsing the expression
* `math`: Math error while evaluating a math operator
* `cast`: Casting error
* `missingAttribute`: Addressed a missing attribute
* `missingFunction`: Addressed a missing function
* `functionEvaluation`: Error while evaluating a function
40 changes: 39 additions & 1 deletion sql/v2/test/tck/like_expression.yaml
@@ -1,8 +1,11 @@
name: Like expression
tests:
- name: Exact match
- name: Exact match (1)
expression: "'abc' LIKE 'abc'"
result: true
- name: Exact match (2)
expression: "'ab\\c' LIKE 'ab\\c'"
result: true
- name: Exact match (negate)
expression: "'abc' NOT LIKE 'abc'"
result: false
Expand All @@ -25,6 +28,12 @@ tests:
- name: Percentage operator (6)
expression: "'' LIKE 'abc'"
result: false
- name: Percentage operator (7)
expression: "'.ab.cde.' LIKE '.%.%.'"
result: true
- name: Percentage operator (8)
expression: "'ab.cde' LIKE '.%.%.'"
result: false

- name: Underscore operator (1)
expression: "'abc' LIKE 'a_b_c'"
Expand All @@ -41,6 +50,12 @@ tests:
- name: Underscore operator (5)
expression: "'azbzc' LIKE 'a_b_c'"
result: true
- name: Underscore operator (6)
expression: "'.a.b.' LIKE '._._.'"
result: true
- name: Underscore operator (7)
expression: "'abcd.' LIKE '._._.'"
result: false

- name: Escaped underscore wildcards (1)
expression: "'a_b_c' LIKE 'a\\_b\\_c'"
Expand Down Expand Up @@ -78,3 +93,26 @@ tests:
eventOverrides:
myext: "abc123123%456_dzf"
result: false

- name: With type coercion from int (1)
expression: "234 LIKE '23_'"
result: true
- name: With type coercion from int (2)
expression: "2344 LIKE '23%'"
result: true
- name: With type coercion from int (3)
expression: "2344 LIKE '23_'"
result: false

- name: With type coercion from bool (1)
expression: "TRUE LIKE 'tr%'"
result: true
- name: With type coercion from bool (2)
expression: "TRUE LIKE '%ue'"
result: true
- name: With type coercion from bool (3)
expression: "FALSE LIKE 'tr%'"
result: false
- name: With type coercion from bool (4)
expression: "FALSE LIKE 'fal%'"
result: true
168 changes: 168 additions & 0 deletions sql/v2/test/tck/subscriptions_api_recreations.yaml
@@ -0,0 +1,168 @@
name: SubscriptionsAPI Recreations
tests:
- name: Prefix filter (1)
expression: "source LIKE 'https://%'"
result: true
eventOverrides:
source: "https://example.com"
- name: Prefix filter (2)
expression: "source LIKE 'https://%'"
result: false
eventOverrides:
source: "http://example.com"
- name: Prefix filter on string extension
expression: "myext LIKE 'custom%'"
result: true
eventOverrides:
myext: "customext"
- name: Prefix filter on missing string extension
expression: "myext LIKE 'custom%'"
error: missingAttribute

- name: Suffix filter (1)
expression: "type like '%.error'"
result: true
eventOverrides:
type: "com.github.error"
- name: Suffix filter (2)
expression: "type like '%.error'"
result: false
eventOverrides:
type: "com.github.success"
- name: Suffix filter on string extension
expression: "myext LIKE '%ext'"
result: true
eventOverrides:
myext: "customext"
- name: Suffix filter on missing string extension
expression: "myext LIKE '%ext'"
error: missingAttribute

- name: Exact filter (1)
expression: "id = 'myId'"
result: true
eventOverrides:
id: "myId"
- name: Exact filter (2)
expression: "id = 'myId'"
result: false
eventOverrides:
id: "notmyId"
- name: Exact filter on string extension
expression: "myext = 'customext'"
result: true
eventOverrides:
myext: "customext"
- name: Exact filter on missing string extension
expression: "myext = 'customext'"
error: missingAttribute

- name: Prefix filter AND Suffix filter (1)
expression: "id LIKE 'my%' AND source LIKE '%.ca'"
result: true
eventOverrides:
id: "myId"
source: "http://www.some-website.ca"
- name: Prefix filter AND Suffix filter (2)
expression: "id LIKE 'my%' AND source LIKE '%.ca'"
result: false
eventOverrides:
id: "myId"
source: "http://www.some-website.com"
- name: Prefix filter AND Suffix filter (3)
expression: "myext LIKE 'custom%' AND type LIKE '%.error'"
result: true
eventOverrides:
myext: "customext"
type: "com.github.error"
- name: Prefix AND Suffix filter (4)
expression: "type LIKE 'example.%' AND myext LIKE 'custom%'"
error: missingAttribute
eventOverrides:
type: "example.event.type"

- name: Prefix OR Suffix filter (1)
expression: "id LIKE 'my%' OR source LIKE '%.ca'"
result: true
eventOverrides:
id: "myId"
source: "http://www.some-website.ca"
- name: Prefix OR Suffix filter (2)
expression: "id LIKE 'my%' OR source LIKE '%.ca'"
result: true
eventOverrides:
id: "myId"
source: "http://www.some-website.com"
- name: Prefix OR Suffix filter (3)
expression: "id LIKE 'my%' OR source LIKE '%.ca'"
result: true
eventOverrides:
id: "notmyId"
source: "http://www.some-website.ca"
- name: Prefix OR Suffix filter (4)
expression: "id LIKE 'my%' OR source LIKE '%.ca'"
result: false
eventOverrides:
id: "notmyId"
source: "http://www.some-website.com"

- name: Disjunctive Normal Form (1)
expression: "(id = 'myId' AND type LIKE '%.success') OR (id = 'notmyId' AND source LIKE 'http://%' AND type LIKE '%.warning')"
result: true
eventOverrides:
id: "myId"
type: "example.event.success"
- name: Disjunctive Normal Form (2)
expression: "(id = 'myId' AND type LIKE '%.success') OR (id = 'notmyId' AND source LIKE 'http://%' AND type LIKE '%.warning')"
result: true
eventOverrides:
id: "notmyId"
type: "example.event.warning"
source: "http://localhost.localdomain"
- name: Disjunctive Normal Form (3)
expression: "(id = 'myId' AND type LIKE '%.success') OR (id = 'notmyId' AND source LIKE 'http://%' AND type LIKE '%.warning')"
result: false
eventOverrides:
id: "notmyId"
type: "example.event.warning"
source: "https://localhost.localdomain"

- name: Conjunctive Normal Form (1)
expression: "(id = 'myId' OR type LIKE '%.success') AND (id = 'notmyId' OR source LIKE 'https://%' OR type LIKE '%.warning')"
result: true
eventOverrides:
id: "myId"
type: "example.event.warning"
source: "http://localhost.localdomain"
- name: Conjunctive Normal Form (2)
expression: "(id = 'myId' OR type LIKE '%.success') AND (id = 'notmyId' OR source LIKE 'https://%' OR type LIKE '%.warning')"
result: true
eventOverrides:
id: "notmyId"
type: "example.event.success"
source: "http://localhost.localdomain"
- name: Conjunctive Normal Form (3)
expression: "(id = 'myId' OR type LIKE '%.success') AND (id = 'notmyId' OR source LIKE 'https://%' OR type LIKE '%.warning')"
result: false
eventOverrides:
id: "notmyId"
type: "example.event.warning"
source: "http://localhost.localdomain"
- name: Conjunctive Normal Form (4)
expression: "(id = 'myId' OR type LIKE '%.success') AND (id = 'notmyId' OR source LIKE 'https://%' OR type LIKE '%.warning')"
result: false
eventOverrides:
id: "myId"
type: "example.event.success"
source: "http://localhost.localdomain"
- name: Conjunctive Normal Form (5)
expression: "(id = 'myId' OR type LIKE '%.success') AND (id = 'notmyId' OR source LIKE 'https://%' OR type LIKE '%.warning') AND (myext = 'customext')"
error: missingAttribute
eventOverrides:
id: "myId"
type: "example.event.warning"
source: "http://localhost.localdomain"




4 changes: 4 additions & 0 deletions sql/v2/test/tck_test.go
Expand Up @@ -40,6 +40,7 @@ var TCKFileNames = []string{
"spec_examples",
"string_builtin_functions",
"sub_expression",
"subscriptions_api_recreations",
}

type ErrorType string
Expand Down Expand Up @@ -93,6 +94,8 @@ func (tc TckTestCase) ExpectedResult() interface{} {
return int32(tc.Result.(int))
case float64:
return int32(tc.Result.(float64))
case bool:
return tc.Result.(bool)
}
return tc.Result
}
Expand Down Expand Up @@ -125,6 +128,7 @@ func TestTCK(t *testing.T) {
t.Run(file.Name, func(t *testing.T) {
for j, testCase := range tckFiles[i].Tests {
j := j
testCase := testCase
t.Run(testCase.Name, func(t *testing.T) {
t.Parallel()
testCase := tckFiles[i].Tests[j]
Expand Down

0 comments on commit 04ed212

Please sign in to comment.