Jasonnn
Jasonnn
CC#
Created by Jasonnn on 11/12/2024 in #help
Threading and Microsoft.Data.Sqlite
I’ll look for the documentation of SqliteConnection
25 replies
CC#
Created by Jasonnn on 11/12/2024 in #help
Threading and Microsoft.Data.Sqlite
it doesn’t crash.
25 replies
CC#
Created by Jasonnn on 11/12/2024 in #help
Threading and Microsoft.Data.Sqlite
The reason why I thought sqlite was handling it well was that when each thread uses its own connection object,
25 replies
CC#
Created by Jasonnn on 11/12/2024 in #help
Threading and Microsoft.Data.Sqlite
Like the error looks like a GC problem
25 replies
CC#
Created by Jasonnn on 11/12/2024 in #help
Threading and Microsoft.Data.Sqlite
SQLite only sees « one user » right?
25 replies
CC#
Created by Jasonnn on 11/12/2024 in #help
Threading and Microsoft.Data.Sqlite
Because if I only have one connection object
25 replies
CC#
Created by Jasonnn on 11/12/2024 in #help
Threading and Microsoft.Data.Sqlite
Umm I’m not sure, isn’t it a c# problem
25 replies
CC#
Created by Jasonnn on 11/12/2024 in #help
Threading and Microsoft.Data.Sqlite
But then I need to have some sort of « locking » mechanism?
25 replies
CC#
Created by Jasonnn on 11/12/2024 in #help
Threading and Microsoft.Data.Sqlite
Or I have one connection object that all threads use
25 replies
CC#
Created by Jasonnn on 11/12/2024 in #help
Threading and Microsoft.Data.Sqlite
Which I thought was bad
25 replies
CC#
Created by Jasonnn on 11/12/2024 in #help
Threading and Microsoft.Data.Sqlite
Well it was either I spawn one connection per thread
25 replies
CC#
Created by Jasonnn on 11/12/2024 in #help
Threading and Microsoft.Data.Sqlite
Ah I see Edit: but it says « By default, Lazy<T> objects are thread-safe. That is, if the constructor does not specify the kind of thread safety, the Lazy<T> objects it creates are thread-safe. In multi-threaded scenarios, the first thread to access the Value property of a thread-safe Lazy<T> object initializes it for all subsequent accesses on all threads, and all threads share the same data. » in the documentation
25 replies
CC#
Created by Jasonnn on 11/12/2024 in #help
Threading and Microsoft.Data.Sqlite
Thread 10 read 17 rows.
Thread 6 read 17 rows.
Thread 16 read 17 rows.
Thread 10 read 17 rows.
Thread 11 read 17 rows.
Thread 6 read 17 rows.
Thread 12 read 17 rows.
Thread 9 read 17 rows.
Thread 14 read 17 rows.
Thread 15 read 17 rows.
Thread 18 read 17 rows.
Thread 16 read 17 rows.
Thread 7 read 17 rows.
Thread 8 read 17 rows.
Thread 13 read 17 rows.
Thread 18 read 17 rows.
Thread 17 read 17 rows.
Thread 20 read 17 rows.
Thread 19 read 17 rows.
Thread 12 read 17 rows.
Thread 14 read 17 rows.
Thread 11 read 17 rows.
Thread 10 read 17 rows.
Thread 6 read 17 rows.
Thread 9 read 17 rows.
Thread 15 read 17 rows.
Thread 16 read 17 rows.
Thread 8 read 17 rows.
Unhandled exception. System.NullReferenceException: Object reference not set to an instance of an object.
at Microsoft.Data.Sqlite.SqliteConnection.RemoveCommand(SqliteCommand command)
at Microsoft.Data.Sqlite.SqliteCommand.Dispose(Boolean disposing)
at System.ComponentModel.Component.Dispose()
at SQLiteMultithreadingExample.SqlDatabase.QueryDatabase() in
Thread 10 read 17 rows.
Thread 6 read 17 rows.
Thread 16 read 17 rows.
Thread 10 read 17 rows.
Thread 11 read 17 rows.
Thread 6 read 17 rows.
Thread 12 read 17 rows.
Thread 9 read 17 rows.
Thread 14 read 17 rows.
Thread 15 read 17 rows.
Thread 18 read 17 rows.
Thread 16 read 17 rows.
Thread 7 read 17 rows.
Thread 8 read 17 rows.
Thread 13 read 17 rows.
Thread 18 read 17 rows.
Thread 17 read 17 rows.
Thread 20 read 17 rows.
Thread 19 read 17 rows.
Thread 12 read 17 rows.
Thread 14 read 17 rows.
Thread 11 read 17 rows.
Thread 10 read 17 rows.
Thread 6 read 17 rows.
Thread 9 read 17 rows.
Thread 15 read 17 rows.
Thread 16 read 17 rows.
Thread 8 read 17 rows.
Unhandled exception. System.NullReferenceException: Object reference not set to an instance of an object.
at Microsoft.Data.Sqlite.SqliteConnection.RemoveCommand(SqliteCommand command)
at Microsoft.Data.Sqlite.SqliteCommand.Dispose(Boolean disposing)
at System.ComponentModel.Component.Dispose()
at SQLiteMultithreadingExample.SqlDatabase.QueryDatabase() in
25 replies
CC#
Created by Jasonnn on 11/12/2024 in #help
Threading and Microsoft.Data.Sqlite
for some reason (I would assume the query is too fast in my MRE, but since I'm able to reproduce the problem I have that's good enough for me)
25 replies
CC#
Created by Jasonnn on 11/12/2024 in #help
Threading and Microsoft.Data.Sqlite
It’s only using around 15 threads
25 replies
CC#
Created by Jasonnn on 11/12/2024 in #help
Threading and Microsoft.Data.Sqlite
So I'm a bit confused as to what I should be doing, what's good practice, and why I have an error in the first place
25 replies
CC#
Created by Jasonnn on 11/12/2024 in #help
Threading and Microsoft.Data.Sqlite
If I do:
var connection = new SqliteConnection("Data Source=Core.db;Mode=ReadOnly");
var connection = new SqliteConnection("Data Source=Core.db;Mode=ReadOnly");
as a local variable in public static void QueryDatabase() then I don't have any problems anymore (but then I'm opening 100 different connections!) Which is why I'm pretty much convinced the problem comes from the fact that all my threads are using the same object.
25 replies
CC#
Created by Jasonnn on 11/12/2024 in #help
Threading and Microsoft.Data.Sqlite
Here is a Minimal Reproducible Example:
using System;
using System.Data;
using System.Threading;
using System.Threading.Tasks;
using Microsoft.Data.Sqlite;

namespace SQLiteMultithreadingExample
{
static class SqlDatabase
{
private static readonly Lazy<SqliteConnection> LazyConnection = new Lazy<SqliteConnection>(
() =>
{
var connection = new SqliteConnection("Data Source=Core.db;Mode=ReadOnly");
connection.Open();
return connection;
}
);

private static SqliteConnection Connection => LazyConnection.Value;

public static void QueryDatabase()
{
using (var command = Connection.CreateCommand())
{
command.CommandText = "SELECT * FROM KITS";

using (var reader = command.ExecuteReader())
{
int rowCount = 0;

while (reader.Read())
{
rowCount++;
}

Console.WriteLine($"Row count in KITS table is {rowCount}");
}
}
}
}

class Program
{

static async Task Main(string[] args)
{
// Number of threads/tasks
int numberOfThreads = 100;
Task[] tasks = new Task[numberOfThreads];

// Start each task to open the database and query KITS table
for (int i = 0; i < numberOfThreads; i++)
{
tasks[i] = Task.Run(() => SqlDatabase.QueryDatabase());
}

// Wait for all tasks to complete
await Task.WhenAll(tasks);

Console.WriteLine("All threads have completed their work.");
}
}
}
using System;
using System.Data;
using System.Threading;
using System.Threading.Tasks;
using Microsoft.Data.Sqlite;

namespace SQLiteMultithreadingExample
{
static class SqlDatabase
{
private static readonly Lazy<SqliteConnection> LazyConnection = new Lazy<SqliteConnection>(
() =>
{
var connection = new SqliteConnection("Data Source=Core.db;Mode=ReadOnly");
connection.Open();
return connection;
}
);

private static SqliteConnection Connection => LazyConnection.Value;

public static void QueryDatabase()
{
using (var command = Connection.CreateCommand())
{
command.CommandText = "SELECT * FROM KITS";

using (var reader = command.ExecuteReader())
{
int rowCount = 0;

while (reader.Read())
{
rowCount++;
}

Console.WriteLine($"Row count in KITS table is {rowCount}");
}
}
}
}

class Program
{

static async Task Main(string[] args)
{
// Number of threads/tasks
int numberOfThreads = 100;
Task[] tasks = new Task[numberOfThreads];

// Start each task to open the database and query KITS table
for (int i = 0; i < numberOfThreads; i++)
{
tasks[i] = Task.Run(() => SqlDatabase.QueryDatabase());
}

// Wait for all tasks to complete
await Task.WhenAll(tasks);

Console.WriteLine("All threads have completed their work.");
}
}
}
25 replies
CC#
Created by Jasonnn on 9/9/2024 in #help
✅ Nullable<int> and xUnit
thanks for confirming!
9 replies
CC#
Created by Jasonnn on 9/9/2024 in #help
✅ Nullable<int> and xUnit
Ok so I definitely got scared because my IDE took time to refresh the warnings
9 replies