When I have a batch size larger than five in my database context, I get the exception below. If the batch size is 5 or lower, no error happens.
{Microsoft.EntityFrameworkCore.DbUpdateException: An error occurred while saving the entity changes. See the inner exception for details.
---> Microsoft.Data.SqlClient.SqlException (0x80131904): A transport-level error has occurred when receiving results from the server. (provider: TCP Provider, error: 35 - An internal exception was caught)
---> System.IO.IOException: Unable to read data from the transport connection: Connection reset by peer.
---> System.Net.Sockets.SocketException (104): Connection reset by peer
at System.Net.Sockets.Socket.AwaitableSocketAsyncEventArgs.CreateException(SocketError error, Boolean forAsyncThrow)
at System.Net.Sockets.Socket.AwaitableSocketAsyncEventArgs.ReceiveAsync(Socket socket, CancellationToken cancellationToken)
at System.Net.Sockets.Socket.ReceiveAsync(Memory`1 buffer, SocketFlags socketFlags, Boolean fromNetworkStream, CancellationToken cancellationToken)
at System.Net.Sockets.NetworkStream.ReadAsync(Memory`1 buffer, CancellationToken cancellationToken)
at Microsoft.Data.SqlClient.SNI.SNINetworkStream.<>n__0(Memory`1 buffer, CancellationToken cancellationToken)
at Microsoft.Data.SqlClient.SNI.SNINetworkStream.ReadAsync(Memory`1 buffer, CancellationToken cancellationToken) in /_/src/Microsoft.Data.SqlClient/netcore/src/Microsoft/Data/SqlClient/SNI/SNIStreams.ValueTask.cs:line 72
at System.Runtime.CompilerServices.AsyncMethodBuilderCore.Start[<ReadAsync>d__1](<ReadAsync>d__1& stateMachine)
at Microsoft.Data.SqlClient.SNI.SNINetworkStream.ReadAsync(Memory`1 buffer, CancellationToken cancellationToken)
at Microsoft.Data.SqlClient.SNI.SslOverTdsStream.ReadAsync(Memory`1 buffer, CancellationToken cancellationToken) in /_/src/Microsoft.Data.SqlClient/netcore/src/Microsoft/Data/SqlClient/SNI/SslOverTdsStream.NetCoreApp.cs:line 84
at System.Runtime.CompilerServices.AsyncMethodBuilderCore.Start[<ReadAsync>d__5](<ReadAsync>d__5& stateMachine)
at Microsoft.Data.SqlClient.SNI.SslOverTdsStream.ReadAsync(Memory`1 buffer, CancellationToken cancellationToken)
at System.Net.Security.AsyncReadWriteAdapter.ReadAsync(Stream stream, Memory`1 buffer, CancellationToken cancellationToken)
at System.Net.Security.SslStream.<EnsureFullTlsFrameAsync>d__161`1[[System.Net.Security.AsyncReadWriteAdapter, System.Net.Security, Version=8.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a]].MoveNext()
at System.Runtime.CompilerServices.PoolingAsyncValueTaskMethodBuilder`1.StateMachineBox`1[[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e],[System.Net.Security.SslStream.<EnsureFullTlsFrameAsync>d__161`1[[System.Net.Security.AsyncReadWriteAdapter, System.Net.Security, Version=8.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a]], System.Net.Security, Version=8.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a]].ExecutionContextCallback(Object s)
at System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state)
at System.Runtime.CompilerServices.PoolingAsyncValueTaskMethodBuilder`1.StateMachineBox`1[[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e],[System.Net.Security.SslStream.<EnsureFullTlsFrameAsync>d__161`1[[System.Net.Security.AsyncReadWriteAdapter, System.Net.Security, Version=8.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a]], System.Net.Security, Version=8.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a]].MoveNext()
at System.Threading.Tasks.AwaitTaskContinuation.RunOrScheduleAction(IAsyncStateMachineBox box, Boolean allowInlining)
at System.Threading.Tasks.Task.RunContinuations(Object continuationObject)
at System.Threading.Tasks.Task.FinishContinuations()
at System.Threading.Tasks.Task`1[[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]].TrySetResult(Int32 result)
at System.Runtime.CompilerServices.AsyncTaskMethodBuilder`1[[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]].SetExistingTaskResult(Task`1 task, Int32 result)
at System.Runtime.CompilerServices.AsyncValueTaskMethodBuilder`1[[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]].SetResult(Int32 result)
at Microsoft.Data.SqlClient.SNI.SslOverTdsStream.ReadAsync(Memory`1 buffer, CancellationToken cancellationToken) in /_/src/Microsoft.Data.SqlClient/netcore/src/Microsoft/Data/SqlClient/SNI/SslOverTdsStream.NetCoreApp.cs:line 173
at System.Runtime.CompilerServices.AsyncTaskMethodBuilder`1.AsyncStateMachineBox`1[[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e],[Microsoft.Data.SqlClient.SNI.SslOverTdsStream.<ReadAsync>d__5, Microsoft.Data.SqlClient, Version=5.0.0.0, Culture=neutral, PublicKeyToken=23ec7fc2d6eaa4a5]].ExecutionContextCallback(Object s)
at System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state)
at System.Runtime.CompilerServices.AsyncTaskMethodBuilder`1.AsyncStateMachineBox`1[[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e],[Microsoft.Data.SqlClient.SNI.SslOverTdsStream.<ReadAsync>d__5, Microsoft.Data.SqlClient, Version=5.0.0.0, Culture=neutral, PublicKeyToken=23ec7fc2d6eaa4a5]].MoveNext(Thread threadPoolThread)
at System.Runtime.CompilerServices.AsyncTaskMethodBuilder`1.AsyncStateMachineBox`1[[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e],[Microsoft.Data.SqlClient.SNI.SslOverTdsStream.<ReadAsync>d__5, Microsoft.Data.SqlClient, Version=5.0.0.0, Culture=neutral, PublicKeyToken=23ec7fc2d6eaa4a5]].MoveNext()
at System.Threading.Tasks.AwaitTaskContinuation.RunOrScheduleAction(IAsyncStateMachineBox box, Boolean allowInlining)
at System.Threading.Tasks.Task.RunContinuations(Object continuationObject)
at System.Threading.Tasks.Task.FinishContinuations()
at System.Threading.Tasks.Task`1[[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]].TrySetResult(Int32 result)
at System.Runtime.CompilerServices.AsyncTaskMethodBuilder`1[[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]].SetExistingTaskResult(Task`1 task, Int32 result)
at System.Runtime.CompilerServices.AsyncValueTaskMethodBuilder`1[[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]].SetResult(Int32 result)
at Microsoft.Data.SqlClient.SNI.SNINetworkStream.ReadAsync(Memory`1 buffer, CancellationToken cancellationToken) in /_/src/Microsoft.Data.SqlClient/netcore/src/Microsoft/Data/SqlClient/SNI/SNIStreams.ValueTask.cs:line 83
at System.Runtime.CompilerServices.AsyncTaskMethodBuilder`1.AsyncStateMachineBox`1[[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e],[Microsoft.Data.SqlClient.SNI.SNINetworkStream.<ReadAsync>d__1, Microsoft.Data.SqlClient, Version=5.0.0.0, Culture=neutral, PublicKeyToken=23ec7fc2d6eaa4a5]].ExecutionContextCallback(Object s)
at System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state)
at System.Runtime.CompilerServices.AsyncTaskMethodBuilder`1.AsyncStateMachineBox`1[[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e],[Microsoft.Data.SqlClient.SNI.SNINetworkStream.<ReadAsync>d__1, Microsoft.Data.SqlClient, Version=5.0.0.0, Culture=neutral, PublicKeyToken=23ec7fc2d6eaa4a5]].MoveNext(Thread threadPoolThread)
at System.Runtime.CompilerServices.AsyncTaskMethodBuilder`1.AsyncStateMachineBox`1[[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e],[Microsoft.Data.SqlClient.SNI.SNINetworkStream.<ReadAsync>d__1, Microsoft.Data.SqlClient, Version=5.0.0.0, Culture=neutral, PublicKeyToken=23ec7fc2d6eaa4a5]].MoveNext()
at System.Threading.ThreadPool.<>c.<.cctor>b__49_0(Object state)
at System.Threading.Tasks.Sources.ManualResetValueTaskSourceCore`1[[System.Boolean, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]].SignalCompletion()
at System.Threading.Tasks.Sources.ManualResetValueTaskSourceCore`1[[System.Boolean, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]].SetResult(Boolean result)
at System.Net.Sockets.Socket.AwaitableSocketAsyncEventArgs.OnCompleted(SocketAsyncEventArgs _)
at System.Net.Sockets.SocketAsyncEventArgs.OnCompletedInternal()
at System.Net.Sockets.SocketAsyncEventArgs.FinishOperationAsyncSuccess(Int32 bytesTransferred, SocketFlags flags)
at System.Net.Sockets.SocketAsyncEventArgs.CompletionCallback(Int32 bytesTransferred, SocketFlags flags, SocketError socketError)
at System.Net.Sockets.SocketAsyncEventArgs.TransferCompletionCallbackCore(Int32 bytesTransferred, Memory`1 socketAddress, SocketFlags receivedFlags, SocketError socketError)
at System.Net.Sockets.SocketAsyncContext.BufferMemoryReceiveOperation.InvokeCallback(Boolean allowPooling)
at System.Net.Sockets.SocketAsyncContext.OperationQueue`1[[System.Net.Sockets.SocketAsyncContext.ReadOperation, System.Net.Sockets, Version=8.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a]].ProcessAsyncOperation(ReadOperation op)
at System.Net.Sockets.SocketAsyncContext.ProcessAsyncReadOperation(ReadOperation op)
at System.Net.Sockets.SocketAsyncContext.ReadOperation.System.Threading.IThreadPoolWorkItem.Execute()
at System.Net.Sockets.SocketAsyncContext.AsyncOperation.Process()
at System.Net.Sockets.SocketAsyncContext.HandleEvents(SocketEvents events)
at System.Net.Sockets.SocketAsyncEngine.System.Threading.IThreadPoolWorkItem.Execute()
at System.Threading.ThreadPoolWorkQueue.Dispatch()
at System.Threading.PortableThreadPool.WorkerThread.WorkerThreadStart()
at System.Threading.Thread.StartCallback()
--- End of stack trace from previous location ---
--- End of inner exception stack trace ---
at Microsoft.Data.SqlClient.SNI.SNINetworkStream.ReadAsync(Memory`1 buffer, CancellationToken cancellationToken) in /_/src/Microsoft.Data.SqlClient/netcore/src/Microsoft/Data/SqlClient/SNI/SNIStreams.ValueTask.cs:line 77
at Microsoft.Data.SqlClient.SNI.SslOverTdsStream.ReadAsync(Memory`1 buffer, CancellationToken cancellationToken) in /_/src/Microsoft.Data.SqlClient/netcore/src/Microsoft/Data/SqlClient/SNI/SslOverTdsStream.NetCoreApp.cs:line 91
at System.Net.Security.SslStream.<EnsureFullTlsFrameAsync>d__161`1[[System.Net.Security.AsyncReadWriteAdapter, System.Net.Security, Version=8.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a]].MoveNext()
at System.Runtime.CompilerServices.PoolingAsyncValueTaskMethodBuilder`1.StateMachineBox`1[[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e],[System.Net.Security.SslStream.<EnsureFullTlsFrameAsync>d__161`1[[System.Net.Security.AsyncReadWriteAdapter, System.Net.Security, Version=8.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a]], System.Net.Security, Version=8.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a]].System.Threading.Tasks.Sources.IValueTaskSource<TResult>.GetResult(Int16 token)
at System.Net.Security.SslStream.<ReadAsyncInternal>d__163`1[[System.Net.Security.AsyncReadWriteAdapter, System.Net.Security, Version=8.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a]].MoveNext()
at System.Runtime.CompilerServices.PoolingAsyncValueTaskMethodBuilder`1.StateMachineBox`1[[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e],[System.Net.Security.SslStream.<ReadAsyncInternal>d__163`1[[System.Net.Security.AsyncReadWriteAdapter, System.Net.Security, Version=8.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a]], System.Net.Security, Version=8.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a]].System.Threading.Tasks.Sources.IValueTaskSource<TResult>.GetResult(Int16 token)
at Microsoft.Data.SqlClient.SNI.SNISslStream.ReadAsync(Memory`1 buffer, CancellationToken cancellationToken) in /_/src/Microsoft.Data.SqlClient/netcore/src/Microsoft/Data/SqlClient/SNI/SNIStreams.ValueTask.cs:line 28
at Microsoft.Data.SqlClient.SqlCommand.<>c.<ExecuteDbDataReaderAsync>b__211_0(Task`1 result) in /_/src/Microsoft.Data.SqlClient/netcore/src/Microsoft/Data/SqlClient/SqlCommand.cs:line 2654
at System.Threading.Tasks.ContinuationResultTaskFromResultTask`2[[Microsoft.Data.SqlClient.SqlDataReader, Microsoft.Data.SqlClient, Version=5.0.0.0, Culture=neutral, PublicKeyToken=23ec7fc2d6eaa4a5],[System.Data.Common.DbDataReader, System.Data.Common, Version=8.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a]].InnerInvoke()
at System.Threading.Tasks.Task.<>c.<.cctor>b__281_0(Object obj)
at System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state)
--- End of stack trace from previous location ---
at System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state)
at System.Threading.Tasks.Task.ExecuteWithThreadLocal(Task& currentTaskSlot, Thread threadPoolThread)
--- End of stack trace from previous location ---
at Microsoft.EntityFrameworkCore.Storage.RelationalCommand.ExecuteReaderAsync(RelationalCommandParameterObject parameterObject, CancellationToken cancellationToken)
at Microsoft.EntityFrameworkCore.Storage.RelationalCommand.ExecuteReaderAsync(RelationalCommandParameterObject parameterObject, CancellationToken cancellationToken)
at Microsoft.EntityFrameworkCore.Update.ReaderModificationCommandBatch.ExecuteAsync(IRelationalConnection connection, CancellationToken cancellationToken)
ClientConnectionId:606c1b87-0d60-4b3b-bb38-eed46b0d2c71
--- End of inner exception stack trace ---
at Microsoft.EntityFrameworkCore.Update.ReaderModificationCommandBatch.ExecuteAsync(IRelationalConnection connection, CancellationToken cancellationToken)
at Microsoft.EntityFrameworkCore.SqlServer.Update.Internal.SqlServerModificationCommandBatch.ExecuteAsync(IRelationalConnection connection, CancellationToken cancellationToken)
at Microsoft.EntityFrameworkCore.Update.Internal.BatchExecutor.ExecuteAsync(IEnumerable`1 commandBatches, IRelationalConnection connection, CancellationToken cancellationToken)
at Microsoft.EntityFrameworkCore.Update.Internal.BatchExecutor.ExecuteAsync(IEnumerable`1 commandBatches, IRelationalConnection connection, CancellationToken cancellationToken)
at Microsoft.EntityFrameworkCore.Update.Internal.BatchExecutor.ExecuteAsync(IEnumerable`1 commandBatches, IRelationalConnection connection, CancellationToken cancellationToken)
at Microsoft.EntityFrameworkCore.ChangeTracking.Internal.StateManager.SaveChangesAsync(IList`1 entriesToSave, CancellationToken cancellationToken)
at Microsoft.EntityFrameworkCore.ChangeTracking.Internal.StateManager.SaveChangesAsync(StateManager stateManager, Boolean acceptAllChangesOnSuccess, CancellationToken cancellationToken)
at Microsoft.EntityFrameworkCore.Storage.ExecutionStrategy.<>c__DisplayClass30_0`2.<<ExecuteAsync>b__0>d[[System.ValueTuple`2[[Microsoft.EntityFrameworkCore.ChangeTracking.Internal.StateManager, Microsoft.EntityFrameworkCore, Version=8.0.7.0, Culture=neutral, PublicKeyToken=adb9793829ddae60],[System.Boolean, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]], System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e],[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]].MoveNext()
--- End of stack trace from previous location ---
at Microsoft.EntityFrameworkCore.Storage.ExecutionStrategy.<ExecuteImplementationAsync>d__31`2[[System.ValueTuple`2[[Microsoft.EntityFrameworkCore.ChangeTracking.Internal.StateManager, Microsoft.EntityFrameworkCore, Version=8.0.7.0, Culture=neutral, PublicKeyToken=adb9793829ddae60],[System.Boolean, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]], System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e],[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]].MoveNext()
at Microsoft.EntityFrameworkCore.Storage.ExecutionStrategy.<ExecuteImplementationAsync>d__31`2[[System.ValueTuple`2[[Microsoft.EntityFrameworkCore.ChangeTracking.Internal.StateManager, Microsoft.EntityFrameworkCore, Version=8.0.7.0, Culture=neutral, PublicKeyToken=adb9793829ddae60],[System.Boolean, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]], System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e],[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]].MoveNext()
at Microsoft.EntityFrameworkCore.Storage.ExecutionStrategy.<ExecuteAsync>d__30`2[[System.ValueTuple`2[[Microsoft.EntityFrameworkCore.ChangeTracking.Internal.StateManager, Microsoft.EntityFrameworkCore, Version=8.0.7.0, Culture=neutral, PublicKeyToken=adb9793829ddae60],[System.Boolean, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]], System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e],[System.Int32, System.Private.CoreLib, Version=8.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]].MoveNext()
at Microsoft.EntityFrameworkCore.DbContext.SaveChangesAsync(Boolean acceptAllChangesOnSuccess, CancellationToken cancellationToken)
at Microsoft.EntityFrameworkCore.DbContext.SaveChangesAsync(Boolean acceptAllChangesOnSuccess, CancellationToken cancellationToken)
at Core.DAL.UnitOfWork.SaveInspection(InspectionRecord inspection, Dictionary`2 failedImages) in D:EagleEyeCoreDALUnitOfWork.cs:line 308}
The related classes are as follows:
public class InspectionRecord
{
/// <summary>
/// The PK, auto-incremented
/// </summary>
public int InspectionRecordId { get; set; }
/// <summary>
/// The date of the inspection
/// </summary>
public DateTime InspectionDate { get; set; }
/// <summary>
/// The name of the inspector
/// </summary>
public string? Inspector { get; set; }
/// <summary>
/// The notes from the inspection
/// </summary>
public string? Notes { get; set; }
/// <summary>
/// The calculated overall condition rating
/// </summary>
public float OverallConditionRating { get; set; }
/// <summary>
/// The FK to the structure
/// </summary>
public virtual int BridgeId { get; set; }
/// <summary>
/// The navigation property to the structure
/// </summary>
public virtual Bridge Bridge { get; set; }
/// <summary>
/// The list of element records for the inspection
/// </summary>
public virtual ICollection<ElementRecord> ElementRecords { get; set; } = [];
}
public class ElementRecord : INotifyPropertyChanged
{
/// <summary>
/// The PK, auto-incremented
/// </summary>
public int ElementRecordId { get; set; }
/// <summary>
/// The condition rating of the element.
/// </summary>
public byte ConditionRating
{
get => conditionRating;
set
{
conditionRating = value;
OnPropertyChanged(nameof(ConditionRating));
}
}
/// <summary>
/// Notes about the element.
/// </summary>
public string? Notes { get; set; }
/// <summary>
/// The FK to the element
/// </summary>
public virtual int ElementId { get; set; }
/// <summary>
/// The navigation property to the element
/// </summary>
public virtual Element Element { get; set; } = null!;
/// <summary>
/// The FK to the inspection
/// </summary>
public virtual int InspectionRecordId { get; set; }
/// <summary>
/// The navigation property to the inspection
/// </summary>
public virtual InspectionRecord InspectionRecord { get; set; } = null!;
/// <summary>
/// The navigation property for the inspection images of the element.
/// </summary>
public virtual ICollection<ElementRecordImage> ElementRecordImages { get; set; } = [];
[NotMapped]
byte conditionRating;
public event PropertyChangedEventHandler? PropertyChanged;
private void OnPropertyChanged(string propertyName)
{
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
}
}
My database context file is as follows:
public partial class EagleEyeDbContext : DbContext
{
protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
{
string connectionString = @"Server=<server>;Initial Catalog=<db>;Persist Security Info=False;User ID=<id>;Password=<password>;MultipleActiveResultSets=False;Encrypt=True;TrustServerCertificate=False;Connection Timeout=30;";
optionsBuilder.UseSqlServer(connectionString,
options => {
options.EnableRetryOnFailure()
.MaxBatchSize(5);
});
#if DEBUG
optionsBuilder.AddInterceptors(new EFCommandInterceptor());
optionsBuilder.LogTo(Console.WriteLine, Microsoft.Extensions.Logging.LogLevel.Information);
#endif
}
public DbSet<Bridge> Bridges { get; set; }
public DbSet<Element> Elements { get; set; }
public DbSet<ImageItem> Images { get; set; }
public DbSet<InspectionRecord> InspectionRecords { get; set; }
public DbSet<ElementRecord> ElementRecords { get; set; }
public DbSet<BridgeImage> BridgeImages { get; set; }
public DbSet<ElementRecordImage> ElementRecordImages { get; set; }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder);
// Inheritance strategies - default to table per hierarchy
// cascade delete strategies - see documentation for details
modelBuilder.Entity<Bridge>()
.HasMany(b => b.BridgeImages)
.WithOne(i => i.Bridge)
.HasForeignKey(i => i.BridgeId)
.OnDelete(DeleteBehavior.Cascade);
modelBuilder.Entity<Bridge>()
.HasMany(b => b.Inspections)
.WithOne(i => i.Bridge)
.HasForeignKey(i => i.BridgeId)
.OnDelete(DeleteBehavior.Cascade);
modelBuilder.Entity<Bridge>()
.HasMany(b => b.Elements)
.WithOne(e => e.Bridge)
.HasForeignKey(e => e.BridgeId)
.OnDelete(DeleteBehavior.Cascade);
modelBuilder.Entity<InspectionRecord>()
.HasMany(i => i.ElementRecords)
.WithOne(e => e.InspectionRecord)
.HasForeignKey(e => e.InspectionRecordId)
.OnDelete(DeleteBehavior.Restrict); // break multiple cascade paths
modelBuilder.Entity<Element>()
.HasMany(e => e.ElementRecords)
.WithOne(r => r.Element)
.HasForeignKey(r => r.ElementId)
.OnDelete(DeleteBehavior.Restrict); // break multiple cascade paths
modelBuilder.Entity<ElementRecord>()
.HasMany(r => r.ElementRecordImages)
.WithOne(i => i.ElementRecord)
.HasForeignKey(i => i.ElementRecordId)
.OnDelete(DeleteBehavior.Cascade);
}
}
This is how I try to save it to the database:
try
{
InspectionRepository.Add(inspection);
await context.SaveChangesAsync();
result = InspectionSaveResult.Success();
}
catch (Exception ex)
{
logger.Error(ex, "Failed to save inspection");
result = InspectionSaveResult.Failure("Failed to save inspection, see app log for details");
}
InspectionRepository
is a generic repository which calls dbSet.Add(entity);
.
Since the error message is extremely cryptic but reveals that the error is in the database, I created an extended event as follows:
CREATE EVENT SESSION [Session3] ON DATABASE
ADD EVENT sqlserver.sql_statement_completed(
ACTION(sqlserver.sql_text)
WHERE ([sqlserver].[sql_text] like '%INSERT%INTO%ElementRecords%')),
ADD EVENT sqlserver.sql_statement_starting(
ACTION(sqlserver.sql_text)
WHERE ([sqlserver].[sql_text] like '%INSERT%INTO%ElementRecords%'))
ADD TARGET package0.event_file(SET filename=N'https://<user>.blob.core.windows.net/<container>/session3.xel')
WITH (MAX_MEMORY=4096 KB,EVENT_RETENTION_MODE=ALLOW_SINGLE_EVENT_LOSS,MAX_DISPATCH_LATENCY=30 SECONDS,MAX_EVENT_SIZE=0 KB,MEMORY_PARTITION_MODE=NONE,TRACK_CAUSALITY=OFF,STARTUP_STATE=OFF)
GO
But I don’t see any events in the log. I tried to capture even more detailed events with
CREATE EVENT SESSION [Session2] ON DATABASE
ADD EVENT sqlserver.error_reported,
ADD EVENT sqlserver.sql_batch_completed,
ADD EVENT sqlserver.sql_batch_starting,
ADD EVENT sqlserver.sql_statement_completed,
ADD EVENT sqlserver.sql_statement_starting
ADD TARGET package0.event_file(SET filename=N'https://<user>.blob.core.windows.net/<container>/session2.xel')
WITH (MAX_MEMORY=4096 KB,EVENT_RETENTION_MODE=ALLOW_SINGLE_EVENT_LOSS,MAX_DISPATCH_LATENCY=30 SECONDS,MAX_EVENT_SIZE=0 KB,MEMORY_PARTITION_MODE=NONE,TRACK_CAUSALITY=OFF,STARTUP_STATE=OFF)
GO
but there were no entries related with the EF errors.
I learnt that SQL Server has a limit of 2100 parameters per batch but my batch has nowhere that limit.
Why could this error happen? Is there any other way to track the origin of this message?