mirror of https://github.com/AMT-Cheif/drift.git
Parse exists expressions
This commit is contained in:
parent
3e910123d2
commit
da07be2da4
|
@ -78,7 +78,10 @@ class TypeResolver {
|
|||
return resolveColumn(expr.resolved as Column);
|
||||
} else if (expr is FunctionExpression) {
|
||||
return resolveFunctionCall(expr);
|
||||
} else if (expr is IsExpression) {
|
||||
} else if (expr is IsExpression ||
|
||||
expr is StringComparisonExpression ||
|
||||
expr is BetweenExpression ||
|
||||
expr is ExistsExpression) {
|
||||
return const ResolveResult(ResolvedType.bool());
|
||||
} else if (expr is BinaryExpression) {
|
||||
final operator = expr.operator.type;
|
||||
|
@ -89,10 +92,6 @@ class TypeResolver {
|
|||
[BasicType.int, BasicType.real, BasicType.text, BasicType.blob]);
|
||||
return ResolveResult(type);
|
||||
}
|
||||
} else if (expr is StringComparisonExpression) {
|
||||
return const ResolveResult(ResolvedType.bool());
|
||||
} else if (expr is BetweenExpression) {
|
||||
return const ResolveResult(ResolvedType.bool());
|
||||
} else if (expr is CaseExpression) {
|
||||
return resolveExpression(expr.whens.first.then);
|
||||
} else if (expr is SubQuery) {
|
||||
|
|
|
@ -145,6 +145,7 @@ abstract class AstVisitor<T> {
|
|||
T visitReference(Reference e);
|
||||
T visitFunction(FunctionExpression e);
|
||||
T visitSubQuery(SubQuery e);
|
||||
T visitExists(ExistsExpression e);
|
||||
T visitCaseExpression(CaseExpression e);
|
||||
T visitWhen(WhenComponent e);
|
||||
|
||||
|
@ -181,6 +182,9 @@ class RecursiveVisitor<T> extends AstVisitor<T> {
|
|||
@override
|
||||
T visitSubQuery(SubQuery e) => visitChildren(e);
|
||||
|
||||
@override
|
||||
T visitExists(ExistsExpression e) => visitChildren(e);
|
||||
|
||||
@override
|
||||
T visitSetComponent(SetComponent e) => visitChildren(e);
|
||||
|
||||
|
|
|
@ -16,3 +16,18 @@ class SubQuery extends Expression {
|
|||
@override
|
||||
bool contentEquals(SubQuery other) => true;
|
||||
}
|
||||
|
||||
class ExistsExpression extends Expression {
|
||||
final SelectStatement select;
|
||||
|
||||
ExistsExpression({@required this.select});
|
||||
|
||||
@override
|
||||
T accept<T>(AstVisitor<T> visitor) => visitor.visitExists(this);
|
||||
|
||||
@override
|
||||
Iterable<AstNode> get childNodes => [select];
|
||||
|
||||
@override
|
||||
bool contentEquals(ExistsExpression other) => true;
|
||||
}
|
||||
|
|
|
@ -33,9 +33,9 @@ class SelectStatement extends Statement with ResultSet {
|
|||
@override
|
||||
Iterable<AstNode> get childNodes {
|
||||
return [
|
||||
if (where != null) where,
|
||||
...columns,
|
||||
if (from != null) ...from,
|
||||
if (where != null) where,
|
||||
if (groupBy != null) groupBy,
|
||||
if (limit != null) limit,
|
||||
if (orderBy != null) orderBy,
|
||||
|
|
|
@ -612,6 +612,13 @@ class Parser {
|
|||
final operator = _previous;
|
||||
final expression = _unary();
|
||||
return UnaryExpression(operator, expression);
|
||||
} else if (_matchOne(TokenType.exists)) {
|
||||
_consume(
|
||||
TokenType.leftParen, 'Expected opening parenthesis after EXISTS');
|
||||
final selectStmt = select();
|
||||
_consume(TokenType.rightParen,
|
||||
'Expected closing paranthesis to finish EXISTS expression');
|
||||
return ExistsExpression(select: selectStmt);
|
||||
}
|
||||
|
||||
return _postfix();
|
||||
|
|
|
@ -35,6 +35,7 @@ enum TokenType {
|
|||
or,
|
||||
tilde,
|
||||
between,
|
||||
exists,
|
||||
|
||||
questionMark,
|
||||
colon,
|
||||
|
@ -104,6 +105,7 @@ const Map<String, TokenType> keywords = {
|
|||
'ALL': TokenType.all,
|
||||
'AND': TokenType.and,
|
||||
'OR': TokenType.or,
|
||||
'EXISTS': TokenType.exists,
|
||||
'BETWEEN': TokenType.between,
|
||||
'DELETE': TokenType.delete,
|
||||
'FROM': TokenType.from,
|
||||
|
|
|
@ -72,6 +72,17 @@ final Map<String, Expression> _testCases = {
|
|||
right: StringLiteral.from(token(TokenType.stringLiteral), '%A%\$'),
|
||||
escape: StringLiteral.from(token(TokenType.stringLiteral), '\$'),
|
||||
),
|
||||
'NOT EXISTS (SELECT * FROM demo)': UnaryExpression(
|
||||
token(TokenType.not),
|
||||
ExistsExpression(
|
||||
select: SelectStatement(
|
||||
columns: [StarResultColumn(null)],
|
||||
from: [
|
||||
TableReference('demo', null),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
};
|
||||
|
||||
void main() {
|
||||
|
|
Loading…
Reference in New Issue