mirror of https://github.com/AMT-Cheif/drift.git
Support LIKE expressions in the new type resolver
This commit is contained in:
parent
a8ffd0a7f3
commit
523eabaa2a
|
@ -2,6 +2,8 @@ part of 'types.dart';
|
||||||
|
|
||||||
const _expectInt =
|
const _expectInt =
|
||||||
ExactTypeExpectation.laxly(ResolvedType(type: BasicType.int));
|
ExactTypeExpectation.laxly(ResolvedType(type: BasicType.int));
|
||||||
|
const _expectString =
|
||||||
|
ExactTypeExpectation.laxly(ResolvedType(type: BasicType.text));
|
||||||
|
|
||||||
class TypeResolver extends RecursiveVisitor<TypeExpectation, void> {
|
class TypeResolver extends RecursiveVisitor<TypeExpectation, void> {
|
||||||
final TypeInferenceSession session;
|
final TypeInferenceSession session;
|
||||||
|
@ -116,16 +118,20 @@ class TypeResolver extends RecursiveVisitor<TypeExpectation, void> {
|
||||||
|
|
||||||
if (e is NullLiteral) {
|
if (e is NullLiteral) {
|
||||||
type = const ResolvedType(type: BasicType.nullType, nullable: true);
|
type = const ResolvedType(type: BasicType.nullType, nullable: true);
|
||||||
|
session.hintNullability(e, true);
|
||||||
} else if (e is StringLiteral) {
|
} else if (e is StringLiteral) {
|
||||||
type = e.isBinary
|
type = e.isBinary
|
||||||
? const ResolvedType(type: BasicType.blob)
|
? const ResolvedType(type: BasicType.blob)
|
||||||
: const ResolvedType(type: BasicType.text);
|
: const ResolvedType(type: BasicType.text);
|
||||||
|
session.hintNullability(e, false);
|
||||||
} else if (e is BooleanLiteral) {
|
} else if (e is BooleanLiteral) {
|
||||||
type = const ResolvedType.bool();
|
type = const ResolvedType.bool();
|
||||||
|
session.hintNullability(e, false);
|
||||||
} else if (e is NumericLiteral) {
|
} else if (e is NumericLiteral) {
|
||||||
type = e.isInt
|
type = e.isInt
|
||||||
? const ResolvedType(type: BasicType.int)
|
? const ResolvedType(type: BasicType.int)
|
||||||
: const ResolvedType(type: BasicType.real);
|
: const ResolvedType(type: BasicType.real);
|
||||||
|
session.hintNullability(e, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
session.checkAndResolve(e, type, arg);
|
session.checkAndResolve(e, type, arg);
|
||||||
|
@ -243,6 +249,24 @@ class TypeResolver extends RecursiveVisitor<TypeExpectation, void> {
|
||||||
visit(e.operand, const NoTypeExpectation());
|
visit(e.operand, const NoTypeExpectation());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@override
|
||||||
|
void visitStringComparison(
|
||||||
|
StringComparisonExpression e, TypeExpectation arg) {
|
||||||
|
session.checkAndResolve(e, const ResolvedType(type: BasicType.text), arg);
|
||||||
|
session.addRelationship(NullableIfSomeOtherIs(
|
||||||
|
e,
|
||||||
|
[
|
||||||
|
e.left,
|
||||||
|
e.right,
|
||||||
|
if (e.escape != null) e.escape,
|
||||||
|
],
|
||||||
|
));
|
||||||
|
|
||||||
|
visit(e.left, _expectString);
|
||||||
|
visit(e.right, _expectString);
|
||||||
|
visitNullable(e.escape, _expectString);
|
||||||
|
}
|
||||||
|
|
||||||
@override
|
@override
|
||||||
void visitReference(Reference e, TypeExpectation arg) {
|
void visitReference(Reference e, TypeExpectation arg) {
|
||||||
final resolved = e.resolvedColumn;
|
final resolved = e.resolvedColumn;
|
||||||
|
|
|
@ -57,6 +57,7 @@ class BinaryExpression extends Expression {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// A like, glob, match or regexp expression.
|
||||||
class StringComparisonExpression extends Expression {
|
class StringComparisonExpression extends Expression {
|
||||||
final bool not;
|
final bool not;
|
||||||
final Token operator;
|
final Token operator;
|
||||||
|
|
|
@ -127,4 +127,14 @@ void main() {
|
||||||
final offsetType = _resolveFirstVariable('SELECT 0 LIMIT 1, ?');
|
final offsetType = _resolveFirstVariable('SELECT 0 LIMIT 1, ?');
|
||||||
expect(offsetType, int);
|
expect(offsetType, int);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
test('handles string matching expressions', () {
|
||||||
|
final type =
|
||||||
|
_resolveFirstVariable('SELECT * FROM demo WHERE content LIKE ?');
|
||||||
|
expect(type, const ResolvedType(type: BasicType.text));
|
||||||
|
|
||||||
|
final escapedType = _resolveFirstVariable(
|
||||||
|
"SELECT * FROM demo WHERE content LIKE 'foo' ESCAPE ?");
|
||||||
|
expect(escapedType, const ResolvedType(type: BasicType.text));
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue