// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.

// ReSharper disable InconsistentNaming

using System.Data.Odbc;
using System.Data.OleDb;
using System.Linq;
using System.Threading.Tasks;
using EntityFrameworkCore.Jet.FunctionalTests.TestUtilities;
using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Query;
using Microsoft.EntityFrameworkCore.TestUtilities;
using Xunit;

namespace EntityFrameworkCore.Jet.FunctionalTests.Query;

public class SimpleQueryJetTest : SimpleQueryRelationalTestBase
{
    protected override ITestStoreFactory TestStoreFactory
        => JetTestStoreFactory.Instance;

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

        AssertSql(
$"""
@__p_0='3'

SELECT TOP 1 `s`.`Id`, `s`.`Email`, `s`.`Logon`, `s`.`ManagerId`, `s`.`Name`, `s`.`SecondaryManagerId`
FROM `Staff` AS `s`
WHERE `s`.`Id` = {AssertSqlHelper.Parameter("@__p_0")}
""",
//
$"""
@__id_0='1'

SELECT TOP 2 `a`.`Id`, `a`.`Complete`, `a`.`Deleted`, `a`.`PeriodEnd`, `a`.`PeriodStart`, `a`.`StaffId`, `s`.`Id`, `s`.`Email`, `s`.`Logon`, `s`.`ManagerId`, `s`.`Name`, `s`.`SecondaryManagerId`, `s0`.`Id`, `s0`.`Email`, `s0`.`Logon`, `s0`.`ManagerId`, `s0`.`Name`, `s0`.`SecondaryManagerId`, `s1`.`Id`, `s1`.`Email`, `s1`.`Logon`, `s1`.`ManagerId`, `s1`.`Name`, `s1`.`SecondaryManagerId`
FROM ((`Appraisals` AS `a`
INNER JOIN `Staff` AS `s` ON `a`.`StaffId` = `s`.`Id`)
LEFT JOIN `Staff` AS `s0` ON `s`.`ManagerId` = `s0`.`Id`)
LEFT JOIN `Staff` AS `s1` ON `s`.`SecondaryManagerId` = `s1`.`Id`
WHERE `a`.`Id` = {AssertSqlHelper.Parameter("@__id_0")}
""");
    }

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

        AssertSql(
$"""
@__bitterTaste_0='1'

SELECT `i`.`IceCreamId`, `i`.`Name`, `i`.`Taste`
FROM `IceCreams` AS `i`
WHERE `i`.`Taste` = {AssertSqlHelper.Parameter("@__bitterTaste_0")}
""");
    }

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

        AssertSql(
"""
SELECT `i`.`IceCreamId`, `i`.`Name`, `i`.`Taste`
FROM `IceCreams` AS `i`
WHERE `i`.`Taste` = 1
""");
    }

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

        AssertSql(
"""
SELECT `f`.`Id`, `f`.`Taste`
FROM `Food` AS `f`
WHERE `f`.`Taste` = CBYTE(1)
""");
    }

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

        AssertSql(
"""
SELECT `f`.`Taste` AS `Bar`
FROM `Food` AS `f`
""");
    }

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

        AssertSql(
"""
SELECT `a`.`Id`, `a`.`BlogId`, `b`.`Id`, `b`.`IsPhotoBlog`, `b`.`Title`, `b`.`NumberOfPhotos`
FROM `Authors` AS `a`
LEFT JOIN `Blog` AS `b` ON `a`.`BlogId` = `b`.`Id`
""");
    }

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

        AssertSql(
"""
SELECT (
    SELECT COUNT(*)
    FROM `Books` AS `b`
    WHERE `a`.`AuthorId` = `b`.`AuthorId`) AS `BooksCount`
FROM `Authors` AS `a`
""");
    }

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

        AssertSql(
"""
SELECT cast(null as int) AS MyValue
""");
    }

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

        AssertSql(
$"""
@__currentUserId_0='1'

SELECT IIF(`u`.`Id` IN (
        SELECT `u0`.`Id`
        FROM `Memberships` AS `m`
        INNER JOIN `Users` AS `u0` ON `m`.`UserId` = `u0`.`Id`
        WHERE `m`.`GroupId` IN (
            SELECT `m0`.`GroupId`
            FROM `Memberships` AS `m0`
            WHERE `m0`.`UserId` = {AssertSqlHelper.Parameter("@__currentUserId_0")}
        )
    ), TRUE, FALSE) AS `HasAccess`
FROM `Users` AS `u`
""");
    }

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

        AssertSql(
$"""
@__currentUserId_0='1'

SELECT IIF(`u`.`Id` IN (
        SELECT `u0`.`Id`
        FROM (`Memberships` AS `m`
        INNER JOIN `Groups` AS `g` ON `m`.`GroupId` = `g`.`Id`)
        INNER JOIN `Users` AS `u0` ON `m`.`UserId` = `u0`.`Id`
        WHERE `g`.`Id` IN (
            SELECT `g0`.`Id`
            FROM `Memberships` AS `m0`
            INNER JOIN `Groups` AS `g0` ON `m0`.`GroupId` = `g0`.`Id`
            WHERE `m0`.`UserId` = {AssertSqlHelper.Parameter("@__currentUserId_0")}
        )
    ), TRUE, FALSE) AS `HasAccess`
FROM `Users` AS `u`
""");
    }

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

        AssertSql(
$"""
@__currentUserId_0='1'

SELECT IIF(EXISTS (
        SELECT 1
        FROM `Memberships` AS `m`
        INNER JOIN `Users` AS `u0` ON `m`.`UserId` = `u0`.`Id`
        WHERE `m`.`GroupId` IN (
            SELECT `m0`.`GroupId`
            FROM `Memberships` AS `m0`
            WHERE `m0`.`UserId` = {AssertSqlHelper.Parameter("@__currentUserId_0")}
        ) AND `u0`.`Id` = `u`.`Id`), TRUE, FALSE) AS `HasAccess`
FROM `Users` AS `u`
""");
    }

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

        AssertSql(
$"""
@__orderId_0='123456'
@__orderId_0='123456'

SELECT `o`.`Id`, `o`.`CancellationDate`, `o`.`OrderId`, `o`.`ShippingDate`
FROM `OrderItems` AS `o`
INNER JOIN (
    SELECT `o0`.`OrderId` AS `Key`, MAX(IIF(`o0`.`ShippingDate` IS NULL AND `o0`.`CancellationDate` IS NULL, `o0`.`OrderId`, `o0`.`OrderId` - 10000000)) AS `IsPending`
    FROM `OrderItems` AS `o0`
    WHERE `o0`.`OrderId` = {AssertSqlHelper.Parameter("@__orderId_0")}
    GROUP BY `o0`.`OrderId`
) AS `t` ON `o`.`OrderId` = `t`.`Key`
WHERE `o`.`OrderId` = {AssertSqlHelper.Parameter("@__orderId_0")}
ORDER BY `o`.`OrderId`
""");
    }

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

        AssertSql(
$"""
@__orderItemType_1='MyType1' (Nullable = false) (Size = 255)
@__orderItemType_1='MyType1' (Nullable = false) (Size = 255)

SELECT `o1`.`Id`, IIF((
        SELECT TOP 1 `o2`.`Price`
        FROM `OrderItems` AS `o2`
        WHERE `o1`.`Id` = `o2`.`Order26472Id` AND `o2`.`Type` = {AssertSqlHelper.Parameter("@__orderItemType_1")}) IS NULL, 0.0, (
        SELECT TOP 1 `o2`.`Price`
        FROM `OrderItems` AS `o2`
        WHERE `o1`.`Id` = `o2`.`Order26472Id` AND `o2`.`Type` = {AssertSqlHelper.Parameter("@__orderItemType_1")})) AS `SpecialSum`
FROM (
    SELECT TOP 1 `o`.`Id`
    FROM `Orders` AS `o`
    WHERE EXISTS (
        SELECT 1
        FROM `OrderItems` AS `o0`
        WHERE `o`.`Id` = `o0`.`Order26472Id`)
    ORDER BY `o`.`Id`
) AS `t`
INNER JOIN `Orders` AS `o1` ON `t`.`Id` = `o1`.`Id`
ORDER BY `t`.`Id`
""");
    }

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

        AssertSql(
"""
SELECT (
    SELECT MIN(`o`.`HourlyRate`)
    FROM `TimeSheets` AS `t0`
    LEFT JOIN `Order` AS `o` ON `t0`.`OrderId` = `o`.`Id`
    WHERE `t0`.`OrderId` IS NOT NULL AND `t`.`OrderId` = `t0`.`OrderId`) AS `HourlyRate`, (
    SELECT MIN(`c`.`Id`)
    FROM (`TimeSheets` AS `t1`
    INNER JOIN `Project` AS `p` ON `t1`.`ProjectId` = `p`.`Id`)
    LEFT JOIN `Customers` AS `c` ON `p`.`CustomerId` = `c`.`Id`
    WHERE (`t1`.`OrderId` IS NOT NULL AND `t`.`OrderId` = `t1`.`OrderId`) AND (`p`.`CustomerId` IS NOT NULL AND `c`.`Id` IS NOT NULL)) AS `CustomerId`, (
    SELECT MIN(`c0`.`Name`)
    FROM (`TimeSheets` AS `t2`
    INNER JOIN `Project` AS `p0` ON `t2`.`ProjectId` = `p0`.`Id`)
    LEFT JOIN `Customers` AS `c0` ON `p0`.`CustomerId` = `c0`.`Id`
    WHERE (`t2`.`OrderId` IS NOT NULL AND `t`.`OrderId` = `t2`.`OrderId`) AND (`p0`.`CustomerId` IS NOT NULL AND `c0`.`Id` IS NOT NULL)) AS `CustomerName`
FROM `TimeSheets` AS `t`
WHERE `t`.`OrderId` IS NOT NULL
GROUP BY `t`.`OrderId`
""");
    }

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

        AssertSql(
"""
SELECT `o`.`CustomerId`, (
    SELECT MIN(`o0`.`HourlyRate`)
    FROM `Order` AS `o0`
    WHERE `o0`.`CustomerId` = `o`.`CustomerId`) AS `CustomerMinHourlyRate`, MIN(`o`.`HourlyRate`) AS `HourlyRate`, COUNT(*) AS `Count`
FROM `Order` AS `o`
WHERE `o`.`Number` <> 'A1' OR `o`.`Number` IS NULL
GROUP BY `o`.`CustomerId`, `o`.`Number`
""");
    }

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

        AssertSql(
"""
SELECT [t].[Value] AS [A], (
    SELECT MAX([t0].[Id])
    FROM [Table] AS [t0]
    WHERE [t0].[Value] = (MAX([t].[Id]) * 6) OR (([t0].[Value] IS NULL) AND (MAX([t].[Id]) IS NULL))) AS [B]
FROM [Table] AS [t]
GROUP BY [t].[Value]
""");
    }

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

        AssertSql(
"""
SELECT [t].[Value] AS [A], COALESCE(SUM([t].[Id]), 0) AS [B], COALESCE((
    SELECT TOP(1) COALESCE(SUM([t].[Id]), 0) + COALESCE(SUM([t0].[Id]), 0)
    FROM [Table] AS [t0]
    GROUP BY [t0].[Value]
    ORDER BY (SELECT 1)), 0) AS [C]
FROM [Table] AS [t]
GROUP BY [t].[Value]
""");
    }

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

        AssertSql(
"""
SELECT (
    SELECT COUNT(*)
    FROM (
        SELECT DISTINCT [c].[Value1]
        FROM (
            SELECT [p0].[Id], [p0].[Child1Id], [p0].[Child2Id], [p0].[ChildFilter1Id], [p0].[ChildFilter2Id], 1 AS [Key]
            FROM [Parents] AS [p0]
        ) AS [t1]
        LEFT JOIN [Child1] AS [c] ON [t1].[Child1Id] = [c].[Id]
        WHERE [t].[Key] = [t1].[Key]
    ) AS [t0]) AS [Test1], (
    SELECT COUNT(*)
    FROM (
        SELECT DISTINCT [c0].[Value2]
        FROM (
            SELECT [p1].[Id], [p1].[Child1Id], [p1].[Child2Id], [p1].[ChildFilter1Id], [p1].[ChildFilter2Id], 1 AS [Key]
            FROM [Parents] AS [p1]
        ) AS [t3]
        LEFT JOIN [Child2] AS [c0] ON [t3].[Child2Id] = [c0].[Id]
        WHERE [t].[Key] = [t3].[Key]
    ) AS [t2]) AS [Test2]
FROM (
    SELECT 1 AS [Key]
    FROM [Parents] AS [p]
) AS [t]
GROUP BY [t].[Key]
""");
    }

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

        AssertSql(
"""
SELECT (
    SELECT COUNT(*)
    FROM (
        SELECT DISTINCT [t2].[Value1]
        FROM (
            SELECT [p0].[Id], [p0].[Child1Id], [p0].[Child2Id], [p0].[ChildFilter1Id], [p0].[ChildFilter2Id], 1 AS [Key]
            FROM [Parents] AS [p0]
        ) AS [t0]
        LEFT JOIN (
            SELECT [c].[Id], [c].[Filter1], [c].[Value1]
            FROM [ChildFilter1] AS [c]
            WHERE [c].[Filter1] = N'Filter1'
        ) AS [t2] ON [t0].[ChildFilter1Id] = [t2].[Id]
        WHERE [t].[Key] = [t0].[Key]
    ) AS [t1]) AS [Test1], (
    SELECT COUNT(*)
    FROM (
        SELECT DISTINCT [t5].[Value2]
        FROM (
            SELECT [p1].[Id], [p1].[Child1Id], [p1].[Child2Id], [p1].[ChildFilter1Id], [p1].[ChildFilter2Id], 1 AS [Key]
            FROM [Parents] AS [p1]
        ) AS [t4]
        LEFT JOIN (
            SELECT [c0].[Id], [c0].[Filter2], [c0].[Value2]
            FROM [ChildFilter2] AS [c0]
            WHERE [c0].[Filter2] = N'Filter2'
        ) AS [t5] ON [t4].[ChildFilter2Id] = [t5].[Id]
        WHERE [t].[Key] = [t4].[Key]
    ) AS [t3]) AS [Test2]
FROM (
    SELECT 1 AS [Key]
    FROM [Parents] AS [p]
) AS [t]
GROUP BY [t].[Key]
""");
    }

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

        AssertSql(
"""
SELECT (
    SELECT TOP 1 `c1`.`SomeOtherNullableDateTime`
    FROM `Child26744` AS `c1`
    WHERE `p`.`Id` = `c1`.`ParentId` AND `c1`.`SomeNullableDateTime` IS NULL
    ORDER BY `c1`.`SomeInteger`)
FROM `Parents` AS `p`
WHERE EXISTS (
    SELECT 1
    FROM `Child26744` AS `c`
    WHERE `p`.`Id` = `c`.`ParentId` AND `c`.`SomeNullableDateTime` IS NULL) AND (
    SELECT TOP 1 `c0`.`SomeOtherNullableDateTime`
    FROM `Child26744` AS `c0`
    WHERE `p`.`Id` = `c0`.`ParentId` AND `c0`.`SomeNullableDateTime` IS NULL
    ORDER BY `c0`.`SomeInteger`) IS NOT NULL
""");
    }

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

        AssertSql(
"""
SELECT [t0].[SomeNullableDateTime]
FROM [Parents] AS [p]
INNER JOIN (
    SELECT [t].[ParentId], [t].[SomeNullableDateTime], [t].[SomeOtherNullableDateTime]
    FROM (
        SELECT [c].[ParentId], [c].[SomeNullableDateTime], [c].[SomeOtherNullableDateTime], ROW_NUMBER() OVER(PARTITION BY [c].[ParentId] ORDER BY [c].[SomeInteger]) AS [row]
        FROM [Child26744] AS [c]
        WHERE [c].[SomeNullableDateTime] IS NULL
    ) AS [t]
    WHERE [t].[row] <= 1
) AS [t0] ON [p].[Id] = [t0].[ParentId]
WHERE [t0].[SomeOtherNullableDateTime] IS NOT NULL
""");
    }

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

        AssertSql(
$"""
@__date_0='2012-12-12T00:00:00.0000000' (DbType = DateTime)

SELECT `m`.`Id`, `m`.`SomeDate`
FROM `MyEntities` AS `m`
WHERE `m`.`SomeDate` = CDATE({AssertSqlHelper.Parameter("@__date_0")})
""",
//
$"""
@__date_0='2012-12-12T00:00:00.0000000' (DbType = DateTime)

SELECT `m`.`Id`, `m`.`SomeDate`
FROM `MyEntities` AS `m`
WHERE `dbo`.`ModifyDate`(`m`.`SomeDate`) = CDATE({AssertSqlHelper.Parameter("@__date_0")})
""");
    }

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

        AssertSql(
"""
SELECT TOP 123456 `t`.`JSON`
FROM `TableData` AS `t`
INNER JOIN (
    SELECT DISTINCT `i`.`Parcel`
    FROM `IndexData` AS `i`
    WHERE `i`.`Parcel` = 'some condition'
    GROUP BY `i`.`Parcel`, `i`.`RowId`
    HAVING COUNT(*) = 1
) AS `t0` ON `t`.`ParcelNumber` = `t0`.`Parcel`
WHERE `t`.`TableId` = 123
ORDER BY `t`.`ParcelNumber`
""");
    }

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

        AssertSql(
"""
SELECT `a`.`Id`, `a`.`Discriminator`, `a`.`Species`, `a`.`Name`, `a`.`EdcuationLevel`, `a`.`FavoriteToy`
FROM `Animals` AS `a`
WHERE `a`.`Discriminator` IN ('Cat', 'Dog') AND (`a`.`Species` LIKE 'F%')
""");
    }

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

        AssertSql(
"""
SELECT `a`.`Id`, `a`.`Species`, `p`.`Name`, `c`.`EdcuationLevel`, `d`.`FavoriteToy`, IIF(`d`.`Id` IS NOT NULL, 'Dog', IIF(`c`.`Id` IS NOT NULL, 'Cat', NULL)) AS `Discriminator`
FROM ((`Animals` AS `a`
LEFT JOIN `Pets` AS `p` ON `a`.`Id` = `p`.`Id`)
LEFT JOIN `Cats` AS `c` ON `a`.`Id` = `c`.`Id`)
LEFT JOIN `Dogs` AS `d` ON `a`.`Id` = `d`.`Id`
WHERE (`d`.`Id` IS NOT NULL OR `c`.`Id` IS NOT NULL) AND (`a`.`Species` LIKE 'F%')
""");
    }

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

        AssertSql(
"""
SELECT `t`.`Id`, `t`.`Species`, `t`.`Name`, `t`.`EdcuationLevel`, `t`.`FavoriteToy`, `t`.`Discriminator`
FROM (
    SELECT `c`.`Id`, `c`.`Species`, `c`.`Name`, `c`.`EdcuationLevel`, NULL AS `FavoriteToy`, 'Cat' AS `Discriminator`
    FROM `Cats` AS `c`
    UNION ALL
    SELECT `d`.`Id`, `d`.`Species`, `d`.`Name`, NULL AS `EdcuationLevel`, `d`.`FavoriteToy`, 'Dog' AS `Discriminator`
    FROM `Dogs` AS `d`
) AS `t`
WHERE `t`.`Species` LIKE 'F%'
""");
    }

    [ConditionalTheory]
    [MemberData(nameof(IsAsyncData))]
    public virtual async Task Muliple_occurrences_of_FromSql_in_group_by_aggregate(bool async)
    {
        var contextFactory = await InitializeAsync<Context27427>();
        using var context = contextFactory.CreateContext();
        
        var parameter = TestEnvironment.DataAccessProviderFactory.CreateParameter();
        if (parameter is OdbcParameter odbcParameter)
        {
            odbcParameter.Value = 1;
            odbcParameter.OdbcType = OdbcType.Int;//Looks like odbcparameter doesnt automatically infer the type
        }
        else if (parameter is OleDbParameter oleDbParameter)
        {
            oleDbParameter.Value = 1;
        }
        
        var query = context.DemoEntities
            .FromSqlRaw("SELECT * FROM DemoEntities WHERE Id = {0}", parameter)
            .Select(e => e.Id);

        var query2 = context.DemoEntities
            .Where(e => query.Contains(e.Id))
            .GroupBy(e => e.Id)
            .Select(g => new { g.Key, Aggregate = g.Count() });

        if (async)
        {
            await query2.ToListAsync();
        }
        else
        {
            query2.ToList();
        }

        AssertSql(
$"""
p0='1'

SELECT `d`.`Id` AS `Key`, COUNT(*) AS `Aggregate`
FROM `DemoEntities` AS `d`
WHERE `d`.`Id` IN (
    SELECT `e`.`Id`
    FROM (
        SELECT * FROM DemoEntities WHERE Id = {AssertSqlHelper.Parameter("@p0")}
    ) AS `e`
)
GROUP BY `d`.`Id`
""");
    }

    protected class Context27427 : DbContext
    {
        public Context27427(DbContextOptions options)
            : base(options)
        {
        }

        public DbSet<DemoEntity> DemoEntities { get; set; }
    }

    protected class DemoEntity
    {
        public int Id { get; set; }
    }
}
