From 77d87d3be36e65a6050356eaf39b8f7198f81538 Mon Sep 17 00:00:00 2001
From: shanj <18996038927@163.com>
Date: Mon, 14 Mar 2022 04:18:03 +0800
Subject: [PATCH] =?UTF-8?q?=E6=96=B0=E5=A2=9E=E5=88=9B=E5=BB=BA=E9=87=91?=
 =?UTF-8?q?=E5=AD=97=E5=A1=94=E7=AD=96=E7=95=A5=E6=9C=BA=E5=99=A8=E4=BA=BA?=
 =?UTF-8?q?=E6=8E=A5=E5=8F=A3?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

---
 .editorconfig                                 |  3 +
 .../Binance.TradeRobot.API.xml                | 13 +++
 .../Controllers/ExchangeAccountController.cs  | 11 +++
 .../Controllers/RobotController.cs            | 29 ++++++
 Binance.TradeRobot.API/Startup.cs             |  2 -
 .../Binance.TradeRobot.Business.xml           | 36 ++++++-
 .../{ => Business}/BaseBusiness.cs            |  0
 .../ExchangeBusiness.cs                       | 32 +++++--
 .../Business/RobotBusiness.cs                 | 93 +++++++++++++++++++
 .../{User => Business}/UserBusiness.cs        |  0
 .../Extensions/RobotExtension.cs              | 24 +++++
 .../Base/MappingProfiles.cs                   |  2 +
 .../Binance.TradeRobot.Model.csproj           |  4 -
 .../Binance.TradeRobot.Model.xml              | 70 ++++++++++++++
 .../Db/Policy/UPrep/PyramidPolicy.cs          | 17 +++-
 .../Db/Robot/RobotAccount.cs                  | 46 +++++++++
 .../Robot/AddPyramidPolicyRobotRequest.cs     | 27 ++++++
 .../Dto/Request/Robot/AddRobotRequest.cs      | 17 ++++
 18 files changed, 409 insertions(+), 17 deletions(-)
 create mode 100644 Binance.TradeRobot.API/Controllers/RobotController.cs
 rename Binance.TradeRobot.Business/{ => Business}/BaseBusiness.cs (100%)
 rename Binance.TradeRobot.Business/{Exchange => Business}/ExchangeBusiness.cs (81%)
 create mode 100644 Binance.TradeRobot.Business/Business/RobotBusiness.cs
 rename Binance.TradeRobot.Business/{User => Business}/UserBusiness.cs (100%)
 create mode 100644 Binance.TradeRobot.Business/Extensions/RobotExtension.cs
 create mode 100644 Binance.TradeRobot.Model/Db/Robot/RobotAccount.cs
 create mode 100644 Binance.TradeRobot.Model/Dto/Request/Robot/AddPyramidPolicyRobotRequest.cs
 create mode 100644 Binance.TradeRobot.Model/Dto/Request/Robot/AddRobotRequest.cs

diff --git a/.editorconfig b/.editorconfig
index 0db2396..cd7ccf1 100644
--- a/.editorconfig
+++ b/.editorconfig
@@ -5,3 +5,6 @@ dotnet_diagnostic.CS8618.severity = none
 
 # CS1591: 缺少对公共可见类型或成员的 XML 注释
 dotnet_diagnostic.CS1591.severity = none
+
+# CS8625: 无法将 null 字面量转换为非 null 的引用类型。
+dotnet_diagnostic.CS8625.severity = none
diff --git a/Binance.TradeRobot.API/Binance.TradeRobot.API.xml b/Binance.TradeRobot.API/Binance.TradeRobot.API.xml
index ecc2412..a4bb4d5 100644
--- a/Binance.TradeRobot.API/Binance.TradeRobot.API.xml
+++ b/Binance.TradeRobot.API/Binance.TradeRobot.API.xml
@@ -23,6 +23,19 @@
             <param name="tradePolicy">交易策略</param>
             <returns></returns>
         </member>
+        <member name="M:Binance.TradeRobot.API.Controllers.ExchangeAccountController.GetNoUsedExchangeAccountList(Binance.TradeRobot.Model.Base.Enums.TradePolicy)">
+            <summary>
+            获取APIKey未使用的交易所账户列表
+            </summary>
+            <param name="tradePolicy"></param>
+            <returns></returns>
+        </member>
+        <member name="M:Binance.TradeRobot.API.Controllers.RobotController.AddPyramidPolicyRobot(Binance.TradeRobot.Model.Dto.AddPyramidPolicyRobotRequest)">
+            <summary>
+            创建金字塔策略合约机器人
+            </summary>
+            <param name="addPyramidPolicyRobotRequest"></param>
+        </member>
         <member name="M:Binance.TradeRobot.API.Controllers.UserController.Login(Binance.TradeRobot.Model.Dto.LoginRequest)">
             <summary>
             用户登录
diff --git a/Binance.TradeRobot.API/Controllers/ExchangeAccountController.cs b/Binance.TradeRobot.API/Controllers/ExchangeAccountController.cs
index da80604..eb88f78 100644
--- a/Binance.TradeRobot.API/Controllers/ExchangeAccountController.cs
+++ b/Binance.TradeRobot.API/Controllers/ExchangeAccountController.cs
@@ -48,5 +48,16 @@ namespace Binance.TradeRobot.API.Controllers
         {
             return exchangeBusiness.GetExchangeAccountList(tradePolicy);
         }
+
+        /// <summary>
+        /// 获取APIKey未使用的交易所账户列表
+        /// </summary>
+        /// <param name="tradePolicy"></param>
+        /// <returns></returns>
+        [HttpGet("{tradePolicy}")]
+        public IList<ExchangeAccountResponse> GetNoUsedExchangeAccountList([FromRoute]Enums.TradePolicy tradePolicy)
+        {
+            return exchangeBusiness.GetNoUsedExchangeAccountList(tradePolicy);
+        }
     }
 }
diff --git a/Binance.TradeRobot.API/Controllers/RobotController.cs b/Binance.TradeRobot.API/Controllers/RobotController.cs
new file mode 100644
index 0000000..7e51e55
--- /dev/null
+++ b/Binance.TradeRobot.API/Controllers/RobotController.cs
@@ -0,0 +1,29 @@
+using Binance.TradeRobot.Business;
+using Binance.TradeRobot.Model.Dto;
+using Microsoft.AspNetCore.Authentication.JwtBearer;
+using Microsoft.AspNetCore.Authorization;
+using Microsoft.AspNetCore.Mvc;
+
+namespace Binance.TradeRobot.API.Controllers
+{
+    [Authorize(AuthenticationSchemes = JwtBearerDefaults.AuthenticationScheme)]
+    public class RobotController : BaseApiController
+    {
+        private RobotBusiness robotBusiness;
+
+        public RobotController(RobotBusiness robotBusiness)
+        {
+            this.robotBusiness = robotBusiness;
+        }
+
+        /// <summary>
+        /// 创建金字塔策略合约机器人
+        /// </summary>
+        /// <param name="addPyramidPolicyRobotRequest"></param>
+        [HttpPost]
+        public void AddPyramidPolicyRobot([FromBody] AddPyramidPolicyRobotRequest addPyramidPolicyRobotRequest)
+        {
+            robotBusiness.AddPyramidPolicyRobot(addPyramidPolicyRobotRequest);
+        }
+    }
+}
diff --git a/Binance.TradeRobot.API/Startup.cs b/Binance.TradeRobot.API/Startup.cs
index 0b2fc3d..ccd5fc5 100644
--- a/Binance.TradeRobot.API/Startup.cs
+++ b/Binance.TradeRobot.API/Startup.cs
@@ -4,13 +4,11 @@ using Binance.TradeRobot.Business;
 using Binance.TradeRobot.Common.Extensions;
 using Binance.TradeRobot.Common.Http;
 using Binance.TradeRobot.Model.Base;
-using HY.TradingRobot.Model.Base;
 using Microsoft.AspNetCore.Authentication.JwtBearer;
 using Microsoft.AspNetCore.Builder;
 using Microsoft.AspNetCore.Hosting;
 using Microsoft.Extensions.Configuration;
 using Microsoft.Extensions.DependencyInjection;
-using Microsoft.Extensions.Hosting;
 using Microsoft.IdentityModel.Tokens;
 using Newtonsoft.Json;
 using Newtonsoft.Json.Serialization;
diff --git a/Binance.TradeRobot.Business/Binance.TradeRobot.Business.xml b/Binance.TradeRobot.Business/Binance.TradeRobot.Business.xml
index a3d173f..0d455e1 100644
--- a/Binance.TradeRobot.Business/Binance.TradeRobot.Business.xml
+++ b/Binance.TradeRobot.Business/Binance.TradeRobot.Business.xml
@@ -4,12 +4,26 @@
         <name>Binance.TradeRobot.Business</name>
     </assembly>
     <members>
-        <member name="M:Binance.TradeRobot.Business.Extensions.UserExtension.CalculateRatio(System.Collections.Generic.IList{Binance.TradeRobot.Model.Dto.UserResponse},System.Boolean)">
+        <member name="M:Binance.TradeRobot.Business.Exchange.ExchangeBusiness.GetNoUsedExchangeAccountList(Binance.TradeRobot.Model.Base.Enums.TradePolicy)">
             <summary>
-            计算成员分红/本金比例
+            获取APIKey未使用交易所账户列表
             </summary>
-            <param name="userList"></param>
-            <param name="multiplyBy100">比例乘100</param>
+            <param name="tradePolicy"></param>
+            <returns></returns>
+        </member>
+        <member name="M:Binance.TradeRobot.Business.RobotBusiness.CheckRobotRegister(Binance.TradeRobot.Model.Dto.AddRobotRequest,Binance.TradeRobot.Model.Db.ExchangeAPIKey@)">
+            <summary>
+            检查机器人注册条件
+            </summary>
+            <param name="addRobotRequest"></param>
+            <param name="exchangeAPIKey"></param>
+            <exception cref="T:Binance.TradeRobot.Model.Base.BusinessException"></exception>
+        </member>
+        <member name="M:Binance.TradeRobot.Business.RobotBusiness.AddPyramidPolicyRobot(Binance.TradeRobot.Model.Dto.AddPyramidPolicyRobotRequest)">
+            <summary>
+            添加金字塔策略机器人
+            </summary>
+            <param name="addPyramidPolicyRobotRequest"></param>
         </member>
         <member name="M:Binance.TradeRobot.Business.UserBusiness.OneWayAssetChange(System.Int64,System.Decimal,System.Int64,Binance.TradeRobot.Model.Base.Enums.CapitalChangeType,System.String)">
             <summary>
@@ -22,5 +36,19 @@
             <param name="remark"></param>
             <exception cref="T:Binance.TradeRobot.Model.Base.BusinessException"></exception>
         </member>
+        <member name="M:Binance.TradeRobot.Business.Extensions.RobotExtension.GetBusinessType(Binance.TradeRobot.Model.Base.Enums.TradePolicy)">
+            <summary>
+            获取交易策略对应的业务类型
+            </summary>
+            <param name="tradePolicy"></param>
+            <returns></returns>
+        </member>
+        <member name="M:Binance.TradeRobot.Business.Extensions.UserExtension.CalculateRatio(System.Collections.Generic.IList{Binance.TradeRobot.Model.Dto.UserResponse},System.Boolean)">
+            <summary>
+            计算成员分红/本金比例
+            </summary>
+            <param name="userList"></param>
+            <param name="multiplyBy100">比例乘100</param>
+        </member>
     </members>
 </doc>
diff --git a/Binance.TradeRobot.Business/BaseBusiness.cs b/Binance.TradeRobot.Business/Business/BaseBusiness.cs
similarity index 100%
rename from Binance.TradeRobot.Business/BaseBusiness.cs
rename to Binance.TradeRobot.Business/Business/BaseBusiness.cs
diff --git a/Binance.TradeRobot.Business/Exchange/ExchangeBusiness.cs b/Binance.TradeRobot.Business/Business/ExchangeBusiness.cs
similarity index 81%
rename from Binance.TradeRobot.Business/Exchange/ExchangeBusiness.cs
rename to Binance.TradeRobot.Business/Business/ExchangeBusiness.cs
index 3e19a6d..ca0b772 100644
--- a/Binance.TradeRobot.Business/Exchange/ExchangeBusiness.cs
+++ b/Binance.TradeRobot.Business/Business/ExchangeBusiness.cs
@@ -1,4 +1,5 @@
-using Binance.TradeRobot.Common.DI;
+using Binance.TradeRobot.Business.Extensions;
+using Binance.TradeRobot.Common.DI;
 using Binance.TradeRobot.Common.Extensions;
 using Binance.TradeRobot.Model.Base;
 using Binance.TradeRobot.Model.Db;
@@ -32,11 +33,7 @@ namespace Binance.TradeRobot.Business.Exchange
                 throw new BusinessException("重复的APIKey或SecretKey");
 
             var exchangeAccount = addExchangeAccountRequest.Map<ExchangeAccount>();
-            if (addExchangeAccountRequest.TradePolicy == Enums.TradePolicy.金字塔)
-                exchangeAccount.BusinessType = Enums.BusinessType.UPrep;
-
-            if (addExchangeAccountRequest.TradePolicy == Enums.TradePolicy.动量趋势v2)
-                exchangeAccount.BusinessType = Enums.BusinessType.Spot_Margin;
+            exchangeAccount.BusinessType = addExchangeAccountRequest.TradePolicy.GetBusinessType();
 
             var exchangeAPIKey = new ExchangeAPIKey()
             {
@@ -133,5 +130,28 @@ namespace Binance.TradeRobot.Business.Exchange
                 ewh.Set();
             }
         }
+
+        /// <summary>
+        /// 获取APIKey未使用交易所账户列表
+        /// </summary>
+        /// <param name="tradePolicy"></param>
+        /// <returns></returns>
+        public IList<ExchangeAccountResponse> GetNoUsedExchangeAccountList(Enums.TradePolicy tradePolicy)
+        {
+            var exchangeAccountList = fsql.Select<ExchangeAccount>().Where(ea => ea.TradePolicy == tradePolicy).ToList().Map<IList<ExchangeAccountResponse>>();
+            var accountIdList = exchangeAccountList.Select(ea => ea.Id);
+            var exchangeAPIKeyList = fsql.Select<ExchangeAPIKey>().Where(k => k.RobotId == null && accountIdList.Contains(k.AccountId))
+                                                                  .ToList()
+                                                                  .Map<IList<ExchangeAPIKeyResponse>>();
+
+            foreach (var exchangeAccount in exchangeAccountList)
+            {
+                var currentExchangeAccountAPIKeyList = exchangeAPIKeyList.Where(k => k.AccountId == exchangeAccount.Id);
+                if (currentExchangeAccountAPIKeyList.Count() == 0)
+                    continue;
+                exchangeAccount.ExchangeAPIKeyList.AddRange(currentExchangeAccountAPIKeyList);
+            }
+            return exchangeAccountList;
+        }
     }
 }
diff --git a/Binance.TradeRobot.Business/Business/RobotBusiness.cs b/Binance.TradeRobot.Business/Business/RobotBusiness.cs
new file mode 100644
index 0000000..6f798b1
--- /dev/null
+++ b/Binance.TradeRobot.Business/Business/RobotBusiness.cs
@@ -0,0 +1,93 @@
+using Binance.TradeRobot.Business.Extensions;
+using Binance.TradeRobot.Common.DI;
+using Binance.TradeRobot.Common.Extensions;
+using Binance.TradeRobot.Model.Base;
+using Binance.TradeRobot.Model.Db;
+using Binance.TradeRobot.Model.Dto;
+using Microsoft.Extensions.Caching.Memory;
+using Microsoft.Extensions.DependencyInjection;
+using System.Data.Common;
+using Yitter.IdGenerator;
+
+namespace Binance.TradeRobot.Business
+{
+    [BatchRegistration(ServiceLifetime.Singleton, RegistrationType.Self)]
+    public class RobotBusiness : BaseBusiness
+    {
+        public RobotBusiness(IFreeSql fsql, NLogManager logManager, IIdGenerator idGenerator, IMemoryCache memoryCache) : base(fsql, logManager, idGenerator, memoryCache)
+        {
+
+        }
+
+        /// <summary>
+        /// 检查机器人注册条件
+        /// </summary>
+        /// <param name="addRobotRequest"></param>
+        /// <param name="exchangeAPIKey"></param>
+        /// <exception cref="BusinessException"></exception>
+        private void CheckRobotRegister(AddRobotRequest addRobotRequest, out ExchangeAPIKey exchangeAPIKey)
+        {
+            exchangeAPIKey = null;
+            if (string.IsNullOrEmpty(addRobotRequest.Symbol) || addRobotRequest.ExchangeAPIKeyId == 0)
+                throw new BusinessException("参数不全");
+            exchangeAPIKey = fsql.Select<ExchangeAPIKey>(addRobotRequest.ExchangeAPIKeyId).ToOne();
+            if (exchangeAPIKey == null)
+                throw new BusinessException("选择的APIKey不存在");
+            if (exchangeAPIKey.RobotId != null)
+                throw new BusinessException("APIKey已被其他机器人使用");
+
+            var accountId = exchangeAPIKey.AccountId;
+            if (fsql.Select<ExchangeAccount, ExchangeAPIKey, Robot>().InnerJoin((ea, ek, r) => ea.Id == ek.AccountId)
+                                                                     .LeftJoin((ea, ek, r) => ek.RobotId == r.Id)
+                                                                     .Where((ea, ek, r) => ea.Id == accountId &&
+                                                                                           r.Symbol == addRobotRequest.Symbol).Any())
+                throw new BusinessException("同一个交易所账号下只允许存在一个交易对");
+        }
+
+        private Robot CreateRobot(AddRobotRequest addRobotRequest)
+        {
+            return new Robot()
+            {
+                Id = idGenerator.NewLong(),
+                Symbol = addRobotRequest.Symbol,
+                TradePolicy = addRobotRequest.TradePolicy,
+                BusinessType = addRobotRequest.TradePolicy.GetBusinessType()
+            };
+        }
+
+        private RobotAccount CreateRobotAccount(long robotId)
+        {
+            return new RobotAccount() { Id = idGenerator.NewLong(), RobotId = robotId };
+        }
+
+        private void ExecuteAddRobotWithTran(Robot robot, RobotAccount robotAccount, long exchangeAPIKeyId, DbTransaction tran)
+        {
+            fsql.Insert(robot).WithTransaction(tran).ExecuteAffrows();
+            fsql.Insert(robotAccount).WithTransaction(tran).ExecuteAffrows();
+            fsql.Update<ExchangeAPIKey>(exchangeAPIKeyId).WithTransaction(tran).Set(ek => ek.RobotId, robot.Id).ExecuteAffrows();
+        }
+
+        /// <summary>
+        /// 添加金字塔策略机器人
+        /// </summary>
+        /// <param name="addPyramidPolicyRobotRequest"></param>
+        public void AddPyramidPolicyRobot(AddPyramidPolicyRobotRequest addPyramidPolicyRobotRequest)
+        {
+            CheckRobotRegister(addPyramidPolicyRobotRequest, out ExchangeAPIKey exchangeAPIKey);
+            var robot = CreateRobot(addPyramidPolicyRobotRequest);
+            var robotAccount = CreateRobotAccount(robot.Id);
+            var pyramidPolicy = addPyramidPolicyRobotRequest.Map<PyramidPolicy>();
+            pyramidPolicy.Id = idGenerator.NewLong();
+            pyramidPolicy.RobotId = robot.Id;
+            fsql.Transaction(() =>
+            {
+                var tran = fsql.Ado.TransactionCurrentThread;
+                ExecuteAddRobotWithTran(robot, robotAccount, addPyramidPolicyRobotRequest.ExchangeAPIKeyId, tran);
+                fsql.Insert(pyramidPolicy).ExecuteAffrows();
+            });
+
+            //调整仓位杠杆倍数
+
+        }
+    }
+}
diff --git a/Binance.TradeRobot.Business/User/UserBusiness.cs b/Binance.TradeRobot.Business/Business/UserBusiness.cs
similarity index 100%
rename from Binance.TradeRobot.Business/User/UserBusiness.cs
rename to Binance.TradeRobot.Business/Business/UserBusiness.cs
diff --git a/Binance.TradeRobot.Business/Extensions/RobotExtension.cs b/Binance.TradeRobot.Business/Extensions/RobotExtension.cs
new file mode 100644
index 0000000..af53670
--- /dev/null
+++ b/Binance.TradeRobot.Business/Extensions/RobotExtension.cs
@@ -0,0 +1,24 @@
+using Binance.TradeRobot.Model.Base;
+using System.Collections.Generic;
+
+namespace Binance.TradeRobot.Business.Extensions
+{
+    public static class RobotExtension
+    {
+        private static IDictionary<Enums.TradePolicy, Enums.BusinessType> BusinessTypeDic = new Dictionary<Enums.TradePolicy, Enums.BusinessType>()
+        {
+            {Enums.TradePolicy.金字塔, Enums.BusinessType.UPrep },
+            { Enums.TradePolicy.动量趋势v2, Enums.BusinessType.Spot_Margin}
+        };
+
+        /// <summary>
+        /// 获取交易策略对应的业务类型
+        /// </summary>
+        /// <param name="tradePolicy"></param>
+        /// <returns></returns>
+        public static Enums.BusinessType GetBusinessType(this Enums.TradePolicy tradePolicy)
+        {
+            return BusinessTypeDic[tradePolicy];
+        }
+    }
+}
diff --git a/Binance.TradeRobot.Model/Base/MappingProfiles.cs b/Binance.TradeRobot.Model/Base/MappingProfiles.cs
index 2027e10..b5ea5f2 100644
--- a/Binance.TradeRobot.Model/Base/MappingProfiles.cs
+++ b/Binance.TradeRobot.Model/Base/MappingProfiles.cs
@@ -15,6 +15,8 @@ namespace Binance.TradeRobot.Model.Base
             CreateMap<AddExchangeAPIKeyRequest, ExchangeAPIKey>();
             CreateMap<ExchangeAPIKey, ExchangeAPIKeyResponse>();
             CreateMap<ExchangeAccount, ExchangeAccountResponse>();
+
+            CreateMap<AddPyramidPolicyRobotRequest, PyramidPolicy>();
         }
     }
 }
diff --git a/Binance.TradeRobot.Model/Binance.TradeRobot.Model.csproj b/Binance.TradeRobot.Model/Binance.TradeRobot.Model.csproj
index 8c08b5a..78b48d1 100644
--- a/Binance.TradeRobot.Model/Binance.TradeRobot.Model.csproj
+++ b/Binance.TradeRobot.Model/Binance.TradeRobot.Model.csproj
@@ -12,8 +12,4 @@
     <PackageReference Include="FreeSql" Version="3.0.100" />
   </ItemGroup>
 
-  <ItemGroup>
-    <Folder Include="Dto\Request\Robot\" />
-  </ItemGroup>
-
 </Project>
diff --git a/Binance.TradeRobot.Model/Binance.TradeRobot.Model.xml b/Binance.TradeRobot.Model/Binance.TradeRobot.Model.xml
index b25f981..4ce0f16 100644
--- a/Binance.TradeRobot.Model/Binance.TradeRobot.Model.xml
+++ b/Binance.TradeRobot.Model/Binance.TradeRobot.Model.xml
@@ -94,11 +94,51 @@
              交易所账号Id
             </summary>
         </member>
+        <member name="P:Binance.TradeRobot.Model.Db.PyramidPolicy.Leverage">
+            <summary>
+            杠杆倍数(1-125整数)
+            </summary>
+        </member>
+        <member name="P:Binance.TradeRobot.Model.Db.PyramidPolicy.Position">
+            <summary>
+            仓位
+            </summary>
+        </member>
+        <member name="P:Binance.TradeRobot.Model.Db.PyramidPolicy.Pyramid">
+            <summary>
+            金字塔
+            </summary>
+        </member>
         <member name="P:Binance.TradeRobot.Model.Db.Robot.RunningTime">
             <summary>
             运行时长(s)
             </summary>
         </member>
+        <member name="P:Binance.TradeRobot.Model.Db.RobotAccount.ClosePositionCount">
+            <summary>
+            平仓次数
+            </summary>
+        </member>
+        <member name="P:Binance.TradeRobot.Model.Db.RobotAccount.SoptCurrentcyAmount">
+            <summary>
+            现货/杠杆持仓金额
+            </summary>
+        </member>
+        <member name="P:Binance.TradeRobot.Model.Db.RobotAccount.SpotCurrencyQuantity">
+            <summary>
+            现货/杠杆持仓数量
+            </summary>
+        </member>
+        <member name="P:Binance.TradeRobot.Model.Db.RobotAccount.TotalProfit">
+            <summary>
+            总收益
+            </summary>
+        </member>
+        <member name="P:Binance.TradeRobot.Model.Db.RobotAccount.WinCount">
+            <summary>
+            盈利次数
+            </summary>
+        </member>
         <member name="P:Binance.TradeRobot.Model.Db.User.CostAmount">
             <summary>
             投资本金
@@ -164,6 +204,36 @@
             交易策略
             </summary>
         </member>
+        <member name="P:Binance.TradeRobot.Model.Dto.AddPyramidPolicyRobotRequest.SignalPeriod">
+            <summary>
+            信号周期
+            </summary>
+        </member>
+        <member name="P:Binance.TradeRobot.Model.Dto.AddPyramidPolicyRobotRequest.Leverage">
+            <summary>
+            杠杆倍数
+            </summary>
+        </member>
+        <member name="P:Binance.TradeRobot.Model.Dto.AddPyramidPolicyRobotRequest.Position">
+            <summary>
+            仓位
+            </summary>
+        </member>
+        <member name="P:Binance.TradeRobot.Model.Dto.AddPyramidPolicyRobotRequest.Pyramid">
+            <summary>
+            金字塔
+            </summary>
+        </member>
+        <member name="P:Binance.TradeRobot.Model.Dto.AddRobotRequest.Symbol">
+            <summary>
+            交易对
+            </summary>
+        </member>
+        <member name="P:Binance.TradeRobot.Model.Dto.AddRobotRequest.ExchangeAPIKeyId">
+            <summary>
+            交易所APIKeyId
+            </summary>
+        </member>
         <member name="P:Binance.TradeRobot.Model.Dto.LoginRequest.Pwd">
             <summary>
             密码需要Md5小写加密
diff --git a/Binance.TradeRobot.Model/Db/Policy/UPrep/PyramidPolicy.cs b/Binance.TradeRobot.Model/Db/Policy/UPrep/PyramidPolicy.cs
index 090169f..0a0603a 100644
--- a/Binance.TradeRobot.Model/Db/Policy/UPrep/PyramidPolicy.cs
+++ b/Binance.TradeRobot.Model/Db/Policy/UPrep/PyramidPolicy.cs
@@ -6,7 +6,6 @@ namespace Binance.TradeRobot.Model.Db
     [Table(DisableSyncStructure = true)]
     public partial class PyramidPolicy
     {
-
         [Column(IsPrimary = true)]
         public long Id { get; set; }
 
@@ -14,6 +13,22 @@ namespace Binance.TradeRobot.Model.Db
         public Enums.SignalPeriod SignalPeriod { get; set; }
 
         public long RobotId { get; set; }
+
+        /// <summary>
+        /// �ܸ˱���(1-125����)
+        /// </summary>
+        public int Leverage { get; set; } = 1;
+
+        /// <summary>
+        /// ��λ
+        /// </summary>
+        [Column(DbType = "decimal(18,8)")]
+        public decimal Position { get; set; } = 0M;
+
+        /// <summary>
+        /// ������
+        /// </summary>
+        public int Pyramid { get; set; } = 0;
     }
 
 }
diff --git a/Binance.TradeRobot.Model/Db/Robot/RobotAccount.cs b/Binance.TradeRobot.Model/Db/Robot/RobotAccount.cs
new file mode 100644
index 0000000..838922f
--- /dev/null
+++ b/Binance.TradeRobot.Model/Db/Robot/RobotAccount.cs
@@ -0,0 +1,46 @@
+using FreeSql.DataAnnotations;
+
+namespace Binance.TradeRobot.Model.Db
+{
+
+    [Table(DisableSyncStructure = true)]
+    public partial class RobotAccount
+    {
+
+        [Column(IsPrimary = true)]
+        public long Id { get; set; }
+
+        /// <summary>
+        /// 平仓次数
+        /// </summary>
+        public long ClosePositionCount { get; set; } = 0;
+
+
+        public long RobotId { get; set; }
+
+        /// <summary>
+        /// 现货/杠杆持仓金额
+        /// </summary>
+        [Column(DbType = "decimal(18,8)")]
+        public decimal SoptCurrentcyAmount { get; set; } = 0.0M;
+
+        /// <summary>
+        /// 现货/杠杆持仓数量
+        /// </summary>
+        [Column(DbType = "decimal(18,8)")]
+        public decimal SpotCurrencyQuantity { get; set; } = 0.0M;
+
+        /// <summary>
+        /// 总收益
+        /// </summary>
+        [Column(DbType = "decimal(18,8)")]
+        public decimal TotalProfit { get; set; } = 0.0M;
+
+        /// <summary>
+        /// 盈利次数
+        /// </summary>
+        public long WinCount { get; set; } = 0;
+
+    }
+
+}
diff --git a/Binance.TradeRobot.Model/Dto/Request/Robot/AddPyramidPolicyRobotRequest.cs b/Binance.TradeRobot.Model/Dto/Request/Robot/AddPyramidPolicyRobotRequest.cs
new file mode 100644
index 0000000..ae46774
--- /dev/null
+++ b/Binance.TradeRobot.Model/Dto/Request/Robot/AddPyramidPolicyRobotRequest.cs
@@ -0,0 +1,27 @@
+using Binance.TradeRobot.Model.Base;
+
+namespace Binance.TradeRobot.Model.Dto
+{
+    public class AddPyramidPolicyRobotRequest : AddRobotRequest
+    {
+        /// <summary>
+        /// 信号周期
+        /// </summary>
+        public Enums.SignalPeriod SignalPeriod { get; set; }
+
+        /// <summary>
+        /// 杠杆倍数
+        /// </summary>
+        public int Leverage { get; set; }
+
+        /// <summary>
+        /// 仓位
+        /// </summary>
+        public decimal Position { get; set; }
+
+        /// <summary>
+        /// 金字塔
+        /// </summary>
+        public int Pyramid { get; set; }
+    }
+}
diff --git a/Binance.TradeRobot.Model/Dto/Request/Robot/AddRobotRequest.cs b/Binance.TradeRobot.Model/Dto/Request/Robot/AddRobotRequest.cs
new file mode 100644
index 0000000..e1f86fe
--- /dev/null
+++ b/Binance.TradeRobot.Model/Dto/Request/Robot/AddRobotRequest.cs
@@ -0,0 +1,17 @@
+using Binance.TradeRobot.Model.Base;
+
+namespace Binance.TradeRobot.Model.Dto
+{
+    public class AddRobotRequest
+    {
+        /// <summary>
+        /// 交易对
+        /// </summary>
+        public string Symbol { get; set; }
+        public Enums.TradePolicy TradePolicy { get; set; }
+        /// <summary>
+        /// 交易所APIKeyId
+        /// </summary>
+        public long ExchangeAPIKeyId { get; set; }
+    }
+}