-
Notifications
You must be signed in to change notification settings - Fork 583
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
clarify type casting in CESQL spec #1281
Merged
duglin
merged 9 commits into
cloudevents:main
from
Cali0707:clarifications-like-expression-casting
May 30, 2024
Merged
Changes from 8 commits
Commits
Show all changes
9 commits
Select commit
Hold shift + click to select a range
9193215
clarify type casting in CESQL spec
Cali0707 6b5f67e
fix: addressed feedback from meeting
Cali0707 4729d2e
address review feedback
Cali0707 8812b57
clarify the default values when an error occurs
Cali0707 14028f4
fix: may -> MAY
Cali0707 7f90d78
clarify second operand in LIKE expression MUST be a string literal
Cali0707 4cbb1af
clarify leading zeros
Cali0707 e90f8c6
add table of supported and unsupported type casts
Cali0707 c755764
add boolean <-> integer casting
Cali0707 File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -268,7 +268,7 @@ Similarly, whenever the left operand of the OR operation evaluates to `true`, th | |
| `x LIKE pattern: String x String -> Boolean` | Returns `true` if the value x matches the `pattern` | | ||
| `x NOT LIKE pattern: String x String -> Boolean` | Same as `NOT (x LIKE PATTERN)` | | ||
|
||
The pattern of the `LIKE` operator can contain: | ||
The pattern of the `LIKE` operator MUST be a string literal, and can contain: | ||
|
||
- `%` represents zero, one, or multiple characters | ||
- `_` represents a single character | ||
|
@@ -278,6 +278,10 @@ For example, the pattern `_b*` will accept values `ab`, `abc`, `abcd1` but won't | |
Both `%` and `_` can be escaped with `\`, in order to be matched literally. For example, the pattern `abc\%` will match | ||
`abc%` but won't match `abcd`. | ||
|
||
In cases where the left operand is not a `String`, it MUST be cast to a `String` before the comparison is made. | ||
The pattern of the `LIKE` operator (that is, the right operand of the operator) MUST be a valid string literal without casting, | ||
otherwise the parser MUST return a parse error. | ||
|
||
#### 3.4.4. Exists operator | ||
|
||
| Definition | Semantics | | ||
|
@@ -353,6 +357,33 @@ left operand of the OR operation evalues to `true`, the right operand MUST NOT b | |
|
||
#### 3.7. Type casting | ||
|
||
The following table indicates which type casts a CESQL engine MUST or MUST NOT support: | ||
|
||
| Type | Integer | String | Boolean | | ||
| ------- | -------- | ------ | -------- | | ||
| Integer | N/A | MUST | MUST NOT | | ||
| String | MUST | N/A | MUST | | ||
| Boolean | MUST NOT | MUST | N/A | | ||
|
||
For all of the type casts which a CESQL engine MUST support, the semantics which the engine MUST use are defined as follows: | ||
|
||
| Definition | Semantics | | ||
| -------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | | ||
| `Integer -> String` | Returns the string representation of the integer value in base 10, without leading `0`s. If the value is less than 0, the '-' character is prepended to the result. | | ||
| `String -> Integer` | Returns the result of interpreting the string as a 32 bit base 10 integer. The string MAY begin with a leading sign '+' or '-'. If the result will overflow or the string is not a valid integer an error is returned along with a value of `0`. | | ||
| `String -> Boolean` | Returns `true` or `false` if the lower case representation of the string is exactly "true" or "false, respectively. Otherwise returns an error along with a value of `false` | | ||
| `Boolean -> String` | Returns `"true"` if the boolean is `true`, and `"false"` if the boolean is `false`. | | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think we should have a 3x3 table (or something) that shows all combinations in one spot. Then it's easy to see what's missing, like bool->int, int->bool |
||
|
||
An example of how _Boolean_ values cast to _String_ combines with the case insensitivity of CESQL keywords is that: | ||
``` | ||
TRUE = "true" AND FALSE = "false" | ||
``` | ||
will evaluate to `true`, while | ||
``` | ||
TRUE = "TRUE" OR FALSE = "FALSE" | ||
``` | ||
will evaluate to `false`. | ||
|
||
When the argument types of an operator/function invocation don't match the signature of the operator/function being invoked, the CESQL engine MUST try to perform an implicit cast. | ||
|
||
This section defines an **ambiguous** operator/function as an operator/function that is overloaded with another | ||
|
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is a valid choice, but I'm curious why you didn't choose to map
1
withtrue
and0
withfalse
?There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Tbh, I just based this off the current implementation in the SDKs...
The
1
mapping totrue
and0
tofalse
sounds reasonable though, especially because then the zero value for integers would be cast tofalse
.Which do you think is better?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm partial to allowing it, then everything can be implicitly cast to anything else - and I think you can then remove an error type.
@jskeet any concerns?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm okay with it - personally I do like being clear about expressions in terms of types, but that's mostly in C# etc. I haven't done significant amounts of SQL in years, so I don't know how it would "feel". If others are happy, that's fine by me.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@duglin if we do this:
then how would we handle an integer value like
200
? Would that be an error? Or to avoid errors would it be better to say that when casting from integer to boolean, any non-zero integer becomestrue
, and0
becomesfalse
.There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yup- I like that. Int->bool is zero vs non-zero. But bool->int is 0 vs 1