Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
jobily
Efcore.Pg
提交
a1aa03ed
E
Efcore.Pg
项目概览
jobily
/
Efcore.Pg
12 个月 前同步成功
通知
1
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
DevOps
流水线
流水线任务
计划
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
E
Efcore.Pg
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
DevOps
DevOps
流水线
流水线任务
计划
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
流水线任务
提交
Issue看板
体验新版 GitCode,发现更多精彩内容 >>
提交
a1aa03ed
编写于
7月 26, 2022
作者:
S
Shay Rojansky
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
Implement bulk delete
Following
https://github.com/dotnet/efcore/pull/28492
Part of #2450
上级
2524b30e
变更
21
隐藏空白更改
内联
并排
Showing
21 changed file
with
1400 addition
and
0 deletion
+1400
-0
src/EFCore.PG/Extensions/NpgsqlServiceCollectionExtensions.cs
...EFCore.PG/Extensions/NpgsqlServiceCollectionExtensions.cs
+1
-0
src/EFCore.PG/Query/Expressions/Internal/PostgresDeleteExpression.cs
...PG/Query/Expressions/Internal/PostgresDeleteExpression.cs
+85
-0
src/EFCore.PG/Query/Internal/NonQueryConvertingExpressionVisitor.cs
....PG/Query/Internal/NonQueryConvertingExpressionVisitor.cs
+86
-0
src/EFCore.PG/Query/Internal/NpgsqlParameterBasedSqlProcessor.cs
...ore.PG/Query/Internal/NpgsqlParameterBasedSqlProcessor.cs
+12
-0
src/EFCore.PG/Query/Internal/NpgsqlQuerySqlGenerator.cs
src/EFCore.PG/Query/Internal/NpgsqlQuerySqlGenerator.cs
+58
-0
src/EFCore.PG/Query/Internal/NpgsqlQueryableMethodTranslatingExpressionVisitor.cs
...rnal/NpgsqlQueryableMethodTranslatingExpressionVisitor.cs
+57
-0
src/EFCore.PG/Query/Internal/NpgsqlQueryableMethodTranslatingExpressionVisitorFactory.cs
...gsqlQueryableMethodTranslatingExpressionVisitorFactory.cs
+19
-0
test/EFCore.PG.FunctionalTests/BulkUpdates/FiltersInheritanceBulkUpdatesNpgsqlFixture.cs
...BulkUpdates/FiltersInheritanceBulkUpdatesNpgsqlFixture.cs
+10
-0
test/EFCore.PG.FunctionalTests/BulkUpdates/FiltersInheritanceBulkUpdatesNpgsqlTest.cs
...ts/BulkUpdates/FiltersInheritanceBulkUpdatesNpgsqlTest.cs
+78
-0
test/EFCore.PG.FunctionalTests/BulkUpdates/InheritanceBulkUpdatesNpgsqlFixture.cs
...lTests/BulkUpdates/InheritanceBulkUpdatesNpgsqlFixture.cs
+10
-0
test/EFCore.PG.FunctionalTests/BulkUpdates/InheritanceBulkUpdatesNpgsqlTest.cs
...onalTests/BulkUpdates/InheritanceBulkUpdatesNpgsqlTest.cs
+77
-0
test/EFCore.PG.FunctionalTests/BulkUpdates/NorthwindBulkUpdatesNpgsqlFixture.cs
...nalTests/BulkUpdates/NorthwindBulkUpdatesNpgsqlFixture.cs
+50
-0
test/EFCore.PG.FunctionalTests/BulkUpdates/NorthwindBulkUpdatesNpgsqlTest.cs
...tionalTests/BulkUpdates/NorthwindBulkUpdatesNpgsqlTest.cs
+506
-0
test/EFCore.PG.FunctionalTests/BulkUpdates/TPCFiltersInheritanceBulkUpdatesNpgsqlFixture.cs
...kUpdates/TPCFiltersInheritanceBulkUpdatesNpgsqlFixture.cs
+6
-0
test/EFCore.PG.FunctionalTests/BulkUpdates/TPCFiltersInheritanceBulkUpdatesNpgsqlTest.cs
...BulkUpdates/TPCFiltersInheritanceBulkUpdatesNpgsqlTest.cs
+87
-0
test/EFCore.PG.FunctionalTests/BulkUpdates/TPCInheritanceBulkUpdatesNpgsqlFixture.cs
...sts/BulkUpdates/TPCInheritanceBulkUpdatesNpgsqlFixture.cs
+13
-0
test/EFCore.PG.FunctionalTests/BulkUpdates/TPCInheritanceBulkUpdatesNpgsqlTest.cs
...lTests/BulkUpdates/TPCInheritanceBulkUpdatesNpgsqlTest.cs
+88
-0
test/EFCore.PG.FunctionalTests/BulkUpdates/TPTFiltersInheritanceBulkUpdatesNpgsqlFixture.cs
...kUpdates/TPTFiltersInheritanceBulkUpdatesNpgsqlFixture.cs
+6
-0
test/EFCore.PG.FunctionalTests/BulkUpdates/TPTFiltersInheritanceBulkUpdatesNpgsqlTest.cs
...BulkUpdates/TPTFiltersInheritanceBulkUpdatesNpgsqlTest.cs
+77
-0
test/EFCore.PG.FunctionalTests/BulkUpdates/TPTInheritanceBulkUpdatesNpgsqlFixture.cs
...sts/BulkUpdates/TPTInheritanceBulkUpdatesNpgsqlFixture.cs
+10
-0
test/EFCore.PG.FunctionalTests/BulkUpdates/TPTInheritanceBulkUpdatesNpgsqlTest.cs
...lTests/BulkUpdates/TPTInheritanceBulkUpdatesNpgsqlTest.cs
+64
-0
未找到文件。
src/EFCore.PG/Extensions/NpgsqlServiceCollectionExtensions.cs
浏览文件 @
a1aa03ed
...
@@ -105,6 +105,7 @@ public static IServiceCollection AddEntityFrameworkNpgsql(this IServiceCollectio
...
@@ -105,6 +105,7 @@ public static IServiceCollection AddEntityFrameworkNpgsql(this IServiceCollectio
.
TryAdd
<
IHistoryRepository
,
NpgsqlHistoryRepository
>()
.
TryAdd
<
IHistoryRepository
,
NpgsqlHistoryRepository
>()
.
TryAdd
<
ICompiledQueryCacheKeyGenerator
,
NpgsqlCompiledQueryCacheKeyGenerator
>()
.
TryAdd
<
ICompiledQueryCacheKeyGenerator
,
NpgsqlCompiledQueryCacheKeyGenerator
>()
.
TryAdd
<
IExecutionStrategyFactory
,
NpgsqlExecutionStrategyFactory
>()
.
TryAdd
<
IExecutionStrategyFactory
,
NpgsqlExecutionStrategyFactory
>()
.
TryAdd
<
IQueryableMethodTranslatingExpressionVisitorFactory
,
NpgsqlQueryableMethodTranslatingExpressionVisitorFactory
>()
.
TryAdd
<
IMethodCallTranslatorProvider
,
NpgsqlMethodCallTranslatorProvider
>()
.
TryAdd
<
IMethodCallTranslatorProvider
,
NpgsqlMethodCallTranslatorProvider
>()
.
TryAdd
<
IAggregateMethodCallTranslatorProvider
,
NpgsqlAggregateMethodCallTranslatorProvider
>()
.
TryAdd
<
IAggregateMethodCallTranslatorProvider
,
NpgsqlAggregateMethodCallTranslatorProvider
>()
.
TryAdd
<
IMemberTranslatorProvider
,
NpgsqlMemberTranslatorProvider
>()
.
TryAdd
<
IMemberTranslatorProvider
,
NpgsqlMemberTranslatorProvider
>()
...
...
src/EFCore.PG/Query/Expressions/Internal/PostgresDeleteExpression.cs
0 → 100644
浏览文件 @
a1aa03ed
namespace
Npgsql.EntityFrameworkCore.PostgreSQL.Query.Expressions.Internal
;
public
sealed
class
PostgresDeleteExpression
:
Expression
,
IPrintableExpression
{
/// <summary>
/// The tables that rows are to be deleted from.
/// </summary>
public
TableExpression
Table
{
get
;
}
/// <summary>
/// Additional tables which can be referenced in the predicate.
/// </summary>
public
IReadOnlyList
<
TableExpressionBase
>
FromItems
{
get
;
}
/// <summary>
/// The WHERE predicate for the DELETE.
/// </summary>
public
SqlExpression
?
Predicate
{
get
;
}
public
PostgresDeleteExpression
(
TableExpression
table
,
IReadOnlyList
<
TableExpressionBase
>
fromItems
,
SqlExpression
?
predicate
)
=>
(
Table
,
FromItems
,
Predicate
)
=
(
table
,
fromItems
,
predicate
);
/// <inheritdoc />
public
override
Type
Type
=>
typeof
(
object
);
/// <inheritdoc />
public
override
ExpressionType
NodeType
=>
ExpressionType
.
Extension
;
protected
override
Expression
VisitChildren
(
ExpressionVisitor
visitor
)
=>
Predicate
is
null
?
this
:
Update
((
SqlExpression
?)
visitor
.
Visit
(
Predicate
));
public
PostgresDeleteExpression
Update
(
SqlExpression
?
predicate
)
=>
predicate
==
Predicate
?
this
:
new
PostgresDeleteExpression
(
Table
,
FromItems
,
predicate
);
public
void
Print
(
ExpressionPrinter
expressionPrinter
)
{
expressionPrinter
.
AppendLine
(
$"DELETE FROM
{
Table
.
Name
}
AS
{
Table
.
Alias
}
"
);
if
(
FromItems
.
Count
>
0
)
{
var
first
=
true
;
foreach
(
var
fromItem
in
FromItems
)
{
if
(
first
)
{
expressionPrinter
.
Append
(
"USING "
);
first
=
false
;
}
else
{
expressionPrinter
.
Append
(
", "
);
}
expressionPrinter
.
Visit
(
fromItem
);
}
}
if
(
Predicate
is
not
null
)
{
expressionPrinter
.
Append
(
"WHERE "
);
expressionPrinter
.
Visit
(
Predicate
);
}
}
/// <inheritdoc />
public
override
bool
Equals
(
object
?
obj
)
=>
obj
!=
null
&&
(
ReferenceEquals
(
this
,
obj
)
||
obj
is
PostgresDeleteExpression
pgDeleteExpression
&&
Equals
(
pgDeleteExpression
));
private
bool
Equals
(
PostgresDeleteExpression
pgDeleteExpression
)
=>
Table
==
pgDeleteExpression
.
Table
&&
FromItems
.
SequenceEqual
(
pgDeleteExpression
.
FromItems
)
&&
(
Predicate
is
null
?
pgDeleteExpression
.
Predicate
is
null
:
Predicate
.
Equals
(
pgDeleteExpression
.
Predicate
));
/// <inheritdoc />
public
override
int
GetHashCode
()
=>
Table
.
GetHashCode
();
}
src/EFCore.PG/Query/Internal/NonQueryConvertingExpressionVisitor.cs
0 → 100644
浏览文件 @
a1aa03ed
using
Npgsql.EntityFrameworkCore.PostgreSQL.Query.Expressions.Internal
;
namespace
Npgsql.EntityFrameworkCore.PostgreSQL.Query.Internal
;
/// <summary>
/// Converts the relational <see cref="NonQueryExpression" /> into a PG-specific <see cref="PostgresDeleteExpression" />, which
/// precisely models a DELETE statement in PostgreSQL. This is done to handle the PG-specific USING syntax for table joining.
/// </summary>
public
class
NonQueryConvertingExpressionVisitor
:
ExpressionVisitor
{
public
virtual
Expression
Process
(
Expression
node
)
=>
node
switch
{
DeleteExpression
deleteExpression
=>
VisitDelete
(
deleteExpression
),
_
=>
node
};
protected
virtual
Expression
VisitDelete
(
DeleteExpression
deleteExpression
)
{
var
selectExpression
=
deleteExpression
.
SelectExpression
;
if
(
selectExpression
.
Offset
!=
null
||
selectExpression
.
Limit
!=
null
||
selectExpression
.
Having
!=
null
||
selectExpression
.
Orderings
.
Count
>
0
||
selectExpression
.
GroupBy
.
Count
>
0
||
selectExpression
.
Projection
.
Count
>
0
)
{
throw
new
InvalidOperationException
(
RelationalStrings
.
ExecuteOperationWithUnsupportedOperatorInSqlGeneration
(
nameof
(
RelationalQueryableExtensions
.
ExecuteDelete
)));
}
var
fromItems
=
new
List
<
TableExpressionBase
>();
SqlExpression
?
joinPredicates
=
null
;
// The SelectExpression also contains the target table being modified (same as deleteExpression.Table).
// If it has additional inner joins, use the PostgreSQL-specific USING syntax to express the join.
// Note that the non-join TableExpression isn't necessary the target table - through projection the last table being
// joined may be the one being modified.
foreach
(
var
tableBase
in
selectExpression
.
Tables
)
{
switch
(
tableBase
)
{
case
TableExpression
tableExpression
:
if
(
tableExpression
!=
deleteExpression
.
Table
)
{
fromItems
.
Add
(
tableExpression
);
}
break
;
case
InnerJoinExpression
{
Table
:
{
}
tableExpression
}
innerJoinExpression
:
if
(
tableExpression
!=
deleteExpression
.
Table
)
{
fromItems
.
Add
(
tableExpression
);
}
joinPredicates
=
joinPredicates
is
null
?
innerJoinExpression
.
JoinPredicate
:
new
SqlBinaryExpression
(
ExpressionType
.
AndAlso
,
joinPredicates
,
innerJoinExpression
.
JoinPredicate
,
typeof
(
bool
),
innerJoinExpression
.
JoinPredicate
.
TypeMapping
);
break
;
default
:
throw
new
InvalidOperationException
(
RelationalStrings
.
ExecuteOperationWithUnsupportedOperatorInSqlGeneration
(
nameof
(
RelationalQueryableExtensions
.
ExecuteDelete
)));
}
}
// Combine the join predicates (if any) before the user-provided predicate
var
predicate
=
(
joinPredicates
,
selectExpression
.
Predicate
)
switch
{
(
null
,
not
null
)
=>
selectExpression
.
Predicate
,
(
not
null
,
null
)
=>
joinPredicates
,
(
null
,
null
)
=>
null
,
(
not
null
,
not
null
)
=>
new
SqlBinaryExpression
(
ExpressionType
.
AndAlso
,
joinPredicates
,
selectExpression
.
Predicate
,
typeof
(
bool
),
joinPredicates
.
TypeMapping
)
};
return
new
PostgresDeleteExpression
(
deleteExpression
.
Table
,
fromItems
,
predicate
);
}
}
src/EFCore.PG/Query/Internal/NpgsqlParameterBasedSqlProcessor.cs
浏览文件 @
a1aa03ed
...
@@ -9,6 +9,18 @@ public class NpgsqlParameterBasedSqlProcessor : RelationalParameterBasedSqlProce
...
@@ -9,6 +9,18 @@ public class NpgsqlParameterBasedSqlProcessor : RelationalParameterBasedSqlProce
{
{
}
}
public
override
Expression
Optimize
(
Expression
queryExpression
,
IReadOnlyDictionary
<
string
,
object
?>
parametersValues
,
out
bool
canCache
)
{
queryExpression
=
base
.
Optimize
(
queryExpression
,
parametersValues
,
out
canCache
);
queryExpression
=
new
NonQueryConvertingExpressionVisitor
().
Process
(
queryExpression
);
return
queryExpression
;
}
/// <inheritdoc />
/// <inheritdoc />
protected
override
Expression
ProcessSqlNullability
(
protected
override
Expression
ProcessSqlNullability
(
Expression
selectExpression
,
IReadOnlyDictionary
<
string
,
object
?>
parametersValues
,
out
bool
canCache
)
Expression
selectExpression
,
IReadOnlyDictionary
<
string
,
object
?>
parametersValues
,
out
bool
canCache
)
...
...
src/EFCore.PG/Query/Internal/NpgsqlQuerySqlGenerator.cs
浏览文件 @
a1aa03ed
...
@@ -44,6 +44,7 @@ protected override Expression VisitExtension(Expression extensionExpression)
...
@@ -44,6 +44,7 @@ protected override Expression VisitExtension(Expression extensionExpression)
PostgresAnyExpression
anyExpression
=>
VisitArrayAny
(
anyExpression
),
PostgresAnyExpression
anyExpression
=>
VisitArrayAny
(
anyExpression
),
PostgresArrayIndexExpression
arrayIndexExpression
=>
VisitArrayIndex
(
arrayIndexExpression
),
PostgresArrayIndexExpression
arrayIndexExpression
=>
VisitArrayIndex
(
arrayIndexExpression
),
PostgresBinaryExpression
binaryExpression
=>
VisitPostgresBinary
(
binaryExpression
),
PostgresBinaryExpression
binaryExpression
=>
VisitPostgresBinary
(
binaryExpression
),
PostgresDeleteExpression
deleteExpression
=>
VisitPostgresDelete
(
deleteExpression
),
PostgresFunctionExpression
functionExpression
=>
VisitPostgresFunction
(
functionExpression
),
PostgresFunctionExpression
functionExpression
=>
VisitPostgresFunction
(
functionExpression
),
PostgresILikeExpression
iLikeExpression
=>
VisitILike
(
iLikeExpression
),
PostgresILikeExpression
iLikeExpression
=>
VisitILike
(
iLikeExpression
),
PostgresJsonTraversalExpression
jsonTraversalExpression
=>
VisitJsonPathTraversal
(
jsonTraversalExpression
),
PostgresJsonTraversalExpression
jsonTraversalExpression
=>
VisitJsonPathTraversal
(
jsonTraversalExpression
),
...
@@ -206,6 +207,45 @@ protected override Expression VisitSqlBinary(SqlBinaryExpression binary)
...
@@ -206,6 +207,45 @@ protected override Expression VisitSqlBinary(SqlBinaryExpression binary)
}
}
}
}
protected
override
void
GenerateRootCommand
(
Expression
rootExpression
)
{
switch
(
rootExpression
)
{
case
PostgresDeleteExpression
pgDeleteExpression
:
VisitPostgresDelete
(
pgDeleteExpression
);
return
;
default
:
base
.
GenerateRootCommand
(
rootExpression
);
return
;
}
}
// NonQueryConvertingExpressionVisitor converts the relational DeleteExpression to PostgresDeleteExpression, so we should never
// get here
protected
override
Expression
VisitDelete
(
DeleteExpression
deleteExpression
)
=>
throw
new
InvalidOperationException
(
"Inconceivable!"
);
protected
virtual
Expression
VisitPostgresDelete
(
PostgresDeleteExpression
pgDeleteExpression
)
{
Sql
.
Append
(
"DELETE FROM "
);
Visit
(
pgDeleteExpression
.
Table
);
if
(
pgDeleteExpression
.
FromItems
.
Count
>
0
)
{
Sql
.
AppendLine
().
Append
(
"USING "
);
GenerateList
(
pgDeleteExpression
.
FromItems
,
t
=>
Visit
(
t
),
sql
=>
sql
.
Append
(
", "
));
}
if
(
pgDeleteExpression
.
Predicate
!=
null
)
{
Sql
.
AppendLine
().
Append
(
"WHERE "
);
Visit
(
pgDeleteExpression
.
Predicate
);
}
return
pgDeleteExpression
;
}
protected
virtual
Expression
VisitPostgresNewArray
(
PostgresNewArrayExpression
postgresNewArrayExpression
)
protected
virtual
Expression
VisitPostgresNewArray
(
PostgresNewArrayExpression
postgresNewArrayExpression
)
{
{
Debug
.
Assert
(
postgresNewArrayExpression
.
TypeMapping
is
not
null
);
Debug
.
Assert
(
postgresNewArrayExpression
.
TypeMapping
is
not
null
);
...
@@ -769,4 +809,22 @@ public virtual Expression VisitPostgresFunction(PostgresFunctionExpression e)
...
@@ -769,4 +809,22 @@ public virtual Expression VisitPostgresFunction(PostgresFunctionExpression e)
private
static
bool
RequiresBrackets
(
SqlExpression
expression
)
private
static
bool
RequiresBrackets
(
SqlExpression
expression
)
=>
expression
is
SqlBinaryExpression
||
expression
is
LikeExpression
||
expression
is
PostgresBinaryExpression
;
=>
expression
is
SqlBinaryExpression
||
expression
is
LikeExpression
||
expression
is
PostgresBinaryExpression
;
private
void
GenerateList
<
T
>(
IReadOnlyList
<
T
>
items
,
Action
<
T
>
generationAction
,
Action
<
IRelationalCommandBuilder
>?
joinAction
=
null
)
{
joinAction
??=
(
isb
=>
isb
.
Append
(
", "
));
for
(
var
i
=
0
;
i
<
items
.
Count
;
i
++)
{
if
(
i
>
0
)
{
joinAction
(
Sql
);
}
generationAction
(
items
[
i
]);
}
}
}
}
\ No newline at end of file
src/EFCore.PG/Query/Internal/NpgsqlQueryableMethodTranslatingExpressionVisitor.cs
0 → 100644
浏览文件 @
a1aa03ed
using
System.Diagnostics.CodeAnalysis
;
namespace
Npgsql.EntityFrameworkCore.PostgreSQL.Query.Internal
;
public
class
NpgsqlQueryableMethodTranslatingExpressionVisitor
:
RelationalQueryableMethodTranslatingExpressionVisitor
{
public
NpgsqlQueryableMethodTranslatingExpressionVisitor
(
QueryableMethodTranslatingExpressionVisitorDependencies
dependencies
,
RelationalQueryableMethodTranslatingExpressionVisitorDependencies
relationalDependencies
,
QueryCompilationContext
queryCompilationContext
)
:
base
(
dependencies
,
relationalDependencies
,
queryCompilationContext
)
{
}
protected
override
bool
IsValidSelectExpressionForExecuteDelete
(
SelectExpression
selectExpression
,
EntityShaperExpression
entityShaperExpression
,
[
NotNullWhen
(
true
)]
out
TableExpression
?
tableExpression
)
{
// The default relational behavior is to allow only single-table expressions, and the only permitted feature is a predicate.
// Here we extend this to also inner joins to tables, which we generate via the PostgreSQL-specific USING construct.
if
(
selectExpression
.
Offset
==
null
&&
selectExpression
.
Limit
==
null
// If entity type has primary key then Distinct is no-op
&&
(!
selectExpression
.
IsDistinct
||
entityShaperExpression
.
EntityType
.
FindPrimaryKey
()
!=
null
)
&&
selectExpression
.
GroupBy
.
Count
==
0
&&
selectExpression
.
Having
==
null
&&
selectExpression
.
Orderings
.
Count
==
0
)
{
TableExpressionBase
?
table
=
null
;
if
(
selectExpression
.
Tables
.
Count
==
1
)
{
table
=
selectExpression
.
Tables
[
0
];
}
else
if
(
selectExpression
.
Tables
.
All
(
t
=>
t
is
TableExpression
or
InnerJoinExpression
))
{
var
projectionBindingExpression
=
(
ProjectionBindingExpression
)
entityShaperExpression
.
ValueBufferExpression
;
var
entityProjectionExpression
=
(
EntityProjectionExpression
)
selectExpression
.
GetProjection
(
projectionBindingExpression
);
var
column
=
entityProjectionExpression
.
BindProperty
(
entityShaperExpression
.
EntityType
.
GetProperties
().
First
());
table
=
column
.
Table
;
if
(
table
is
JoinExpressionBase
joinExpressionBase
)
{
table
=
joinExpressionBase
.
Table
;
}
}
if
(
table
is
TableExpression
te
)
{
tableExpression
=
te
;
return
true
;
}
}
tableExpression
=
null
;
return
false
;
}
}
src/EFCore.PG/Query/Internal/NpgsqlQueryableMethodTranslatingExpressionVisitorFactory.cs
0 → 100644
浏览文件 @
a1aa03ed
namespace
Npgsql.EntityFrameworkCore.PostgreSQL.Query.Internal
;
public
class
NpgsqlQueryableMethodTranslatingExpressionVisitorFactory
:
IQueryableMethodTranslatingExpressionVisitorFactory
{
public
NpgsqlQueryableMethodTranslatingExpressionVisitorFactory
(
QueryableMethodTranslatingExpressionVisitorDependencies
dependencies
,
RelationalQueryableMethodTranslatingExpressionVisitorDependencies
relationalDependencies
)
{
Dependencies
=
dependencies
;
RelationalDependencies
=
relationalDependencies
;
}
protected
virtual
QueryableMethodTranslatingExpressionVisitorDependencies
Dependencies
{
get
;
}
protected
virtual
RelationalQueryableMethodTranslatingExpressionVisitorDependencies
RelationalDependencies
{
get
;
}
public
virtual
QueryableMethodTranslatingExpressionVisitor
Create
(
QueryCompilationContext
queryCompilationContext
)
=>
new
NpgsqlQueryableMethodTranslatingExpressionVisitor
(
Dependencies
,
RelationalDependencies
,
queryCompilationContext
);
}
test/EFCore.PG.FunctionalTests/BulkUpdates/FiltersInheritanceBulkUpdatesNpgsqlFixture.cs
0 → 100644
浏览文件 @
a1aa03ed
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.
namespace
Npgsql.EntityFrameworkCore.PostgreSQL.BulkUpdates
;
public
class
FiltersInheritanceBulkUpdatesNpgsqlFixture
:
InheritanceBulkUpdatesNpgsqlFixture
{
protected
override
bool
EnableFilters
=>
true
;
}
test/EFCore.PG.FunctionalTests/BulkUpdates/FiltersInheritanceBulkUpdatesNpgsqlTest.cs
0 → 100644
浏览文件 @
a1aa03ed
using
Microsoft.EntityFrameworkCore.BulkUpdates
;
using
Npgsql.EntityFrameworkCore.PostgreSQL.Query
;
namespace
Npgsql.EntityFrameworkCore.PostgreSQL.BulkUpdates
;
public
class
FiltersInheritanceBulkUpdatesNpgsqlTest
:
FiltersInheritanceBulkUpdatesTestBase
<
FiltersInheritanceBulkUpdatesNpgsqlFixture
>
{
public
FiltersInheritanceBulkUpdatesNpgsqlTest
(
FiltersInheritanceBulkUpdatesNpgsqlFixture
fixture
)
:
base
(
fixture
)
{
ClearLog
();
}
public
override
async
Task
Delete_where_hierarchy
(
bool
async
)
{
await
base
.
Delete_where_hierarchy
(
async
);
AssertSql
(
@"DELETE FROM ""Animals"" AS a
WHERE a.""CountryId"" = 1 AND a.""Name"" = 'Great spotted kiwi'"
);
}
public
override
async
Task
Delete_where_hierarchy_derived
(
bool
async
)
{
await
base
.
Delete_where_hierarchy_derived
(
async
);
AssertSql
(
@"DELETE FROM ""Animals"" AS a
WHERE a.""Discriminator"" = 'Kiwi' AND a.""CountryId"" = 1 AND a.""Name"" = 'Great spotted kiwi'"
);
}
public
override
async
Task
Delete_where_using_hierarchy
(
bool
async
)
{
await
base
.
Delete_where_using_hierarchy
(
async
);
AssertSql
(
@"DELETE FROM ""Countries"" AS c
WHERE (
SELECT count(*)::int
FROM ""Animals"" AS a
WHERE a.""CountryId"" = 1 AND c.""Id"" = a.""CountryId"" AND a.""CountryId"" > 0) > 0"
);
}
public
override
async
Task
Delete_where_using_hierarchy_derived
(
bool
async
)
{
await
base
.
Delete_where_using_hierarchy_derived
(
async
);
AssertSql
(
@"DELETE FROM ""Countries"" AS c
WHERE (
SELECT count(*)::int
FROM ""Animals"" AS a
WHERE a.""CountryId"" = 1 AND c.""Id"" = a.""CountryId"" AND a.""Discriminator"" = 'Kiwi' AND a.""CountryId"" > 0) > 0"
);
}
public
override
async
Task
Delete_where_keyless_entity_mapped_to_sql_query
(
bool
async
)
{
await
base
.
Delete_where_keyless_entity_mapped_to_sql_query
(
async
);
AssertSql
();
}
public
override
async
Task
Delete_where_hierarchy_subquery
(
bool
async
)
{
await
base
.
Delete_where_hierarchy_subquery
(
async
);
AssertSql
();
}
[
ConditionalFact
]
public
virtual
void
Check_all_tests_overridden
()
=>
TestHelpers
.
AssertAllMethodsOverridden
(
GetType
());
protected
override
void
ClearLog
()
=>
Fixture
.
TestSqlLoggerFactory
.
Clear
();
private
void
AssertSql
(
params
string
[]
expected
)
=>
Fixture
.
TestSqlLoggerFactory
.
AssertBaseline
(
expected
);
}
test/EFCore.PG.FunctionalTests/BulkUpdates/InheritanceBulkUpdatesNpgsqlFixture.cs
0 → 100644
浏览文件 @
a1aa03ed
using
Microsoft.EntityFrameworkCore.BulkUpdates
;
using
Npgsql.EntityFrameworkCore.PostgreSQL.TestUtilities
;
namespace
Npgsql.EntityFrameworkCore.PostgreSQL.BulkUpdates
;
public
class
InheritanceBulkUpdatesNpgsqlFixture
:
InheritanceBulkUpdatesRelationalFixture
{
protected
override
ITestStoreFactory
TestStoreFactory
=>
NpgsqlTestStoreFactory
.
Instance
;
}
test/EFCore.PG.FunctionalTests/BulkUpdates/InheritanceBulkUpdatesNpgsqlTest.cs
0 → 100644
浏览文件 @
a1aa03ed
using
Microsoft.EntityFrameworkCore.BulkUpdates
;
namespace
Npgsql.EntityFrameworkCore.PostgreSQL.BulkUpdates
;
public
class
InheritanceBulkUpdatesNpgsqlTest
:
InheritanceBulkUpdatesTestBase
<
InheritanceBulkUpdatesNpgsqlFixture
>
{
public
InheritanceBulkUpdatesNpgsqlTest
(
InheritanceBulkUpdatesNpgsqlFixture
fixture
)
:
base
(
fixture
)
{
ClearLog
();
}
public
override
async
Task
Delete_where_hierarchy
(
bool
async
)
{
await
base
.
Delete_where_hierarchy
(
async
);
AssertSql
(
@"DELETE FROM ""Animals"" AS a
WHERE a.""Name"" = 'Great spotted kiwi'"
);
}
public
override
async
Task
Delete_where_hierarchy_derived
(
bool
async
)
{
await
base
.
Delete_where_hierarchy_derived
(
async
);
AssertSql
(
@"DELETE FROM ""Animals"" AS a
WHERE a.""Discriminator"" = 'Kiwi' AND a.""Name"" = 'Great spotted kiwi'"
);
}
public
override
async
Task
Delete_where_using_hierarchy
(
bool
async
)
{
await
base
.
Delete_where_using_hierarchy
(
async
);
AssertSql
(
@"DELETE FROM ""Countries"" AS c
WHERE (
SELECT count(*)::int
FROM ""Animals"" AS a
WHERE c.""Id"" = a.""CountryId"" AND a.""CountryId"" > 0) > 0"
);
}
public
override
async
Task
Delete_where_using_hierarchy_derived
(
bool
async
)
{
await
base
.
Delete_where_using_hierarchy_derived
(
async
);
AssertSql
(
@"DELETE FROM ""Countries"" AS c
WHERE (
SELECT count(*)::int
FROM ""Animals"" AS a
WHERE c.""Id"" = a.""CountryId"" AND a.""Discriminator"" = 'Kiwi' AND a.""CountryId"" > 0) > 0"
);
}
public
override
async
Task
Delete_where_keyless_entity_mapped_to_sql_query
(
bool
async
)
{
await
base
.
Delete_where_keyless_entity_mapped_to_sql_query
(
async
);
AssertSql
();
}
public
override
async
Task
Delete_where_hierarchy_subquery
(
bool
async
)
{
await
base
.
Delete_where_hierarchy_subquery
(
async
);
AssertSql
();
}
[
ConditionalFact
]
public
virtual
void
Check_all_tests_overridden
()
=>
TestHelpers
.
AssertAllMethodsOverridden
(
GetType
());
protected
override
void
ClearLog
()
=>
Fixture
.
TestSqlLoggerFactory
.
Clear
();
private
void
AssertSql
(
params
string
[]
expected
)
=>
Fixture
.
TestSqlLoggerFactory
.
AssertBaseline
(
expected
);
}
test/EFCore.PG.FunctionalTests/BulkUpdates/NorthwindBulkUpdatesNpgsqlFixture.cs
0 → 100644
浏览文件 @
a1aa03ed
using
Microsoft.EntityFrameworkCore.BulkUpdates
;
using
Microsoft.EntityFrameworkCore.TestModels.Northwind
;
using
Npgsql.EntityFrameworkCore.PostgreSQL.TestUtilities
;
namespace
Npgsql.EntityFrameworkCore.PostgreSQL.BulkUpdates
;
public
class
NorthwindBulkUpdatesNpgsqlFixture
<
TModelCustomizer
>
:
NorthwindBulkUpdatesFixture
<
TModelCustomizer
>
where
TModelCustomizer
:
IModelCustomizer
,
new
()
{
protected
override
ITestStoreFactory
TestStoreFactory
=>
NpgsqlNorthwindTestStoreFactory
.
Instance
;
protected
override
void
OnModelCreating
(
ModelBuilder
modelBuilder
,
DbContext
context
)
{
base
.
OnModelCreating
(
modelBuilder
,
context
);
modelBuilder
.
Entity
<
Customer
>()
.
Property
(
c
=>
c
.
CustomerID
)
.
HasColumnType
(
"char(5)"
);
modelBuilder
.
Entity
<
Employee
>(
b
=>
{
b
.
Property
(
c
=>
c
.
EmployeeID
).
HasColumnType
(
"int"
);
b
.
Property
(
c
=>
c
.
ReportsTo
).
HasColumnType
(
"int"
);
});
modelBuilder
.
Entity
<
Order
>(
b
=>
{
b
.
Property
(
o
=>
o
.
EmployeeID
).
HasColumnType
(
"int"
);
b
.
Property
(
o
=>
o
.
OrderDate
).
HasColumnType
(
"timestamp without time zone"
);
});
modelBuilder
.
Entity
<
OrderDetail
>()
.
Property
(
od
=>
od
.
UnitPrice
)
.
HasColumnType
(
"money"
);
modelBuilder
.
Entity
<
Product
>(
b
=>
{
b
.
Property
(
p
=>
p
.
UnitPrice
).
HasColumnType
(
"money"
);
b
.
Property
(
p
=>
p
.
UnitsInStock
).
HasColumnType
(
"smallint"
);
});
modelBuilder
.
Entity
<
MostExpensiveProduct
>()
.
Property
(
p
=>
p
.
UnitPrice
)
.
HasColumnType
(
"money"
);
}
}
test/EFCore.PG.FunctionalTests/BulkUpdates/NorthwindBulkUpdatesNpgsqlTest.cs
0 → 100644
浏览文件 @
a1aa03ed
using
Microsoft.EntityFrameworkCore.BulkUpdates
;
namespace
Npgsql.EntityFrameworkCore.PostgreSQL.BulkUpdates
;
public
class
NorthwindBulkUpdatesNpgsqlTest
:
NorthwindBulkUpdatesTestBase
<
NorthwindBulkUpdatesNpgsqlFixture
<
NoopModelCustomizer
>>
{
public
NorthwindBulkUpdatesNpgsqlTest
(
NorthwindBulkUpdatesNpgsqlFixture
<
NoopModelCustomizer
>
fixture
,
ITestOutputHelper
testOutputHelper
)
:
base
(
fixture
)
{
ClearLog
();
// Fixture.TestSqlLoggerFactory.SetTestOutputHelper(testOutputHelper);
}
[
ConditionalFact
]
public
virtual
void
Check_all_tests_overridden
()
=>
TestHelpers
.
AssertAllMethodsOverridden
(
GetType
());
public
override
async
Task
Delete_Where
(
bool
async
)
{
await
base
.
Delete_Where
(
async
);
AssertSql
(
@"DELETE FROM ""Order Details"" AS o
WHERE o.""OrderID"" < 10300"
);
}
public
override
async
Task
Delete_Where_parameter
(
bool
async
)
{
await
base
.
Delete_Where_parameter
(
async
);
AssertSql
(
@"@__quantity_0='1' (Nullable = true) (DbType = Int16)
DELETE FROM ""Order Details"" AS o
WHERE o.""Quantity"" = @__quantity_0"
,
//
@"DELETE FROM ""Order Details"" AS o
WHERE FALSE"
);
}
public
override
async
Task
Delete_Where_OrderBy
(
bool
async
)
{
await
base
.
Delete_Where_OrderBy
(
async
);
AssertSql
(
@"DELETE FROM ""Order Details"" AS o
WHERE EXISTS (
SELECT 1
FROM ""Order Details"" AS o0
WHERE o0.""OrderID"" < 10300 AND o0.""OrderID"" = o.""OrderID"" AND o0.""ProductID"" = o.""ProductID"")"
);
}
public
override
async
Task
Delete_Where_OrderBy_Skip
(
bool
async
)
{
await
base
.
Delete_Where_OrderBy_Skip
(
async
);
AssertSql
(
@"@__p_0='100'
DELETE FROM ""Order Details"" AS o
WHERE EXISTS (
SELECT 1
FROM (
SELECT o0.""OrderID"", o0.""ProductID"", o0.""Discount"", o0.""Quantity"", o0.""UnitPrice""
FROM ""Order Details"" AS o0
WHERE o0.""OrderID"" < 10300
ORDER BY o0.""OrderID"" NULLS FIRST
OFFSET @__p_0
) AS t
WHERE t.""OrderID"" = o.""OrderID"" AND t.""ProductID"" = o.""ProductID"")"
);
}
public
override
async
Task
Delete_Where_OrderBy_Take
(
bool
async
)
{
await
base
.
Delete_Where_OrderBy_Take
(
async
);
AssertSql
(
@"@__p_0='100'
DELETE FROM ""Order Details"" AS o
WHERE EXISTS (
SELECT 1
FROM (
SELECT o0.""OrderID"", o0.""ProductID"", o0.""Discount"", o0.""Quantity"", o0.""UnitPrice""
FROM ""Order Details"" AS o0
WHERE o0.""OrderID"" < 10300
ORDER BY o0.""OrderID"" NULLS FIRST
LIMIT @__p_0
) AS t
WHERE t.""OrderID"" = o.""OrderID"" AND t.""ProductID"" = o.""ProductID"")"
);
}
public
override
async
Task
Delete_Where_OrderBy_Skip_Take
(
bool
async
)
{
await
base
.
Delete_Where_OrderBy_Skip_Take
(
async
);
AssertSql
(
@"@__p_0='100'
DELETE FROM ""Order Details"" AS o
WHERE EXISTS (
SELECT 1
FROM (
SELECT o0.""OrderID"", o0.""ProductID"", o0.""Discount"", o0.""Quantity"", o0.""UnitPrice""
FROM ""Order Details"" AS o0
WHERE o0.""OrderID"" < 10300
ORDER BY o0.""OrderID"" NULLS FIRST
LIMIT @__p_0 OFFSET @__p_0
) AS t
WHERE t.""OrderID"" = o.""OrderID"" AND t.""ProductID"" = o.""ProductID"")"
);
}
public
override
async
Task
Delete_Where_Skip
(
bool
async
)
{
await
base
.
Delete_Where_Skip
(
async
);
AssertSql
(
@"@__p_0='100'
DELETE FROM ""Order Details"" AS o
WHERE EXISTS (
SELECT 1
FROM (
SELECT o0.""OrderID"", o0.""ProductID"", o0.""Discount"", o0.""Quantity"", o0.""UnitPrice""
FROM ""Order Details"" AS o0
WHERE o0.""OrderID"" < 10300
OFFSET @__p_0
) AS t
WHERE t.""OrderID"" = o.""OrderID"" AND t.""ProductID"" = o.""ProductID"")"
);
}
public
override
async
Task
Delete_Where_Take
(
bool
async
)
{
await
base
.
Delete_Where_Take
(
async
);
AssertSql
(
@"@__p_0='100'
DELETE FROM ""Order Details"" AS o
WHERE EXISTS (
SELECT 1
FROM (
SELECT o0.""OrderID"", o0.""ProductID"", o0.""Discount"", o0.""Quantity"", o0.""UnitPrice""
FROM ""Order Details"" AS o0
WHERE o0.""OrderID"" < 10300
LIMIT @__p_0
) AS t
WHERE t.""OrderID"" = o.""OrderID"" AND t.""ProductID"" = o.""ProductID"")"
);
}
public
override
async
Task
Delete_Where_Skip_Take
(
bool
async
)
{
await
base
.
Delete_Where_Skip_Take
(
async
);
AssertSql
(
@"@__p_0='100'
DELETE FROM ""Order Details"" AS o
WHERE EXISTS (
SELECT 1
FROM (
SELECT o0.""OrderID"", o0.""ProductID"", o0.""Discount"", o0.""Quantity"", o0.""UnitPrice""
FROM ""Order Details"" AS o0
WHERE o0.""OrderID"" < 10300
LIMIT @__p_0 OFFSET @__p_0
) AS t
WHERE t.""OrderID"" = o.""OrderID"" AND t.""ProductID"" = o.""ProductID"")"
);
}
public
override
async
Task
Delete_Where_predicate_with_group_by_aggregate
(
bool
async
)
{
await
base
.
Delete_Where_predicate_with_group_by_aggregate
(
async
);
AssertSql
(
@"DELETE FROM ""Order Details"" AS o
WHERE o.""OrderID"" < (
SELECT (
SELECT o1.""OrderID""
FROM ""Orders"" AS o1
WHERE o0.""CustomerID"" = o1.""CustomerID"" OR ((o0.""CustomerID"" IS NULL) AND (o1.""CustomerID"" IS NULL))
LIMIT 1)
FROM ""Orders"" AS o0
GROUP BY o0.""CustomerID""
HAVING count(*)::int > 11
LIMIT 1)"
);
}
public
override
async
Task
Delete_Where_predicate_with_group_by_aggregate_2
(
bool
async
)
{
await
base
.
Delete_Where_predicate_with_group_by_aggregate_2
(
async
);
AssertSql
();
}
public
override
async
Task
Delete_GroupBy_Where_Select
(
bool
async
)
{
await
base
.
Delete_GroupBy_Where_Select
(
async
);
AssertSql
();
}
public
override
async
Task
Delete_Where_Skip_Take_Skip_Take_causing_subquery
(
bool
async
)
{
await
base
.
Delete_Where_Skip_Take_Skip_Take_causing_subquery
(
async
);
AssertSql
(
@"@__p_0='100'
@__p_2='5'
@__p_1='20'
DELETE FROM ""Order Details"" AS o
WHERE EXISTS (
SELECT 1
FROM (
SELECT t.""OrderID"", t.""ProductID"", t.""Discount"", t.""Quantity"", t.""UnitPrice""
FROM (
SELECT o0.""OrderID"", o0.""ProductID"", o0.""Discount"", o0.""Quantity"", o0.""UnitPrice""
FROM ""Order Details"" AS o0
WHERE o0.""OrderID"" < 10300
LIMIT @__p_0 OFFSET @__p_0
) AS t
LIMIT @__p_2 OFFSET @__p_1
) AS t0
WHERE t0.""OrderID"" = o.""OrderID"" AND t0.""ProductID"" = o.""ProductID"")"
);
}
public
override
async
Task
Delete_Where_Distinct
(
bool
async
)
{
await
base
.
Delete_Where_Distinct
(
async
);
AssertSql
(
@"DELETE FROM ""Order Details"" AS o
WHERE o.""OrderID"" < 10300"
);
}
public
override
async
Task
Delete_SelectMany
(
bool
async
)
{
await
base
.
Delete_SelectMany
(
async
);
AssertSql
(
@"DELETE FROM ""Order Details"" AS o0
USING ""Orders"" AS o
WHERE o.""OrderID"" = o0.""OrderID"" AND o.""OrderID"" < 10250"
);
}
public
override
async
Task
Delete_SelectMany_subquery
(
bool
async
)
{
await
base
.
Delete_SelectMany_subquery
(
async
);
AssertSql
(
@"DELETE FROM ""Order Details"" AS o
WHERE EXISTS (
SELECT 1
FROM ""Orders"" AS o0
INNER JOIN (
SELECT o1.""OrderID"", o1.""ProductID"", o1.""Discount"", o1.""Quantity"", o1.""UnitPrice""
FROM ""Order Details"" AS o1
WHERE o1.""ProductID"" > 0
) AS t ON o0.""OrderID"" = t.""OrderID""
WHERE o0.""OrderID"" < 10250 AND t.""OrderID"" = o.""OrderID"" AND t.""ProductID"" = o.""ProductID"")"
);
}
public
override
async
Task
Delete_Where_using_navigation
(
bool
async
)
{
await
base
.
Delete_Where_using_navigation
(
async
);
AssertSql
(
@"DELETE FROM ""Order Details"" AS o
USING ""Orders"" AS o0
WHERE o.""OrderID"" = o0.""OrderID"" AND date_part('year', o0.""OrderDate"")::int = 2000"
);
}
public
override
async
Task
Delete_Where_using_navigation_2
(
bool
async
)
{
await
base
.
Delete_Where_using_navigation_2
(
async
);
AssertSql
(
@"DELETE FROM ""Order Details"" AS o
WHERE EXISTS (
SELECT 1
FROM ""Order Details"" AS o0
INNER JOIN ""Orders"" AS o1 ON o0.""OrderID"" = o1.""OrderID""
LEFT JOIN ""Customers"" AS c ON o1.""CustomerID"" = c.""CustomerID""
WHERE (c.""CustomerID"" IS NOT NULL) AND (c.""CustomerID"" LIKE 'F%') AND o0.""OrderID"" = o.""OrderID"" AND o0.""ProductID"" = o.""ProductID"")"
);
}
public
override
async
Task
Delete_Union
(
bool
async
)
{
await
base
.
Delete_Union
(
async
);
AssertSql
(
@"DELETE FROM ""Order Details"" AS o
WHERE EXISTS (
SELECT 1
FROM (
SELECT o0.""OrderID"", o0.""ProductID"", o0.""Discount"", o0.""Quantity"", o0.""UnitPrice""
FROM ""Order Details"" AS o0
WHERE o0.""OrderID"" < 10250
UNION
SELECT o1.""OrderID"", o1.""ProductID"", o1.""Discount"", o1.""Quantity"", o1.""UnitPrice""
FROM ""Order Details"" AS o1
WHERE o1.""OrderID"" > 11250
) AS t
WHERE t.""OrderID"" = o.""OrderID"" AND t.""ProductID"" = o.""ProductID"")"
);
}
public
override
async
Task
Delete_Concat
(
bool
async
)
{
await
base
.
Delete_Concat
(
async
);
AssertSql
(
@"DELETE FROM ""Order Details"" AS o
WHERE EXISTS (
SELECT 1
FROM (
SELECT o0.""OrderID"", o0.""ProductID"", o0.""Discount"", o0.""Quantity"", o0.""UnitPrice""
FROM ""Order Details"" AS o0
WHERE o0.""OrderID"" < 10250
UNION ALL
SELECT o1.""OrderID"", o1.""ProductID"", o1.""Discount"", o1.""Quantity"", o1.""UnitPrice""
FROM ""Order Details"" AS o1
WHERE o1.""OrderID"" > 11250
) AS t
WHERE t.""OrderID"" = o.""OrderID"" AND t.""ProductID"" = o.""ProductID"")"
);
}
public
override
async
Task
Delete_Intersect
(
bool
async
)
{
await
base
.
Delete_Intersect
(
async
);
AssertSql
(
@"DELETE FROM ""Order Details"" AS o
WHERE EXISTS (
SELECT 1
FROM (
SELECT o0.""OrderID"", o0.""ProductID"", o0.""Discount"", o0.""Quantity"", o0.""UnitPrice""
FROM ""Order Details"" AS o0
WHERE o0.""OrderID"" < 10250
INTERSECT
SELECT o1.""OrderID"", o1.""ProductID"", o1.""Discount"", o1.""Quantity"", o1.""UnitPrice""
FROM ""Order Details"" AS o1
WHERE o1.""OrderID"" > 11250
) AS t
WHERE t.""OrderID"" = o.""OrderID"" AND t.""ProductID"" = o.""ProductID"")"
);
}
public
override
async
Task
Delete_Except
(
bool
async
)
{
await
base
.
Delete_Except
(
async
);
AssertSql
(
@"DELETE FROM ""Order Details"" AS o
WHERE EXISTS (
SELECT 1
FROM (
SELECT o0.""OrderID"", o0.""ProductID"", o0.""Discount"", o0.""Quantity"", o0.""UnitPrice""
FROM ""Order Details"" AS o0
WHERE o0.""OrderID"" < 10250
EXCEPT
SELECT o1.""OrderID"", o1.""ProductID"", o1.""Discount"", o1.""Quantity"", o1.""UnitPrice""
FROM ""Order Details"" AS o1
WHERE o1.""OrderID"" > 11250
) AS t
WHERE t.""OrderID"" = o.""OrderID"" AND t.""ProductID"" = o.""ProductID"")"
);
}
public
override
async
Task
Delete_non_entity_projection
(
bool
async
)
{
await
base
.
Delete_non_entity_projection
(
async
);
AssertSql
();
}
public
override
async
Task
Delete_non_entity_projection_2
(
bool
async
)
{
await
base
.
Delete_non_entity_projection_2
(
async
);
AssertSql
();
}
public
override
async
Task
Delete_non_entity_projection_3
(
bool
async
)
{
await
base
.
Delete_non_entity_projection_3
(
async
);
AssertSql
();
}
public
override
async
Task
Delete_FromSql_converted_to_subquery
(
bool
async
)
{
await
base
.
Delete_FromSql_converted_to_subquery
(
async
);
AssertSql
(
@"DELETE FROM ""Order Details"" AS o
WHERE EXISTS (
SELECT 1
FROM (
SELECT ""OrderID"", ""ProductID"", ""UnitPrice"", ""Quantity"", ""Discount""
FROM ""Order Details""
WHERE ""OrderID"" < 10300
) AS m
WHERE m.""OrderID"" = o.""OrderID"" AND m.""ProductID"" = o.""ProductID"")"
);
}
public
override
async
Task
Delete_with_join
(
bool
async
)
{
await
base
.
Delete_with_join
(
async
);
AssertSql
(
@"@__p_1='100'
@__p_0='0'
DELETE FROM ""Order Details"" AS o
USING (
SELECT o0.""OrderID"", o0.""CustomerID"", o0.""EmployeeID"", o0.""OrderDate""
FROM ""Orders"" AS o0
WHERE o0.""OrderID"" < 10300
ORDER BY o0.""OrderID"" NULLS FIRST
LIMIT @__p_1 OFFSET @__p_0
) AS t
WHERE o.""OrderID"" = t.""OrderID"""
);
}
public
override
async
Task
Delete_with_left_join
(
bool
async
)
{
await
base
.
Delete_with_left_join
(
async
);
AssertSql
(
@"@__p_1='100'
@__p_0='0'
DELETE FROM ""Order Details"" AS o
WHERE EXISTS (
SELECT 1
FROM ""Order Details"" AS o0
LEFT JOIN (
SELECT o1.""OrderID"", o1.""CustomerID"", o1.""EmployeeID"", o1.""OrderDate""
FROM ""Orders"" AS o1
WHERE o1.""OrderID"" < 10300
ORDER BY o1.""OrderID"" NULLS FIRST
LIMIT @__p_1 OFFSET @__p_0
) AS t ON o0.""OrderID"" = t.""OrderID""
WHERE o0.""OrderID"" < 10276 AND o0.""OrderID"" = o.""OrderID"" AND o0.""ProductID"" = o.""ProductID"")"
);
}
public
override
async
Task
Delete_with_cross_join
(
bool
async
)
{
await
base
.
Delete_with_cross_join
(
async
);
AssertSql
(
@"DELETE FROM ""Order Details"" AS o
WHERE EXISTS (
SELECT 1
FROM ""Order Details"" AS o0
CROSS JOIN (
SELECT o1.""OrderID"", o1.""CustomerID"", o1.""EmployeeID"", o1.""OrderDate""
FROM ""Orders"" AS o1
WHERE o1.""OrderID"" < 10300
ORDER BY o1.""OrderID"" NULLS FIRST
LIMIT 100 OFFSET 0
) AS t
WHERE o0.""OrderID"" < 10276 AND o0.""OrderID"" = o.""OrderID"" AND o0.""ProductID"" = o.""ProductID"")"
);
}
public
override
async
Task
Delete_with_cross_apply
(
bool
async
)
{
await
base
.
Delete_with_cross_apply
(
async
);
AssertSql
(
@"DELETE FROM ""Order Details"" AS o
WHERE EXISTS (
SELECT 1
FROM ""Order Details"" AS o0
JOIN LATERAL (
SELECT o1.""OrderID"", o1.""CustomerID"", o1.""EmployeeID"", o1.""OrderDate""
FROM ""Orders"" AS o1
WHERE o1.""OrderID"" < o0.""OrderID""
ORDER BY o1.""OrderID"" NULLS FIRST
LIMIT 100 OFFSET 0
) AS t ON TRUE
WHERE o0.""OrderID"" < 10276 AND o0.""OrderID"" = o.""OrderID"" AND o0.""ProductID"" = o.""ProductID"")"
);
}
public
override
async
Task
Delete_with_outer_apply
(
bool
async
)
{
await
base
.
Delete_with_outer_apply
(
async
);
AssertSql
(
@"DELETE FROM ""Order Details"" AS o
WHERE EXISTS (
SELECT 1
FROM ""Order Details"" AS o0
LEFT JOIN LATERAL (
SELECT o1.""OrderID"", o1.""CustomerID"", o1.""EmployeeID"", o1.""OrderDate""
FROM ""Orders"" AS o1
WHERE o1.""OrderID"" < o0.""OrderID""
ORDER BY o1.""OrderID"" NULLS FIRST
LIMIT 100 OFFSET 0
) AS t ON TRUE
WHERE o0.""OrderID"" < 10276 AND o0.""OrderID"" = o.""OrderID"" AND o0.""ProductID"" = o.""ProductID"")"
);
}
private
void
AssertSql
(
params
string
[]
expected
)
=>
Fixture
.
TestSqlLoggerFactory
.
AssertBaseline
(
expected
);
}
test/EFCore.PG.FunctionalTests/BulkUpdates/TPCFiltersInheritanceBulkUpdatesNpgsqlFixture.cs
0 → 100644
浏览文件 @
a1aa03ed
namespace
Npgsql.EntityFrameworkCore.PostgreSQL.BulkUpdates
;
public
class
TPCFiltersInheritanceBulkUpdatesNpgsqlFixture
:
TPCInheritanceBulkUpdatesNpgsqlFixture
{
protected
override
bool
EnableFilters
=>
true
;
}
test/EFCore.PG.FunctionalTests/BulkUpdates/TPCFiltersInheritanceBulkUpdatesNpgsqlTest.cs
0 → 100644
浏览文件 @
a1aa03ed
using
Microsoft.EntityFrameworkCore.BulkUpdates
;
using
Npgsql.EntityFrameworkCore.PostgreSQL.Query
;
using
Npgsql.EntityFrameworkCore.PostgreSQL.TestUtilities
;
namespace
Npgsql.EntityFrameworkCore.PostgreSQL.BulkUpdates
;
public
class
TPCFiltersInheritanceBulkUpdatesNpgsqlTest
:
TPCFiltersInheritanceBulkUpdatesTestBase
<
TPCFiltersInheritanceBulkUpdatesNpgsqlFixture
>
{
public
TPCFiltersInheritanceBulkUpdatesNpgsqlTest
(
TPCFiltersInheritanceBulkUpdatesNpgsqlFixture
fixture
)
:
base
(
fixture
)
{
ClearLog
();
}
[
ConditionalFact
]
public
virtual
void
Check_all_tests_overridden
()
=>
TestHelpers
.
AssertAllMethodsOverridden
(
GetType
());
public
override
async
Task
Delete_where_hierarchy
(
bool
async
)
{
await
base
.
Delete_where_hierarchy
(
async
);
AssertSql
();
}
public
override
async
Task
Delete_where_hierarchy_derived
(
bool
async
)
{
await
base
.
Delete_where_hierarchy_derived
(
async
);
AssertSql
(
@"DELETE FROM ""Kiwi"" AS k
WHERE k.""CountryId"" = 1 AND k.""Name"" = 'Great spotted kiwi'"
);
}
public
override
async
Task
Delete_where_using_hierarchy
(
bool
async
)
{
await
base
.
Delete_where_using_hierarchy
(
async
);
AssertSql
(
@"DELETE FROM ""Countries"" AS c
WHERE (
SELECT count(*)::int
FROM (
SELECT e.""Id"", e.""CountryId"", e.""Name"", e.""Species"", e.""EagleId"", e.""IsFlightless"", e.""Group"", NULL AS ""FoundOn"", 'Eagle' AS ""Discriminator""
FROM ""Eagle"" AS e
UNION ALL
SELECT k.""Id"", k.""CountryId"", k.""Name"", k.""Species"", k.""EagleId"", k.""IsFlightless"", NULL AS ""Group"", k.""FoundOn"", 'Kiwi' AS ""Discriminator""
FROM ""Kiwi"" AS k
) AS t
WHERE t.""CountryId"" = 1 AND c.""Id"" = t.""CountryId"" AND t.""CountryId"" > 0) > 0"
);
}
public
override
async
Task
Delete_where_using_hierarchy_derived
(
bool
async
)
{
await
base
.
Delete_where_using_hierarchy_derived
(
async
);
AssertSql
(
@"DELETE FROM ""Countries"" AS c
WHERE (
SELECT count(*)::int
FROM (
SELECT k.""Id"", k.""CountryId"", k.""Name"", k.""Species"", k.""EagleId"", k.""IsFlightless"", NULL AS ""Group"", k.""FoundOn"", 'Kiwi' AS ""Discriminator""
FROM ""Kiwi"" AS k
) AS t
WHERE t.""CountryId"" = 1 AND c.""Id"" = t.""CountryId"" AND t.""CountryId"" > 0) > 0"
);
}
public
override
async
Task
Delete_where_keyless_entity_mapped_to_sql_query
(
bool
async
)
{
await
base
.
Delete_where_keyless_entity_mapped_to_sql_query
(
async
);
AssertSql
();
}
public
override
async
Task
Delete_where_hierarchy_subquery
(
bool
async
)
{
await
base
.
Delete_where_hierarchy_subquery
(
async
);
AssertSql
();
}
protected
override
void
ClearLog
()
=>
Fixture
.
TestSqlLoggerFactory
.
Clear
();
private
void
AssertSql
(
params
string
[]
expected
)
=>
Fixture
.
TestSqlLoggerFactory
.
AssertBaseline
(
expected
);
}
test/EFCore.PG.FunctionalTests/BulkUpdates/TPCInheritanceBulkUpdatesNpgsqlFixture.cs
0 → 100644
浏览文件 @
a1aa03ed
using
Microsoft.EntityFrameworkCore.BulkUpdates
;
using
Npgsql.EntityFrameworkCore.PostgreSQL.TestUtilities
;
namespace
Npgsql.EntityFrameworkCore.PostgreSQL.BulkUpdates
;
public
class
TPCInheritanceBulkUpdatesNpgsqlFixture
:
TPCInheritanceBulkUpdatesFixture
{
protected
override
ITestStoreFactory
TestStoreFactory
=>
NpgsqlTestStoreFactory
.
Instance
;
protected
override
bool
UseGeneratedKeys
=>
false
;
}
test/EFCore.PG.FunctionalTests/BulkUpdates/TPCInheritanceBulkUpdatesNpgsqlTest.cs
0 → 100644
浏览文件 @
a1aa03ed
using
Microsoft.EntityFrameworkCore.BulkUpdates
;
using
Npgsql.EntityFrameworkCore.PostgreSQL.Query
;
using
Npgsql.EntityFrameworkCore.PostgreSQL.TestUtilities
;
namespace
Npgsql.EntityFrameworkCore.PostgreSQL.BulkUpdates
;
public
class
TPCInheritanceBulkUpdatesNpgsqlTest
:
TPCInheritanceBulkUpdatesTestBase
<
TPCInheritanceBulkUpdatesNpgsqlFixture
>
{
public
TPCInheritanceBulkUpdatesNpgsqlTest
(
TPCInheritanceBulkUpdatesNpgsqlFixture
fixture
)
:
base
(
fixture
)
{
ClearLog
();
}
[
ConditionalFact
]
public
virtual
void
Check_all_tests_overridden
()
=>
TestHelpers
.
AssertAllMethodsOverridden
(
GetType
());
public
override
async
Task
Delete_where_hierarchy
(
bool
async
)
{
await
base
.
Delete_where_hierarchy
(
async
);
AssertSql
();
}
public
override
async
Task
Delete_where_hierarchy_derived
(
bool
async
)
{
await
base
.
Delete_where_hierarchy_derived
(
async
);
AssertSql
(
@"DELETE FROM ""Kiwi"" AS k
WHERE k.""Name"" = 'Great spotted kiwi'"
);
}
public
override
async
Task
Delete_where_using_hierarchy
(
bool
async
)
{
await
base
.
Delete_where_using_hierarchy
(
async
);
AssertSql
(
@"DELETE FROM ""Countries"" AS c
WHERE (
SELECT count(*)::int
FROM (
SELECT e.""Id"", e.""CountryId"", e.""Name"", e.""Species"", e.""EagleId"", e.""IsFlightless"", e.""Group"", NULL AS ""FoundOn"", 'Eagle' AS ""Discriminator""
FROM ""Eagle"" AS e
UNION ALL
SELECT k.""Id"", k.""CountryId"", k.""Name"", k.""Species"", k.""EagleId"", k.""IsFlightless"", NULL AS ""Group"", k.""FoundOn"", 'Kiwi' AS ""Discriminator""
FROM ""Kiwi"" AS k
) AS t
WHERE c.""Id"" = t.""CountryId"" AND t.""CountryId"" > 0) > 0"
);
}
public
override
async
Task
Delete_where_using_hierarchy_derived
(
bool
async
)
{
await
base
.
Delete_where_using_hierarchy_derived
(
async
);
AssertSql
(
@"DELETE FROM ""Countries"" AS c
WHERE (
SELECT count(*)::int
FROM (
SELECT k.""Id"", k.""CountryId"", k.""Name"", k.""Species"", k.""EagleId"", k.""IsFlightless"", NULL AS ""Group"", k.""FoundOn"", 'Kiwi' AS ""Discriminator""
FROM ""Kiwi"" AS k
) AS t
WHERE c.""Id"" = t.""CountryId"" AND t.""CountryId"" > 0) > 0"
);
}
public
override
async
Task
Delete_where_keyless_entity_mapped_to_sql_query
(
bool
async
)
{
await
base
.
Delete_where_keyless_entity_mapped_to_sql_query
(
async
);
AssertSql
();
}
public
override
async
Task
Delete_where_hierarchy_subquery
(
bool
async
)
{
await
base
.
Delete_where_hierarchy_subquery
(
async
);
AssertSql
();
}
protected
override
void
ClearLog
()
=>
Fixture
.
TestSqlLoggerFactory
.
Clear
();
private
void
AssertSql
(
params
string
[]
expected
)
=>
Fixture
.
TestSqlLoggerFactory
.
AssertBaseline
(
expected
);
}
test/EFCore.PG.FunctionalTests/BulkUpdates/TPTFiltersInheritanceBulkUpdatesNpgsqlFixture.cs
0 → 100644
浏览文件 @
a1aa03ed
namespace
Npgsql.EntityFrameworkCore.PostgreSQL.BulkUpdates
;
public
class
TPTFiltersInheritanceBulkUpdatesNpgsqlFixture
:
TPTInheritanceBulkUpdatesNpgsqlFixture
{
protected
override
bool
EnableFilters
=>
true
;
}
test/EFCore.PG.FunctionalTests/BulkUpdates/TPTFiltersInheritanceBulkUpdatesNpgsqlTest.cs
0 → 100644
浏览文件 @
a1aa03ed
using
Microsoft.EntityFrameworkCore.BulkUpdates
;
using
Npgsql.EntityFrameworkCore.PostgreSQL.Query
;
namespace
Npgsql.EntityFrameworkCore.PostgreSQL.BulkUpdates
;
public
class
TPTFiltersInheritanceBulkUpdatesSqlServerTest
:
TPTFiltersInheritanceBulkUpdatesTestBase
<
TPTFiltersInheritanceBulkUpdatesNpgsqlFixture
>
{
public
TPTFiltersInheritanceBulkUpdatesSqlServerTest
(
TPTFiltersInheritanceBulkUpdatesNpgsqlFixture
fixture
)
:
base
(
fixture
)
{
ClearLog
();
}
[
ConditionalFact
]
public
virtual
void
Check_all_tests_overridden
()
=>
TestHelpers
.
AssertAllMethodsOverridden
(
GetType
());
public
override
async
Task
Delete_where_hierarchy
(
bool
async
)
{
await
base
.
Delete_where_hierarchy
(
async
);
AssertSql
();
}
public
override
async
Task
Delete_where_hierarchy_derived
(
bool
async
)
{
await
base
.
Delete_where_hierarchy_derived
(
async
);
AssertSql
();
}
public
override
async
Task
Delete_where_using_hierarchy
(
bool
async
)
{
await
base
.
Delete_where_using_hierarchy
(
async
);
AssertSql
(
@"DELETE FROM [c]
FROM [Countries] AS [c]
WHERE (
SELECT COUNT(*)
FROM [Animals] AS [a]
WHERE [a].[CountryId] = 1 AND [c].[Id] = [a].[CountryId] AND [a].[CountryId] > 0) > 0"
);
}
public
override
async
Task
Delete_where_using_hierarchy_derived
(
bool
async
)
{
await
base
.
Delete_where_using_hierarchy_derived
(
async
);
AssertSql
(
@"DELETE FROM [c]
FROM [Countries] AS [c]
WHERE (
SELECT COUNT(*)
FROM [Animals] AS [a]
WHERE [a].[CountryId] = 1 AND [c].[Id] = [a].[CountryId] AND [a].[Discriminator] = N'Kiwi' AND [a].[CountryId] > 0) > 0"
);
}
public
override
async
Task
Delete_where_keyless_entity_mapped_to_sql_query
(
bool
async
)
{
await
base
.
Delete_where_keyless_entity_mapped_to_sql_query
(
async
);
AssertSql
();
}
public
override
async
Task
Delete_where_hierarchy_subquery
(
bool
async
)
{
await
base
.
Delete_where_hierarchy_subquery
(
async
);
AssertSql
();
}
protected
override
void
ClearLog
()
=>
Fixture
.
TestSqlLoggerFactory
.
Clear
();
private
void
AssertSql
(
params
string
[]
expected
)
=>
Fixture
.
TestSqlLoggerFactory
.
AssertBaseline
(
expected
);
}
test/EFCore.PG.FunctionalTests/BulkUpdates/TPTInheritanceBulkUpdatesNpgsqlFixture.cs
0 → 100644
浏览文件 @
a1aa03ed
using
Microsoft.EntityFrameworkCore.BulkUpdates
;
using
Npgsql.EntityFrameworkCore.PostgreSQL.TestUtilities
;
namespace
Npgsql.EntityFrameworkCore.PostgreSQL.BulkUpdates
;
public
class
TPTInheritanceBulkUpdatesNpgsqlFixture
:
TPTInheritanceBulkUpdatesFixture
{
protected
override
ITestStoreFactory
TestStoreFactory
=>
NpgsqlTestStoreFactory
.
Instance
;
}
test/EFCore.PG.FunctionalTests/BulkUpdates/TPTInheritanceBulkUpdatesNpgsqlTest.cs
0 → 100644
浏览文件 @
a1aa03ed
using
Microsoft.EntityFrameworkCore.BulkUpdates
;
using
Npgsql.EntityFrameworkCore.PostgreSQL.Query
;
namespace
Npgsql.EntityFrameworkCore.PostgreSQL.BulkUpdates
;
public
class
TPTInheritanceBulkUpdatesNpgsqlTest
:
TPTInheritanceBulkUpdatesTestBase
<
TPTInheritanceBulkUpdatesNpgsqlFixture
>
{
public
TPTInheritanceBulkUpdatesNpgsqlTest
(
TPTInheritanceBulkUpdatesNpgsqlFixture
fixture
)
:
base
(
fixture
)
{
ClearLog
();
}
[
ConditionalFact
]
public
virtual
void
Check_all_tests_overridden
()
=>
TestHelpers
.
AssertAllMethodsOverridden
(
GetType
());
public
override
async
Task
Delete_where_hierarchy
(
bool
async
)
{
await
base
.
Delete_where_hierarchy
(
async
);
AssertSql
();
}
public
override
async
Task
Delete_where_hierarchy_derived
(
bool
async
)
{
await
base
.
Delete_where_hierarchy_derived
(
async
);
AssertSql
();
}
public
override
async
Task
Delete_where_using_hierarchy
(
bool
async
)
{
await
base
.
Delete_where_using_hierarchy
(
async
);
AssertSql
();
}
public
override
async
Task
Delete_where_using_hierarchy_derived
(
bool
async
)
{
await
base
.
Delete_where_using_hierarchy_derived
(
async
);
AssertSql
();
}
public
override
async
Task
Delete_where_keyless_entity_mapped_to_sql_query
(
bool
async
)
{
await
base
.
Delete_where_keyless_entity_mapped_to_sql_query
(
async
);
AssertSql
();
}
public
override
async
Task
Delete_where_hierarchy_subquery
(
bool
async
)
{
await
base
.
Delete_where_hierarchy_subquery
(
async
);
AssertSql
();
}
protected
override
void
ClearLog
()
=>
Fixture
.
TestSqlLoggerFactory
.
Clear
();
private
void
AssertSql
(
params
string
[]
expected
)
=>
Fixture
.
TestSqlLoggerFactory
.
AssertBaseline
(
expected
);
}
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录