C ා data operation series - 18 plug-ins to make Dapper stronger

0. Preface

In the previous article, we talked about the application of Dapper, but it gives us the feeling that Dapper is not like an ORM but an extension of IDbConnection. Yes, that's right. In actual development, we often use Dapper as a supplement to EF Core. Of course, Dapper is not the only one. Let's make Dapper more like an ORM through this article.

1. Dapper Contrib

Dapper constraint extends dapper's CRUD method for entity classes:

Installation method:

Command line:

dotnet add package Dapper.Contrib


Install-Package Dapper.Contrib


using Dapper.Contrib.Extensions;

This is an extension package that makes Dapper more powerful. Because CRUD is supported, you need to add configuration to entity classes. This extension package uses Attribute as the basis for related mapping configuration:

public class Model
    public int Id{get;set;}
    public int Count {get;set;}
    public String Name{get;set;}

This is all the configurations. Table is used to declare that it is a table. The table name must be specified. Key indicates that the property is the database primary key, ExplicitKey indicates that the property is the primary key of the display setting in the database, Computed indicates that the field is a calculation field, and Write indicates that the field can be entered with the set value. It should be noted that key and ExplicitKey cannot be marked on one attribute at the same time.

Next, let's see what it extends:

Insert a single object:

public static long Insert<T>(this IDbConnection connection, T entityToInsert, IDbTransaction transaction = null, int? commandTimeout = null) where T : class;

Where transfer represents a transaction. If a transaction is specified, the submission of data will be controlled by the transaction. The method will return the primary key of the inserted object (if the primary key of the object is of numeric type) or the number of inserted rows in the list to be inserted.

Get single object:

public static T Get<T>(this IDbConnection connection, [Dynamic] dynamic id, IDbTransaction transaction = null, int? commandTimeout = null) where T : class;

Get a data by passing in the primary key

Get all data:

public static IEnumerable<T> GetAll<T>(this IDbConnection connection, IDbTransaction transaction = null, int? commandTimeout = null) where T : class;

Update data:

Dapper Contrib provides a way to update:

public static bool Update<T>(this IDbConnection connection, T entityToUpdate, IDbTransaction transaction = null, int? commandTimeout = null) where T : class;

This method is more interesting

var entity = connection.Get<Model>(1);
entity.Name = "Test 1";


var models = connection.GetAll<Model>();
foreach(var m in models)
    m.StringLength ++;

It's OK. It's not wrong.

However, it should be noted that if the instance to be updated does not specify the primary key value (the primary minus attribute is not assigned), no rows will be updated. And when updating, all columns will be updated, not because they are not assigned.

There are two ways to delete:

public static bool Delete<T>(this IDbConnection connection, T entityToDelete, IDbTransaction transaction = null, int? commandTimeout = null) where T : class;
public static bool DeleteAll<T>(this IDbConnection connection, IDbTransaction transaction = null, int? commandTimeout = null) where T : class;

Deleting is also to pass in an entity class. It just needs the primary key to have a value. If the data corresponding to the primary key is not found, there will be no change. Delete is the same as Update. If you pass in a List collection, you can.

2. Dapper Transaction

This package extends Dapper's transaction processing capabilities. Although it is an extension package of Dapper, it adds an extension method to IConnection. Examples of use are as follows:

dotnet add package Dapper.Transaction

The old rule, remember to add the bag first.

Then the code is as follows:

using Dapper.Transaction;
using(var connection = new SqliteConnection("Data Source=./demo.db"))
    var transcation = connection.BeginTransaction();
    // Write business code

If you use Dapper Transaction, you need to call connection.Open() to make sure the connection is open.

The transfer object can be used as a normal dbtransfer object, a method passed to Dapper, or as a Dapper client with transaction enabled. In other words, Dapper's method of extending IDbConnection also extends the method of responding to idbtransfer in this package:

3. Dapper Plus

This plug-in is a plug-in used to process huge amount of data on Dapper, but it's a paid plug-in, but it has a certain trial period every month. You can try the following:

dotnet add package Z.Dapper.Plus


using Z.Dapper.Plus;

Before using this plug-in, you need to configure the mapping relationship between the entity class and the database:

DapperPlusManager.Entity<Supplier>().Table("Suppliers").Identity(x => x.SupplierID);

The plug-in supports four groups of mass processing methods:

  • Bulk Insert
  • Bulk Update
  • Bulk Merge
  • Bulk Delete
DapperPlusManager.Entity<Supplier>().Table("Suppliers").Identity(x => x.SupplierID);
DapperPlusManager.Entity<Product>().Table("Products").Identity(x => x.ProductID);

using (var connection = new SqlConnection(FiddleHelper.GetConnectionStringSqlServerW3Schools()))
    connection.BulkInsert(suppliers).ThenForEach(x => x.Products.ForEach(y => y.SupplierID =  x.SupplierID)).ThenBulkInsert(x => x.Products);

using (var connection = new SqlConnection(FiddleHelper.GetConnectionStringSqlServerW3Schools()))
    connection.BulkUpdate(suppliers, x => x.Products);

using (var connection = new SqlConnection(FiddleHelper.GetConnectionStringSqlServerW3Schools()))
    connection.BulkMerge(suppliers).ThenForEach(x => x.Products.ForEach(y => y.SupplierID =  x.SupplierID)).ThenBulkMerge(x => x.Products);

using (var connection = new SqlConnection(FiddleHelper.GetConnectionStringSqlServerW3Schools()))
    connection.BulkDelete(suppliers.SelectMany(x => x.Products)).BulkDelete(suppliers);

4. Summary

These plug-ins make Dapper stronger and have a complete ORM method. Of course, the actual development needs to be combined with the actual needs. Maybe not everything is right.

That's all for Dapper. It was supposed to start the next one asp.net The content of core, but a little friend recommended FreeSql. I saw it and felt it was very good. I would like to introduce it to my little friends. After this introduction, I will enter what I have been looking forward to for a long time asp.net Core series.

Please pay attention to more My blog Mr. Gao's Cabin

Tags: C# Attribute Database

Posted on Thu, 28 May 2020 03:00:41 -0400 by techi3