ORM框架对分表分库的实现

AntData ORM框架是我维护的一个开源ORM框架

https://github.com/yuzd/AntData.ORM

该框架是在Linq2db这个优秀的linq转sql引擎基础上进行改造而来的。

分离了linq2sql引擎和db执行逻辑。

画一个图的话 应该是这样的:

分表分库功能设计

框架内置目前使用比较多的两种分片模式:

取模 (mod)

范围 (range)

为了让框架更容易扩展

开放分片策略的接口 当有自定义分片规则可以继承实现

下面我用内置的 取模 分片模式来说明 ,运行环境: netcore平台

1. DB Sharding

db配置:

Provider 指定为 mysql

Name 是逻辑名称 可以随意指定

ShardingStrategy 指定分片的逻辑处理

ConnectionItemList 指定一个或多个db链接配置

image

注意:

class=AntData.DbEngine.Sharding.ModShardingStrategy;column=ID;mod=2;shardByDB=true

的意思是:

采用内置的取模分片法,走分片的字段叫ID mod为2 也就是1分为2个 分别是 (0 和 1),所以下面的ConnectionItemList指定的 Sharding分别是0和1的数据库连接

按照上面的配置的话,当满足

表还有字段ID

db搜索的条件含有id字段,或者 db更新的条件含有id字段 或者db删除的条件含有id字段

都应该走取模算法来走对应的db。

下面来测试它

DB Sharding 使用场景举例说明 /// <summary> /// 测试mod分库插入到testorm2数据库 /// </summary> [TestMethod] public void TestMethod6_01() { //id查询 1 mod 2 = 1 所以会走到 testorm2数据库 var id = 1; var odIsExist = DB.Tables.Orders.Any(r => r.ID.Equals(1)); if (odIsExist) { return; } var order = new Order { ID = 1, Name = "上海大学" }; var result = DB.Insert(order); Assert.AreEqual(result, 1); } /// <summary> /// 测试mod分库插入到testorm1数据库 /// </summary> [TestMethod] public void TestMethod6_02() { var id = 2; var odIsExist = DB.Tables.Orders.Any(r => r.ID.Equals(2)); if (odIsExist) { return; } var order = new Order { ID = 2, Name = "北京大学" }; var result = DB.Insert(order); Assert.AreEqual(result, 1); } /// <summary> /// 测试mod分库 查询testorm2数据库 /// </summary> [TestMethod] public void TestMethod6_03() { var id = 1; var tb1 = DB.Tables.Orders.FirstOrDefault(r => r.ID.Equals(1)); Assert.IsNotNull(tb1); } /// <summary> /// 测试mod分库 查询testorm1数据库 /// </summary> [TestMethod] public void TestMethod6_04() { var id = 2; var tb1 = DB.Tables.Orders.FirstOrDefault(r => r.ID.Equals(2)); Assert.IsNotNull(tb1); } /// <summary> /// 测试mod分库 不指定sharing column 查询叠加 /// </summary> [TestMethod] public void TestMethod6_05() { var tb1 = DB.Tables.Orders.ToList(); Assert.IsNotNull(tb1); Assert.AreEqual(tb1.Count, 2); var odIsExist = DB.Tables.Orders.Where(r => r.ID.Equals(1) || r.ID.Equals(2)).ToList(); Assert.AreEqual(odIsExist.Count, 2); } /// <summary> /// 测试mod分库修改到testorm2数据库 /// </summary> [TestMethod] public void TestMethod6_06() { var id = 1; var result = DB.Tables.Orders.Where(r => r.ID.Equals(1)).Set(r => r.Name, y => y.Name + "1").Update(); Assert.AreEqual(result, 1); } /// <summary> /// 测试mod分库修改到testorm1数据库 /// </summary> [TestMethod] public void TestMethod6_07() { var id = 2; var result = DB.Tables.Orders.Where(r => r.ID.Equals(2)).Set(r => r.Name, y => y.Name + "1").Update(); Assert.AreEqual(result, 1); } /// <summary> /// 测试mod分库删除到testorm2数据库 /// </summary> [TestMethod] public void TestMethod6_08() { var id = 1; var result = DB.Tables.Orders.Where(r => r.ID.Equals(1)).Delete(); Assert.AreEqual(result, 1); } /// <summary> /// 测试mod分库删除到testorm1数据库 /// </summary> [TestMethod] public void TestMethod6_09() { var id = 2; var result = DB.Tables.Orders.Where(r => r.ID.Equals(2)).Delete(); Assert.AreEqual(result, 1); } [TestMethod] public void TestMethod7_01() { var id = 2; //var odIsExist = DB.Tables.Orders.Any(r => r.ID.Equals(id)); var odIsExist = DB.Tables.Orders.Any(r => r.ID.Equals(2)); if (odIsExist) { return; } } /// <summary> /// 测试mod分库批量分别插入到testorm1 testorm2数据库 /// </summary> [TestMethod] public void TestMethod7_02() { var orderList = new List<Order>(); orderList.Add(new Order { ID = 3, Name = "上海大学" }); orderList.Add(new Order { ID = 4, Name = "上海大学" }); //没有指定 shading column的话是默认分到第一个分片 orderList.Add(new Order { ID = null, Name = "上海大学" }); var rows = DB.BulkCopy(orderList); Assert.AreEqual(rows.RowsCopied, 3); } /// <summary> /// 不指定sharing column 删除会叠加 /// </summary> [TestMethod] public void TestMethod7_03() { var odIsExist = DB.Tables.Orders.Delete(); Assert.AreEqual(odIsExist, 3); } 2. Table Sharding

Provider 指定为 mysql

Name 是逻辑名称 可以随意指定

ShardingStrategy 指定分片的逻辑处理

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://www.heiqu.com/wpxppf.html