-
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathSQLiteSession.cs
More file actions
146 lines (130 loc) · 4.98 KB
/
Copy pathSQLiteSession.cs
File metadata and controls
146 lines (130 loc) · 4.98 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
using System;
using System.Collections.Generic;
using System.Data;
using Microsoft.Data.Sqlite;
namespace DBAClientX;
/// <summary>
/// Represents a SQLite connection session owned and managed by <see cref="SQLite"/>.
/// </summary>
/// <remarks>
/// The session keeps provider-specific connection and transaction objects inside DBAClientX while
/// allowing callers to run related commands against the same SQLite connection.
/// </remarks>
public sealed class SQLiteSession : IDisposable
{
private readonly SQLite _client;
private readonly SqliteConnection _connection;
private readonly SqliteTransaction? _transaction;
private readonly bool _ownsConnection;
private bool _disposed;
internal SQLiteSession(SQLite client, SqliteConnection connection)
: this(client, connection, transaction: null, ownsConnection: true)
{
}
internal SQLiteSession(SQLite client, SqliteConnection connection, SqliteTransaction transaction)
: this(client, connection, transaction, ownsConnection: false)
{
}
private SQLiteSession(
SQLite client,
SqliteConnection connection,
SqliteTransaction? transaction,
bool ownsConnection)
{
_client = client ?? throw new ArgumentNullException(nameof(client));
_connection = connection ?? throw new ArgumentNullException(nameof(connection));
_transaction = transaction;
_ownsConnection = ownsConnection;
}
/// <summary>
/// Executes a SQL statement that does not return rows using this session's connection.
/// </summary>
/// <param name="query">SQL command text.</param>
/// <param name="parameters">Optional parameter values.</param>
/// <returns>The number of rows affected by the command.</returns>
public int ExecuteNonQuery(string query, IDictionary<string, object?>? parameters = null)
{
ThrowIfDisposed();
return _client.ExecuteSessionNonQuery(_connection, _transaction, query, parameters);
}
/// <summary>
/// Executes a SQL statement and returns the first column of the first row.
/// </summary>
/// <param name="query">SQL command text.</param>
/// <param name="parameters">Optional parameter values.</param>
/// <returns>The scalar value returned by the provider.</returns>
public object? ExecuteScalar(string query, IDictionary<string, object?>? parameters = null)
{
ThrowIfDisposed();
return _client.ExecuteSessionScalar(_connection, _transaction, query, parameters);
}
/// <summary>
/// Executes a query and maps each row through a provider-neutral <see cref="IDataRecord"/>.
/// </summary>
/// <typeparam name="T">The row projection type.</typeparam>
/// <param name="query">SQL query text.</param>
/// <param name="map">Mapping callback invoked for each row.</param>
/// <param name="parameters">Optional parameter values.</param>
/// <param name="initialize">Optional callback invoked once after the reader opens.</param>
/// <returns>The mapped rows.</returns>
public IReadOnlyList<T> QueryAsList<T>(
string query,
Func<IDataRecord, T> map,
IDictionary<string, object?>? parameters = null,
Action<IDataRecord>? initialize = null)
{
ThrowIfDisposed();
return _client.ExecuteSessionQueryAsList(_connection, _transaction, query, map, parameters, initialize);
}
/// <summary>
/// Runs a group of operations inside one SQLite transaction using this session's connection.
/// </summary>
/// <typeparam name="TResult">The operation result type.</typeparam>
/// <param name="operation">Callback that receives a transaction-bound session.</param>
/// <returns>The callback result after the transaction commits.</returns>
public TResult RunInTransaction<TResult>(Func<SQLiteSession, TResult> operation)
{
ThrowIfDisposed();
if (_transaction != null)
{
throw new DbaTransactionException("A session transaction is already active.");
}
return _client.ExecuteSessionTransaction(_connection, operation);
}
/// <summary>
/// Runs a group of operations inside one SQLite transaction using this session's connection.
/// </summary>
/// <param name="operation">Callback that receives a transaction-bound session.</param>
public void RunInTransaction(Action<SQLiteSession> operation)
{
if (operation == null)
{
throw new ArgumentNullException(nameof(operation));
}
RunInTransaction(session =>
{
operation(session);
return true;
});
}
/// <inheritdoc />
public void Dispose()
{
if (_disposed)
{
return;
}
if (_ownsConnection)
{
_connection.Dispose();
}
_disposed = true;
}
private void ThrowIfDisposed()
{
if (_disposed)
{
throw new ObjectDisposedException(nameof(SQLiteSession));
}
}
}