tursodatabase/turso · error · InvalidOperationException
The connection is already open.
Error message
The connection is already open.
What it means
Open() throws InvalidOperationException when either the local database handle (_turso) or the remote client (_remoteClient) is already initialized (TursoConnection.cs:56-58) — the connection is already open. TursoConnection does not implicitly reopen, so a second Open without an intervening Close is an error.
Source
Thrown at bindings/dotnet/src/Turso.Data/TursoConnection.cs:76
_connectionOptions.IsRemote && !_connectionOptions.IsReplica
|| _syncDatabase is not null;
protected override DbProviderFactory DbProviderFactory => TursoFactory.Instance;
public TursoConnection() : this("")
{
}
public TursoConnection(string connectionString)
{
_connectionOptions = TursoConnectionOptions.Parse(connectionString);
}
public override void Open()
{
ObjectDisposedException.ThrowIf(_disposed, this);
if (_turso is not null || _remoteClient is not null)
throw new InvalidOperationException("The connection is already open.");
if (_connectionOptions.IsRemote)
{
OpenRemote();
return;
}
ValidateLocalOnlyOptions();
var filename = _connectionOptions["Data Source"] ?? ":memory:";
var cipher = _connectionOptions.GetEncryptionCipher();
var hexkey = _connectionOptions["Encryption Key"];
if (cipher.HasValue)
{
if (string.IsNullOrWhiteSpace(hexkey))
throw new InvalidOperationException("Encryption Key is required when Encryption Cipher is specified.");
View on GitHub (pinned to 6c72522679)
Solutions
- Check state first: if (conn.State != ConnectionState.Open) await conn.OpenAsync(ct);
- Centralize opening in one place (a lazy-open helper or connection factory) so callers never open directly.
- Fix DI lifetimes or the retry policy so Open is invoked at most once per open connection.
Example fix
// before
await conn.OpenAsync(ct);
// retry policy or second caller:
await conn.OpenAsync(ct); // throws InvalidOperationException
// after
if (conn.State != ConnectionState.Open)
await conn.OpenAsync(ct); Defensive patterns
Strategy: validation
Validate before calling
if (conn.State != ConnectionState.Open)
await conn.OpenAsync(ct); Prevention
- Centralize Open behind one EnsureOpen helper used by all consumers.
- Exclude Open from retry delegates, or make the retry check State first.
- Match DI lifetime to usage so a connection is not opened by multiple consumers.
When it happens
Trigger: conn.Open(); conn.Open(); or an open-retry wrapper (e.g. Polly) that re-runs the open delegate without checking State; double-open across a base class and derived code.
Common situations: Retry policies around connection establishment; DI singleton/scoped connections reused across requests where each consumer calls Open; wrappers that call Open 'to be safe' on possibly-open connections.
Related errors
- Turso database is closed.
- Connection must be a TursoConnection.
- Connection must be set before executing a command.
- Connection must be set before preparing a command.
- Turso batch execution is currently supported only for remote
AI-assisted analysis of tursodatabase/turso@6c72522679 (2026-08-20).
Data as JSON: /api/errors/62e860deb160abfb.
Report an issue: GitHub.