@@ -71,7 +71,7 @@ public virtual async Task UniqueColumnViolationSameNamesIndexesInDifferentSchema
7171 {
7272 Name = "Rope Access"
7373 } ) ;
74-
74+
7575 SameNameIndexesContext . IncidentCategories . Add ( new EFExceptionSchema . Entities . Incidents . Category
7676 {
7777 Name = "Rope Access"
@@ -109,7 +109,7 @@ public virtual async Task PrimaryKeyViolationThrowsUniqueConstraintException()
109109 Assert . False ( string . IsNullOrEmpty ( uniqueConstraintException . ConstraintName ) ) ;
110110 Assert . False ( string . IsNullOrEmpty ( uniqueConstraintException . SchemaQualifiedTableName ) ) ;
111111 Assert . NotEmpty ( uniqueConstraintException . ConstraintProperties ) ;
112- Assert . Contains < string > ( nameof ( Product . Id ) , uniqueConstraintException . ConstraintProperties ) ;
112+ Assert . Contains < string > ( nameof ( Product . Id ) , uniqueConstraintException . ConstraintProperties ) ;
113113 }
114114 }
115115
@@ -348,6 +348,41 @@ public async Task NotHandledViolationReThrowsOriginalException()
348348 await Assert . ThrowsAsync < DbUpdateException > ( ( ) => DemoContext . SaveChangesAsync ( ) ) ;
349349 }
350350
351+ [ Fact ]
352+ public virtual async Task Deadlock ( )
353+ {
354+ var p1 = DemoContext . Products . Add ( new ( ) { Name = "Test1" } ) ;
355+ var p2 = DemoContext . Products . Add ( new ( ) { Name = "Test2" } ) ;
356+
357+ await DemoContext . SaveChangesAsync ( ) ;
358+
359+ var id1 = p1 . Entity . Id ;
360+ var id2 = p2 . Entity . Id ;
361+
362+ using var controlContext = new DemoContext ( DemoContext . Options ) ;
363+ using var transaction1 = DemoContext . Database . BeginTransactionAsync ( ) ;
364+ using var transaction2 = controlContext . Database . BeginTransactionAsync ( ) ;
365+
366+ await DemoContext . Products . Where ( c => c . Id == id1 )
367+ . ExecuteUpdateAsync ( c => c . SetProperty ( p => p . Name , "Test11" ) ) ;
368+
369+ await Assert . ThrowsAsync < DeadlockException > ( async ( ) =>
370+ {
371+ await controlContext . Products . Where ( c => c . Id == id2 )
372+ . ExecuteUpdateAsync ( c => c . SetProperty ( p => p . Name , "Test21" ) ) ;
373+
374+ var task1 = Task . Run ( ( ) => DemoContext . Products . Where ( c => c . Id == id2 )
375+ . ExecuteUpdateAsync ( c => c . SetProperty ( p => p . Name , "Test22" ) ) ) ;
376+
377+ await Task . Delay ( 100 ) ;
378+
379+ var task2 = controlContext . Products . Where ( c => c . Id == id1 )
380+ . ExecuteUpdateAsync ( c => c . SetProperty ( p => p . Name , "Test12" ) ) ;
381+
382+ await Task . WhenAll ( task1 , task2 ) ;
383+ } ) ;
384+ }
385+
351386 public virtual void Dispose ( )
352387 {
353388 CleanupContext ( ) ;
@@ -360,4 +395,4 @@ protected void CleanupContext()
360395 entityEntry . State = EntityState . Detached ;
361396 }
362397 }
363- }
398+ }
0 commit comments