Skip to content

Commit

Permalink
Sqlite: Support translation of ToString
Browse files Browse the repository at this point in the history
* Resolve: dotnet#17223
  • Loading branch information
ralmsdeveloper committed Jan 3, 2020
1 parent bfd0d0e commit dc559cf
Show file tree
Hide file tree
Showing 3 changed files with 96 additions and 3 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,8 @@ public SqliteMethodCallTranslatorProvider([NotNull] RelationalMethodCallTranslat
new SqliteByteArrayMethodTranslator(sqlExpressionFactory),
new SqliteDateTimeAddTranslator(sqlExpressionFactory),
new SqliteMathTranslator(sqlExpressionFactory),
new SqliteStringMethodTranslator(sqlExpressionFactory)
new SqliteObjectToStringTranslator(sqlExpressionFactory),
new SqliteStringMethodTranslator(sqlExpressionFactory),
});
}
}
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.

using System;
using System.Collections.Generic;
using System.Reflection;
using JetBrains.Annotations;
using Microsoft.EntityFrameworkCore.Query;
using Microsoft.EntityFrameworkCore.Query.SqlExpressions;
using Microsoft.EntityFrameworkCore.Utilities;

namespace Microsoft.EntityFrameworkCore.Sqlite.Query.Internal
{
public class SqliteObjectToStringTranslator : IMethodCallTranslator
{
private static readonly HashSet<Type> _typeMapping = new HashSet<Type>
{
typeof(int),
typeof(long),
typeof(DateTime),
typeof(Guid),
typeof(byte),
typeof(byte[]),
typeof(double),
typeof(DateTimeOffset),
typeof(char),
typeof(short),
typeof(float),
typeof(decimal),
typeof(TimeSpan),
typeof(uint),
typeof(ushort),
typeof(ulong),
typeof(sbyte),
};

private readonly ISqlExpressionFactory _sqlExpressionFactory;

public SqliteObjectToStringTranslator([NotNull] ISqlExpressionFactory sqlExpressionFactory)
=> _sqlExpressionFactory = sqlExpressionFactory;

public virtual SqlExpression Translate(SqlExpression instance, MethodInfo method, IReadOnlyList<SqlExpression> arguments)
{
Check.NotNull(method, nameof(method));
Check.NotNull(arguments, nameof(arguments));

return method.Name == nameof(ToString)
&& arguments.Count == 0
&& instance != null
&& _typeMapping.Contains(instance.Type.UnwrapNullableType())
? _sqlExpressionFactory.Convert(instance, typeof(string))
: null;
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -21,8 +21,15 @@ public NorthwindMiscellaneousQuerySqliteTest(NorthwindQuerySqliteFixture<NoopMod
//Fixture.TestSqlLoggerFactory.SetTestOutputHelper(testOutputHelper);
}

public override Task Query_expression_with_to_string_and_contains(bool async)
=> AssertTranslationFailed(() => base.Query_expression_with_to_string_and_contains(async));
public override async Task Query_expression_with_to_string_and_contains(bool async)
{
await base.Query_expression_with_to_string_and_contains(async);

AssertSql(
@"SELECT ""o"".""CustomerID""
FROM ""Orders"" AS ""o""
WHERE ""o"".""OrderDate"" IS NOT NULL AND (('10' = '') OR (instr(CAST(""o"".""EmployeeID"" AS TEXT), '10') > 0))");
}

public override async Task Take_Skip(bool async)
{
Expand Down Expand Up @@ -236,6 +243,36 @@ LIMIT @__p_0
) AS ""t""");
}

public override async Task Select_expression_other_to_string(bool async)
{
await base.Select_expression_other_to_string(async);

AssertSql(
@"SELECT CAST(""o"".""OrderDate"" AS TEXT) AS ""ShipName""
FROM ""Orders"" AS ""o""
WHERE ""o"".""OrderDate"" IS NOT NULL");
}

public override async Task Select_expression_long_to_string(bool async)
{
await base.Select_expression_long_to_string(async);

AssertSql(
@"SELECT CAST(CAST(""o"".""OrderID"" AS INTEGER) AS TEXT) AS ""ShipName""
FROM ""Orders"" AS ""o""
WHERE ""o"".""OrderDate"" IS NOT NULL");
}

public override async Task Select_expression_int_to_string(bool async)
{
await base.Select_expression_int_to_string(async);

AssertSql(
@"SELECT CAST(""o"".""OrderID"" AS TEXT) AS ""ShipName""
FROM ""Orders"" AS ""o""
WHERE ""o"".""OrderDate"" IS NOT NULL");
}

public override Task Complex_nested_query_doesnt_try_binding_to_grandparent_when_parent_returns_complex_result(bool async)
=> null;

Expand Down

0 comments on commit dc559cf

Please sign in to comment.