DbController.MySql
5.0.0
dotnet add package DbController.MySql --version 5.0.0
NuGet\Install-Package DbController.MySql -Version 5.0.0
<PackageReference Include="DbController.MySql" Version="5.0.0" />
paket add DbController.MySql --version 5.0.0
#r "nuget: DbController.MySql, 5.0.0"
// Install DbController.MySql as a Cake Addin #addin nuget:?package=DbController.MySql&version=5.0.0 // Install DbController.MySql as a Cake Tool #tool nuget:?package=DbController.MySql&version=5.0.0
DbController
An easy to use database wrapper which uses Dapper.
What does this package do?
This package has been created to minify the effort to write database queries in C#.
For example take a look on this block of code:
DataTable result = new DataTable();
MySqlConnection connection = new MySqlConnection("YOUR_CONNECTION_STRING");
connection.Open();
MySqlCommand command = connection.CreateCommand();
command.CommandText = "SELECT * FROM customers";
MySqlDataAdapter adapter = new MySqlDataAdapter(command);
adapter.Fill(result);
connection.Close();
command.Dispose();
connection.Dispose();
With this package this code can be reduced to:
using MySqlController dbController = await MySqlController.CreateAsync("YOUR_CONNECTION_STRING");
List<Customer> customer = await dbController.SelectDataAsync<Customer>("SELECT * FROM customers");
It can even be more reduced when passing the IDbController
around.
public Task<List<Customer>> GetCustomers(IDbController dbController)
{
return dbController.SelectDataAsync<Customer>("SELECT * FROM customers");
}
Once initialized, the connection to the database will be opened automatically and it will kept open until the DbController gets disposed. In addition it keeps track of the active transaction with no addition work.
Installation
We offer different packages for this library.
For MySql use:
Install-Package DbController.MySql
For SqlServer use:
Install-Package DbController.SqlServer
If you want to implement your own DbController then you should use:
Install-Package DbController
Usage
Start by creating an instance of the DbController based on the package you want to use:
When using the DbController.MySql
package a new controller can be created like this:
using MySqlController dbController = await MySqlController.CreateAsync("YOUR_CONNECTION_STRING");
For the DbController.SqlServer
package:
using SqlController dbController = await SqlController.CreateAsync("YOUR_CONNECTION_STRING");
You can also use the interface to change the used DbController at runtime with dependency injection.
using IDbController dbController = await MySqlController.CreateAsync("YOUR_CONNECTION_STRING");
DbController
is using Dapper under the hood for object mapping.
Extension to Dappers mapping
This package provides you with an attribute to map columns in the database to the corresponding property from your object. For example your customers table has a column with the name customer_id
�. Your C# class uses a slightly different name to match the C# naming conventions.
Now you can add an attribute to your property like this:
public class Customer
{
[CompareField("customer_id")]
public int CustomerId { get; set; }
}
Both packages will create a TypeAttributeCache
mapping all CustomFieldAttributes
to the corresponding properties.
This will be done in the static constructor for the IDbController implementation. If you want to add this functionality to your own implementation of IDbController you'll should add a static constructor like this:
/// <summary>
/// Static constructor to initialize the TypeAttributeCache
/// </summary>
static MySqlController()
{
// INIT Dapper for CompareField
foreach (Type type in SingletonTypeAttributeCache.CacheAll<CompareFieldAttribute>((att) => att.FieldNames))
{
SqlMapper.SetTypeMap(type, new CustomPropertyTypeMap(
type,
(type, columnName) =>
{
PropertyInfo? prop = SingletonTypeAttributeCache.Get(type, columnName);
return prop is null ? type.GetProperty(columnName, BindingFlags.IgnoreCase | BindingFlags.Public | BindingFlags.Instance) : prop;
}
));
}
}
Methods
Every IDbController provides the following methods to work with:
Method | Description | Returns |
---|---|---|
QueryAsync | Executes SQL | --- |
GetFirstAsync<T> | Executes SQL and returns maps the result to the corresponding object | Returns an instance of the object, null when no row is found |
SelectDataAsync<T> | Executes SQL and maps all results into a list | If no object is found it will return an empty list |
ExecuteReaderAsync | Executes SQL and allows to process each row individually | |
StartTransactionAsync | Starts a new transaction | Nothing will be returned |
CommitChangesAsync | Commits and writes all data from the current transaction | --- |
RollbackChangesAsync | Rolls back all changes from the current transaction | --- |
GetLastIdSql | Generates a valid SQL string to fetch the last inserted id | string |
GetPaginationSyntax | Generates a valid SQL string for pagination within SQL statements | string |
Best practices
It's generally recommended to pass an instance of IDbController to each function which needs to execute some SQL. For example:
public static async Task Main(string[] args)
{
using IDbController dbController = await MySqlController.CreateAsync("YOUR_CONNECTIONSTRING");
List<Customer> customers = await GetCustomers(dbController);
List<Employee> employees = await GetEmployees(dbController);
}
public Task<List<Customer>> GetCustomers(IDbController dbController)
{
return dbController.SelectDataAsync<Customer>("SELECT * FROM customers");
}
public Task<List<Employee>> GetEmployees(IDbController dbController)
{
return dbController.SelectDataAsync<Employee>("SELECT * FROM employees");
}
The main benefit is that every function will be able to read from the current transaction state.
Product | Versions Compatible and additional computed target framework versions. |
---|---|
.NET | net9.0 is compatible. |
-
net9.0
- DbController (>= 5.0.0)
- MySqlConnector (>= 2.4.0)
NuGet packages
This package is not used by any NuGet packages.
GitHub repositories
This package is not used by any popular GitHub repositories.
Version | Downloads | Last updated |
---|---|---|
5.0.0 | 115 | 11/14/2024 |
4.1.0 | 180 | 4/25/2024 |
4.0.0 | 130 | 4/9/2024 |
3.6.0 | 131 | 3/8/2024 |
3.5.0 | 191 | 1/11/2024 |
3.4.0 | 162 | 1/3/2024 |
3.3.0 | 180 | 12/7/2023 |
3.2.0 | 159 | 11/29/2023 |
3.1.0 | 161 | 11/8/2023 |
3.0.0 | 172 | 10/12/2023 |
2.6.0 | 163 | 9/21/2023 |
2.5.0 | 179 | 9/4/2023 |
2.4.0 | 222 | 7/3/2023 |
2.3.0 | 207 | 6/22/2023 |
2.2.0 | 207 | 5/4/2023 |
2.1.0 | 206 | 4/27/2023 |
2.0.0 | 193 | 4/26/2023 |
1.0.1 | 274 | 2/21/2023 |
1.0.0 | 269 | 2/21/2023 |