Fast.Framework ORM 試用

2022-09-16 18:02:22

簡介

Fast.Framework 是一款基於 .NET 6 封裝的輕量級ORM框架,支援多種資料庫(SQL Server、Oracle、MySQL、PostgreSQL、SQLite)。

優點

  1. 效能好
  2. 使用簡單

如何使用

1. 安裝

NuGet搜尋Fast.Framework並安裝最新版本

2. 建立DbContext物件

DbContext是輕量級的,可以頻繁建立,一個執行緒建立一個DbContext,不要跨執行緒使用。

private IDbContext GetDbContext()
{
    IDbContext _db = new DbContext(new List<DbOptions>() {
            new DbOptions()
            {
                DbId = "1",
                DbType = DbType.MySQL,
                ProviderName = "MySqlConnector",
                FactoryName = "MySqlConnector.MySqlConnectorFactory,MySqlConnector",
                ConnectionStrings = "Data Source=localhost;Port=3306;User ID=root;Password=123456;Initial Catalog=fast_framework_test;Charset=utf8mb4;SslMode=none;Allow User Variables=True;connection timeout=600;"
            }
        });

    if (_printSql)
    {
        _db.Aop.DbLog = (sql, dp) =>
        {
            Console.WriteLine($"執行Sql:{sql}");
            if (dp != null)
            {
                foreach (var item in dp)
                {
                    Console.WriteLine($"引數名稱:{item.ParameterName} 引數值:{item.Value}");
                }
            }
        };
    }

    return _db;
}

實體類

實體類原生支援微軟特性,相容Entity Framework。

using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;

namespace Models
{
    /// <summary>
    /// 使用者表
    /// </summary>
    [Serializable]
    [Table("sys_user")]
    public partial class SysUser
    {

        /// <summary>
        /// 主鍵
        /// </summary>
        [Key]
        [Column("id")]
        public long Id { get; set; }

        /// <summary>
        /// 使用者名稱
        /// </summary>
        [Column("user_name")]
        public string UserName { get; set; }

        /// <summary>
        /// 使用者姓名
        /// </summary>
        [Column("real_name")]
        public string RealName { get; set; }

        /// <summary>
        /// 使用者密碼
        /// </summary>
        [Column("password")]
        public string Password { get; set; }

        /// <summary>
        /// 備註
        /// </summary>
        [Column("remark")]
        public string Remark { get; set; }

        /// <summary>
        /// 建立者ID
        /// </summary>
        [Column("create_userid")]
        public string CreateUserid { get; set; }

        /// <summary>
        /// 建立時間
        /// </summary>
        [Column("create_time")]
        public DateTime CreateTime { get; set; }

        /// <summary>
        /// 更新者ID
        /// </summary>
        [Column("update_userid")]
        public string UpdateUserid { get; set; }

        /// <summary>
        /// 更新時間
        /// </summary>
        [Column("update_time")]
        public DateTime? UpdateTime { get; set; }

    }
}

.NET 6 依賴注入FastDbContext

組態檔

"DbConfig": [
  {
    "DbId": 1,
    "DbType": "MySQL",
    "IsDefault": true,
    "ProviderName": "MySqlConnector",
    "FactoryName": "MySqlConnector.MySqlConnectorFactory,MySqlConnector",
    "ConnectionStrings": "Data Source=localhost;Port=3306;User ID=root;Password=123456;Initial Catalog=fast_framework_test;Charset=utf8mb4;SslMode=none;Allow User Variables=True;connection timeout=600;"
  }
]

注入程式碼

//注入FastDbContext
builder.Services.Configure<List<DbOptions>>(builder.Configuration.GetSection("DbConfig"));
builder.Services.AddFastDbContext();

迴圈插入

await db.Ado.BeginTranAsync();
foreach (SysUser user in userList)
{
    await db.Insert(user).ExceuteAsync();
}
await db.Ado.CommitTranAsync();

批次插入

await GetDbContext().Insert(userList).ExceuteAsync();

迴圈修改

await db.Ado.BeginTranAsync();
foreach (SysUser user in userList)
{
    await db.Update(user).ExceuteAsync();
}
await db.Ado.CommitTranAsync();

批次修改

await GetDbContext().Update(userList).ExceuteAsync();

條件查詢

Pagination pagination = new Pagination();
pagination.Page = 10;
pagination.PageSize = 200;

var list = await _db.Query<SysUser>()
    .Where(t => t.Id > 20 && t.RealName.Contains("測試"))
    .OrderBy(t => t.CreateTime, "desc")
    .OrderBy(t => t.Id).ToPageListAsync(pagination);

分組聚合統計查詢

這個寫法很優雅。

var list = await db.Query<BsOrderDetail>()
    .LeftJoin<BsOrder>((d, o) => o.Id == d.OrderId)
    .GroupBy((d, o) => new { o.Id, o.OrderTime, o.Remark })
    .Having((d, o) => SqlFunc.Sum(d.Quantity * d.Price) > 1000)
    .Select((d, o) => new
    {
        o.Id,
        o.OrderTime,
        o.Remark,
        Amount = SqlFunc.Sum(d.Quantity * d.Price)
    }).ToListAsync();

效能測試

效能測試使用Winform測試
與其它ORM的對比請參考《ORM增刪改查並行效能測試2

常規測試

並行查詢

並行插入

結論

感覺還是非常快的,效能非常優異。