【问题标题】:mysql in dot net core (pomelo mysql provider) - Cannot access a disposed objectdot net core(pomelo mysql provider)中的mysql - 无法访问已处置的对象
【发布时间】:2020-07-09 12:11:17
【问题描述】:

我在将 .Net Core (3.1) 与 Mysql(提供者 Pomelo.mysql 3.1.1)一起使用时遇到问题。 我有一个非常基本的函数(只是从表中获取所有记录,一个单行函数),但由于某种原因,我总是得到 ObjectDisposedException,所有堆栈跟踪都发生在 Pomelo Provider 中。 有谁知道是什么原因造成的?

System.ObjectDisposedException: Cannot access a disposed object.
      Object name: 'MySqlConnection'.
         at MySql.Data.MySqlClient.MySqlConnection.VerifyNotDisposed() in C:\projects\mysqlconnector\src\MySqlConnector\MySql.Data.MySqlClient\MySqlConnection.cs:line 707
         at MySql.Data.MySqlClient.MySqlConnection.get_Session() in C:\projects\mysqlconnector\src\MySqlConnector\MySql.Data.MySqlClient\MySqlConnection.cs:line 480
         at MySqlConnector.Core.ICancellableCommandExtensions.ResetCommandTimeout(ICancellableCommand command) in C:\projects\mysqlconnector\src\MySqlConnector\Core\ICancellableCommand.cs:line 42
         at MySql.Data.MySqlClient.MySqlCommand.ExecuteDbDataReaderAsync(CommandBehavior behavior, CancellationToken cancellationToken) in C:\projects\mysqlconnector\src\MySqlConnector\MySql.Data.MySqlClient\MySqlCommand.cs:line 261

初始化代码为:

            services
                .AddDbContextPool<DeviceDbContext>(o => o
                    .UseMySql(connectionString, o => o
                        .ServerVersion(new ServerVersion(new Version(8, 0, 19), ServerType.MySql))
                        .MigrationsAssembly(typeof(DeviceDbContext).Assembly.GetName().Name)
                        .EnableRetryOnFailure()))
                .AddHostedService<MigrationsHostedService<DeviceDbContext>>()
                .AddHealthChecks()
                .AddMySql(connectionString, "mysql");
return services;

后来就这样了

services.AddDbContext();

那么以后的使用就比较简单了:

private readonly DeviceDbContextdbContext;

        public DeviceEntityFrameworkRepository(DeviceDbContext dbContext)
        {
            EnsureArg.IsNotNull(dbContext, nameof(dbContext));
            this.dbContext = dbContext;
        }

        public async Task<IEnumerable<Device>> FindAllDevicesAsync()
            => await this.dbContext.Set<Device>().ToListAsync().ConfigureAwait(false);

完整的异常堆栈是

System.ObjectDisposedException: Cannot access a disposed object.
      Object name: 'MySqlConnection'.
         at MySql.Data.MySqlClient.MySqlConnection.VerifyNotDisposed() in C:\projects\mysqlconnector\src\MySqlConnector\MySql.Data.MySqlClient\MySqlConnection.cs:line 707
         at MySql.Data.MySqlClient.MySqlConnection.get_Session() in C:\projects\mysqlconnector\src\MySqlConnector\MySql.Data.MySqlClient\MySqlConnection.cs:line 480
         at MySqlConnector.Core.ICancellableCommandExtensions.ResetCommandTimeout(ICancellableCommand command) in C:\projects\mysqlconnector\src\MySqlConnector\Core\ICancellableCommand.cs:line 42
         at MySql.Data.MySqlClient.MySqlCommand.ExecuteDbDataReaderAsync(CommandBehavior behavior, CancellationToken cancellationToken) in C:\projects\mysqlconnector\src\MySqlConnector\MySql.Data.MySqlClient\MySqlCommand.cs:line 261
         at System.Data.Common.DbCommand.ExecuteReaderAsync(CancellationToken cancellationToken)
         at Microsoft.EntityFrameworkCore.Storage.RelationalCommand.ExecuteReaderAsync(RelationalCommandParameterObject parameterObject, CancellationToken cancellationToken)
         at Microsoft.EntityFrameworkCore.Storage.RelationalCommand.ExecuteReaderAsync(RelationalCommandParameterObject parameterObject, CancellationToken cancellationToken)
         at Microsoft.EntityFrameworkCore.Storage.RelationalCommand.ExecuteReaderAsync(RelationalCommandParameterObject parameterObject, CancellationToken cancellationToken)
         at Microsoft.EntityFrameworkCore.Query.Internal.QueryingEnumerable`1.AsyncEnumerator.InitializeReaderAsync(DbContext _, Boolean result, CancellationToken cancellationToken)
         at Microsoft.EntityFrameworkCore.Storage.ExecutionStrategy.ExecuteImplementationAsync[TState,TResult](Func`4 operation, Func`4 verifySucceeded, TState state, CancellationToken cancellationToken)
         at Microsoft.EntityFrameworkCore.Storage.ExecutionStrategy.ExecuteImplementationAsync[TState,TResult](Func`4 operation, Func`4 verifySucceeded, TState state, CancellationToken cancellationToken)
         at Microsoft.EntityFrameworkCore.Query.Internal.QueryingEnumerable`1.AsyncEnumerator.MoveNextAsync()

【问题讨论】:

  • 我们能得到一些代码吗?你如何设置你的 DI(假设你正在使用它)?你是如何使用上下文的?
  • 你能粘贴完整的异常调用堆栈吗?发生异常时你的代码是什么?
  • 在您向我们提供实例化数据库连接的代码及其使用方式之前,我们真的无能为力。
  • 使用这些详细信息编辑了问题,无法将其添加为评论
  • 异常调用堆栈仍然不包含您的任何代码。您是否保存IEnumerable&lt;&gt; 值并在关闭数据库连接后访问它?这可能会导致此错误。

标签: c# mysql .net-core pomelo-entityframeworkcore-mysql


【解决方案1】:

初始化代码为:

            services
                .AddDbContextPool<DeviceDbContext>(o => o
                    .UseMySql(connectionString, o => o
                        .ServerVersion(new ServerVersion(new Version(8, 0, 19), ServerType.MySql))
                        .MigrationsAssembly(typeof(DeviceDbContext).Assembly.GetName().Name)
                        .EnableRetryOnFailure()))
                .AddHostedService<MigrationsHostedService<DeviceDbContext>>()
                .AddHealthChecks()
                .AddMySql(connectionString, "mysql");
return services;

后来就这样了

services.AddDbContext();

听起来你正在实例化 两个 DbContexts。您可能想使用AddDbContextPool()AddDbContext(),但不能同时使用两者。

出于测试目的,从使用AddDbContext() 开始,看看您是否仍然过早地释放上下文。

如果您愿意,您还可以发布/上传您的完整项目,以便我们仔细查看您的代码到底出了什么问题。

【讨论】:

    猜你喜欢
    • 2018-07-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-08-29
    • 2018-11-01
    • 1970-01-01
    • 2011-10-23
    相关资源
    最近更新 更多