{"record":{"id":"4b34a8d9c76db287","repo":"DapperLib/Dapper","slug":"async-operations-require-use-of-a-dbconnection-or","errorCode":null,"errorMessage":"Async operations require use of a DbConnection or an already-open IDbConnection","messagePattern":"Async operations require use of a DbConnection or an already-open IDbConnection","errorType":"exception","errorClass":"InvalidOperationException","httpStatus":null,"severity":"error","filePath":"Dapper/SqlMapper.Async.cs","lineNumber":403,"sourceCode":"            if (task.Status == TaskStatus.Faulted && Settings.DisableCommandBehaviorOptimizations(behavior, task.Exception!.InnerException!))\r\n            { // we can retry; this time it will have different flags\r\n                return cmd.ExecuteReaderAsync(GetBehavior(wasClosed, behavior), cancellationToken);\r\n            }\r\n            return task;\r\n        }\r\n\r\n        /// <summary>\r\n        /// Attempts to open a connection asynchronously, with a better error message for unsupported usages.\r\n        /// </summary>\r\n        private static Task TryOpenAsync(this IDbConnection cnn, CancellationToken cancel)\r\n        {\r\n            if (cnn is DbConnection dbConn)\r\n            {\r\n                return dbConn.OpenAsync(cancel);\r\n            }\r\n            else\r\n            {\r\n                throw new InvalidOperationException(\"Async operations require use of a DbConnection or an already-open IDbConnection\");\r\n            }\r\n        }\r\n\r\n        /// <summary>\r\n        /// Attempts setup a <see cref=\"DbCommand\"/> on a <see cref=\"DbConnection\"/>, with a better error message for unsupported usages.\r\n        /// </summary>\r\n        private static DbCommand TrySetupAsyncCommand(this CommandDefinition command, IDbConnection cnn, Action<IDbCommand, object?>? paramReader)\r\n        {\r\n            if (command.SetupCommand(cnn, paramReader) is DbCommand dbCommand)\r\n            {\r\n                return dbCommand;\r\n            }\r\n            else\r\n            {\r\n                throw new InvalidOperationException(\"Async operations require use of a DbConnection or an IDbConnection where .CreateCommand() returns a DbCommand\");\r\n            }\r\n        }\r\n\r","sourceCodeStart":385,"sourceCodeEnd":421,"githubUrl":"https://github.com/DapperLib/Dapper/blob/72a54c475f75e18cb93cba0809d00a5e6e49efd9/Dapper/SqlMapper.Async.cs#L385-L421","documentation":"TryOpenAsync throws InvalidOperationException(\"Async operations require use of a DbConnection or an already-open IDbConnection\") when the connection passed to an async query is not a DbConnection (i.e. it is a custom/raw IDbConnection implementation). Dapper's async path calls OpenAsync, which only exists on DbConnection; a plain IDbConnection cannot be opened asynchronously. The error message is a deliberate, clearer substitute for a MissingMethodException.","triggerScenarios":"Passing a custom IDbConnection implementation that does not derive from System.Data.Common.DbConnection to any async Dapper method (QueryAsync, ExecuteAsync, etc.) while the connection is closed — Dapper then tries to open it asynchronously and fails.","commonSituations":"Mocking IDbConnection for tests and exercising async APIs; wrapping a legacy provider whose connection type predates DbConnection; a third-party ADO.NET shim that only implements IDbConnection.","solutions":["Use a connection type derived from System.Data.Common.DbConnection (the standard provider types like SqlConnection, NpgsqlConnection, MySqlConnection, SQLiteConnection all are).","Open the connection yourself before the async call — but the message notes DbConnection is still required, so prefer switching to a real DbConnection-derived type.","For tests, mock at the DbConnection level or use a provider that implements it (e.g. Microsoft.Data.Sqlite)."],"exampleFix":"// before (custom raw IDbConnection)\npublic class MyConn : IDbConnection { ... }\nawait cnn.QueryAsync<T>(sql); // throws\n\n// after\ncnn.Open(); // pre-open; and/or switch to a DbConnection-derived type\nawait cnn.QueryAsync<T>(sql);","handlingStrategy":"type-guard","validationCode":"if (cnn is not DbConnection) throw new InvalidOperationException(\"Async Dapper requires a DbConnection-derived connection.\");\nawait cnn.QueryAsync<T>(sql);","typeGuard":"static bool SupportsAsync(IDbConnection c) => c is System.Data.Common.DbConnection;","tryCatchPattern":"try { await cnn.QueryAsync<T>(sql); }\ncatch (InvalidOperationException ex) when (ex.Message.Contains(\"DbConnection\"))\n{ /* switch to a DbConnection-derived provider type */ }","preventionTips":["Use standard DbConnection-derived providers (SqlConnection, NpgsqlConnection, etc.) for async work.","In tests, mock DbConnection or use an in-memory provider like Microsoft.Data.Sqlite rather than raw IDbConnection."],"tags":["async","connection","invalid-operation","ado-net"],"backgroundTag":null,"analyzedSha":"72a54c475f75e18cb93cba0809d00a5e6e49efd9","analyzedAt":"2026-08-13T14:18:18.115Z","schemaVersion":2},"datasetVersion":"2026-08-13T19:17:28.613Z"}