Parcourir la source

增肌数据回传管理功能

dodo hold il y a 1 an
Parent
commit
8952c818c2

+ 10 - 7
molilian.api/Controllers/admin/AliyunController.cs

@@ -56,8 +56,14 @@ namespace molilian.api.Controllers
                .Where(filter, new { keyword })
                .Page(size, page)
                .Order(orderBy)
-               .PageList<dynamic>(getTotal);
+               .PageList<AliyunPoolDTO>(getTotal);
 
+            foreach (var item in result.List)
+            {
+                item.ecs_list = AliyunPoolCore.EcsList(item);
+                item.accessKeyId = string.Empty;
+                item.accessKeySecret = string.Empty;
+            }
             return new APIResult(new { data = result });
         }
 
@@ -95,7 +101,7 @@ namespace molilian.api.Controllers
                     decimal amout = 0;
                     try
                     {
-                        AliyunCore core = new AliyunCore(item.id);
+                        AliyunCore core = new AliyunCore(item);
                         var response = core.QueryAccountBalance();
                         var balance = response.Body.Data.AvailableAmount;
                         if (decimal.TryParse(balance, out amout))
@@ -194,16 +200,13 @@ namespace molilian.api.Controllers
             }
 
             using var conn = CenterHub.GetOpenConnection();
-            var result = new DBContext.Table(conn, "center_daily_logs")
+            var result = new DBContext.Table(conn, "aliyun_ecs")
                 .Where(filter, new { channel, accountName, stime, etime })
                 .Page(size, page)
                 .Order(orderBy)
-                .PageList<DailyLogsDTO>(getTotal);
+                .PageList<AliyunEcsDTO>(getTotal);
 
 
-            var accounts = await JdPoolCore.ListAsync();
-            var hide_ids = accounts.Where(e => e.is_hide).Select(e => e.id).ToList();
-            result.List = result.List.Where(e => e.channel != 1 || !hide_ids.Contains(e.accountId));
             return new APIResult(new { data = result });
         }
 

+ 274 - 0
molilian.api/Controllers/admin/DataReportController.cs

@@ -0,0 +1,274 @@
+using molilian.core;
+using dodohold.core;
+using Microsoft.AspNetCore.Mvc;
+using System.Text.Json;
+using static molilian.core.ChartDataCore;
+using TencentCloud.Soe.V20180724.Models;
+using TencentCloud.Mrs.V20200910.Models;
+using System.Xml.Linq;
+using System.Security.Cryptography;
+using TencentCloud.Bi.V20220105.Models;
+using static Microsoft.Extensions.Logging.EventSource.LoggingEventSource;
+using molilian.core.PushDataReport;
+using System.Threading;
+using OfficeOpenXml.DataValidation.Exceptions;
+namespace molilian.api.Controllers
+{
+    [ApiController]
+    [MyAuthorize("admin")]
+    [Route("api/[controller]/[action]")]
+    public class DataReportController : ControllerBase
+    {
+        readonly IAuthorizationProvider provider = new AdminProvider();
+        protected IHttpContextAccessor _accessor;
+        public DataReportController(IHttpContextAccessor accessor)
+        {
+            _accessor = accessor;
+        }
+
+        [HttpPost]
+        public ActionResult list([FromBody] JsonElement form)
+        {
+            var token = provider.Get(_accessor.HttpContext);
+
+            int page = form.Read("current", 1);
+            int size = form.Read("pageSize", 10);
+            bool getTotal = form.Read("getTotal", true);
+
+            string sort = form.Read<string>("sort");
+            string order = form.Read<string>("order");
+
+            //string filter = string.Empty;
+
+            // 临时锁定所有口令推送数据
+            string filter = "type<>1";
+
+            int type = form.Read("type", 0);
+            if (type > 0) filter += $" AND type = @type";
+
+
+            int status = form.Read("status", -1);
+            if (status != -1) filter += $" AND status = @status";
+
+            int is_settlement = form.Read("is_settlement", -1);
+            if (is_settlement != -1) filter += $" AND is_settlement = @is_settlement";
+
+
+            int platform = form.Read("platform", 0);
+            if (platform > 0) filter += $" AND platform = @platform";
+
+            var report_date = form.Read<DateTime>("report_date", DateTime.MinValue);
+            if (report_date != DateTime.MinValue) filter += $" AND report_date = @report_date";
+
+
+            filter = filter.StringTrimStart(" AND ");
+
+            string orderBy = "id DESC";
+            if (!string.IsNullOrEmpty(order))
+            {
+                order = "descending".Equals(order) ? "DESC" : "ASC";
+                orderBy = sort switch
+                {
+                    _ => $"{sort} {order}",
+                };
+            }
+
+            var result = new DBContext.Table("push_data_report")
+               .Where(filter, new { type, report_date, is_settlement, status, platform })
+               .Page(size, page)
+               .Order(orderBy)
+               .PageList<dynamic>(getTotal);
+
+            return new APIResult(new { data = result });
+        }
+
+
+
+        [HttpPost]
+        public async Task<ActionResult> push([FromBody] JsonElement form)
+        {
+            int id = form.Read<int>("id");
+
+            using var conn = DBContext.GetOpenConnection();
+            var item = new DBContext.Table(conn, "push_data_report").Get<PushDataReportDTO>("id=@id", new { id });
+            if (item == null) return new APIResult(new { data = new { success = false, msg = "PUSH失败,记录不存在" } });
+
+            // 临时锁定所有口令推送数据
+            if (item.type == 1) return new APIResult(new { data = new { success = false, msg = "PUSH失败,类型错误" } });
+
+            PushDataReportPush plus = new PushDataReportPush();
+
+            item.request_id = Guid.NewGuid().ToString();
+            var response = await plus.PushReportData(item);
+
+            bool success = response.code == 200;
+            if (!success)
+            {
+                item.request_id = $"{item.request_id}:{response.message}";
+            }
+
+            new DBContext.Table("push_data_report")
+                        .Add("status", success)
+                        .Add("request_id", item.request_id)
+                        .Add("update_time", DateTime.Now)
+                        .Add("last_push_time", DateTime.Now)
+                        .Where("id=@id", new { id })
+                        .Update();
+
+            return new APIResult(new
+            {
+                data = new { success, msg = success ? "Push成功" : "Push失败" },
+            });
+        }
+
+
+        [HttpPost]
+        public async Task<ActionResult> save([FromBody] JsonElement from)
+        {
+            var clientIp = _accessor.HttpContext.GetUserIp();
+            var token = provider.Get(_accessor.HttpContext);
+
+            using var conn = DBContext.GetOpenConnection();
+            int result = 0;
+            bool success = false;
+
+            try
+            {
+                int id = from.Read("id", 0);
+                var report_date = from.Read<DateTime>("report_date", DateTime.Now).Date;
+                var platform = from.Read<int>("platform", 0);
+                var type = from.Read<int>("type", 0);
+
+                // 临时锁定所有口令推送数据
+                if (type == 1) return new APIResult(new { data = new { success = false, msg = "更新失败,类型错误" } });
+
+
+                var update = new DBContext.Table("push_data_report");
+
+                //PushDataReportCore core = new();
+                //await core.FillCpsCouponData(report_date);
+
+                //return new APIResult(new
+                //{
+                //    data = new { success = false, msg = $"更新失败,test" },
+                //});
+
+                update.Fill(from);
+                update.Add("report_date", report_date);
+                update.Loader<bool>("is_settlement");
+                update.Loader<int>("type");
+                update.Loader<int>("sub_type");
+                update.Loader<int>("platform");
+                update.Loader<string>("platform_name");
+                update.Loader<int>("distribution");
+                update.Loader<int>("req_count");
+                update.Loader<int>("dp_transition_succ_count");
+                update.Loader<int>("transition_succ_count");
+                update.Loader<int>("expose_count");
+                update.Loader<int>("expose_user_count");
+                update.Loader<int>("click_count");
+                update.Loader<int>("click_user_count");
+                update.Loader<int>("app_open_count");
+                update.Loader<int>("app_open_user_count");
+                update.Loader<int>("order_count");
+                update.Loader<int>("order_user_count");
+                update.Loader<decimal>("gmv");
+                update.Loader<decimal>("income");
+
+                if (id == 0)
+                {
+
+                    result = update.Create();
+                    success = result > 0;
+
+
+
+                    if (success)
+                    {
+                        OperationLogCore.LogOperation(token.AccessKey, clientIp, $"push_data_report:{report_date}:{platform}:{type}", from.Convert2Json(), "新增");
+                    }
+                }
+                else
+                {
+
+                    var item = new DBContext.Table(conn, "push_data_report").Get<PushDataReportDTO>("id=@id", new { id });
+                    if (item == null) return new APIResult(new { data = new { success = false, msg = "更新失败,记录不存在" } });
+
+                    result = update.Where("id=@id", new { id }).Update();
+
+                    success = result > 0;
+                    if (success)
+                    {
+                        var newItem = new DBContext.Table(conn, "push_data_report").Get<PushDataReportDTO>("id=@id", new { id });
+                        string desc = ObjectComparer.PrintCompareToString(item, newItem).Trim();
+                        OperationLogCore.LogOperation(token.AccessKey, clientIp, $"push_data_report:{report_date}:{platform}:{type}", item.Convert2Json(), desc);
+                    }
+                }
+            }
+            catch (Exception ex)
+            {
+                return new APIResult(new
+                {
+                    data = new { success = false, msg = $"更新失败,{ex.Message}" },
+                });
+            }
+            return new APIResult(new
+            {
+                data = new { success, msg = success ? "更新成功" : "更新失败,请检查输入信息" },
+            });
+        }
+
+
+        [HttpPost]
+        public async Task<ActionResult> save2([FromBody] PushDataReportDTO data)
+        {
+            var clientIp = _accessor.HttpContext.GetUserIp();
+            var token = provider.Get(_accessor.HttpContext);
+
+            using var conn = DBContext.GetOpenConnection();
+            int result = 0;
+            bool success = false;
+
+            try
+            {
+
+                if (data.id == 0)
+                {
+                    result = (int)conn.Insert(data);
+                    success = result > 0;
+                    if (success)
+                    {
+                        OperationLogCore.LogOperation(token.AccessKey, clientIp, $"push_data_report:{data.report_date}:{data.platform}:{data.distribution}", data.Convert2Json(), "新增");
+                    }
+                }
+                else
+                {
+                    var item = new DBContext.Table(conn, "push_data_report").Get<PushDataReportDTO>("id=@id", new { data.id });
+                    if (item == null) return new APIResult(new { data = new { success = false, msg = "更新失败,记录不存在" } });
+
+                    result = (int)conn.Replace(data);
+                    string desc = ObjectComparer.PrintCompareToString(item, data).Trim();
+                    success = result > 0;
+                    if (success)
+                    {
+                        OperationLogCore.LogOperation(token.AccessKey, clientIp, $"push_data_report:{data.report_date}:{data.platform}:{data.distribution}", item.Convert2Json(), desc);
+                    }
+                }
+
+            }
+            catch (Exception ex)
+            {
+                return new APIResult(new
+                {
+                    data = new { success = false, msg = $"更新失败,{ex.Message}" },
+                });
+            }
+            return new APIResult(new
+            {
+                data = new { success, msg = success ? "更新成功" : "更新失败,请检查输入信息" },
+            });
+        }
+
+
+    }
+}

+ 60 - 0
molilian.api/Controllers/admin/ProxyController.cs

@@ -0,0 +1,60 @@
+using molilian.core;
+using dodohold.core;
+using Microsoft.AspNetCore.Mvc;
+using Org.BouncyCastle.Ocsp;
+using System.Text.Json;
+using System.Runtime.InteropServices;
+using TencentCloud.Scf.V20180416.Models;
+using Quartz.Impl.AdoJobStore.Common;
+using TencentCloud.Gaap.V20180529.Models;
+using System.Net;
+using TencentCloud.Ie.V20200304.Models;
+using TencentCloud.Soe.V20180724.Models;
+
+namespace molilian.api.Controllers
+{
+    [ApiController]
+    [MyAuthorize("admin")]
+    [Route("api/[controller]/[action]")]
+    public class ProxyController : ControllerBase
+    {
+        readonly IAuthorizationProvider provider = new AdminProvider();
+        protected IHttpContextAccessor _accessor;
+        public ProxyController(IHttpContextAccessor accessor)
+        {
+            _accessor = accessor;
+        }
+
+        [HttpGet]
+        public ActionResult get()
+        {
+            var list = new DBContext.Table("proxy_nodes")
+                .Where("status=@status", new { status = 1 })
+                .Select<ProxyNodesDTO>();
+
+            // 参考数据
+            //61	1	6	品阅245	品阅辅助网卡	bj	http	http://172.21.127.245:33128	molilian	Bhquvmkn8zLO36lGjuqk	2024-04-09 14:25:53	2024-04-09 14:25:56
+            //59  1   6   品阅243 品阅辅助网卡  bj http    http://172.21.127.243:33128	molilian	Bhquvmkn8zLO36lGjuqk	2024-04-09 14:25:53	2024-04-09 14:25:56
+
+            foreach (var proxy in list)
+            {
+                //通过 curl myip.ipip.net检测proxy可访问行
+            }
+
+
+            var tasks = new List<Task<int>>
+                {
+                Task.Run(()=>{ })
+             };
+
+            // 等待所有任务完成
+            Task.WhenAll(tasks).Wait();
+
+
+
+            return new APIResult(new { list });
+        }
+
+
+    }
+}

+ 1 - 1
molilian.api/Controllers/admin/TaobaoController.cs

@@ -499,12 +499,12 @@ namespace molilian.api.Controllers
                 .PageList<TkReportDTO>(getTotal);
 
 
-
             var tb_accounts = await TkPoolCore.AllListAsync();
             var tb_hide_ids = tb_accounts.Where(e => e.is_hide).Select(e => e.id).ToList();
             result.List = result.List.Where(e => !tb_hide_ids.Contains(e.accountId));
 
 
+
             foreach (var item in result.List)
             {
 #if DEBUG

+ 2 - 2
molilian.api/Controllers/public/TaskController.cs

@@ -27,14 +27,14 @@ namespace molilian.api.Controllers
             _accessor = accessor;
         }
 
-        
+
         [HttpGet]
         public async Task<ActionResult> FillPushReortData(DateTime date = default)
         {
             PushDataReportCore core = new();
             if (date == default) date = DateTime.Now.AddDays(-1);
 
-            int count = await core.FillData(date);
+            int count = await core.FillData(date.Date);
             return new APIResult(new { success = true, count });
         }
 

+ 15 - 2
molilian.api/Controllers/public/TestController.cs

@@ -31,6 +31,19 @@ namespace molilian.api.Controllers
         }
 
 
+        [HttpGet]
+        public async Task<ActionResult> ecs_list_test()
+        {
+            var list = AliyunPoolCore.EcsList();
+            return new APIResult(new
+            {
+                success = true,
+                msg = "ok",
+                list
+            });
+        }
+
+
         [HttpGet]
         public async Task<ActionResult> testReconnectionRedis()
         {
@@ -52,14 +65,14 @@ namespace molilian.api.Controllers
             int aliyun_id = proxy_node.aliyun_id;
             string proxy_server = proxy_node.server;
 
-            var account = new DBContext.Table("aliyun_pool").Get<dynamic>(aliyun_id);
+            var account = new DBContext.Table("aliyun_pool").Get<AliyunPoolDTO>(aliyun_id);
             if (account == null) return new APIResult(new { success = false, msg = "没有匹配的 aliyun_pool 记录" });
 
 
 
             var uri = new Uri(proxy_server);
             string privateIp = uri.Host;
-            AliyunCore core = new AliyunCore(account.id);
+            AliyunCore core = new AliyunCore(account);
             var success = core.ChangePublicIp(privateIp);
             return new APIResult(new { success = "ok" });
         }

Fichier diff supprimé car celui-ci est trop grand
+ 0 - 0
molilian.api/Properties/PublishProfiles/latest.pubxml.user


+ 71 - 3
molilian.core/Core/PushDataReport/PushDataReportCore.cs

@@ -22,6 +22,7 @@ using TencentCloud.Cdn.V20180606.Models;
 using static molilian.core.ApiReportCore;
 using molilian.core.PushDataReport;
 using Org.BouncyCastle.Asn1.Ocsp;
+using TencentCloud.Cms.V20190321.Models;
 
 
 namespace molilian.core
@@ -45,6 +46,7 @@ namespace molilian.core
             count += await FillToolData(reportDatetime);
             count += await FillParseData(reportDatetime);
             count += await FillDeeplinkData(reportDatetime);
+            count += await FillCpsCouponData(reportDatetime);
             return count;
         }
         public async Task<int> FillParseData(DateTime reportDatetime)
@@ -146,6 +148,72 @@ namespace molilian.core
                 return 0;
             }
         }
+        public async Task<int> FillCpsCouponData(DateTime report_date)
+        {
+
+            var list = DeeplinkParseRuleCore.List();
+            var conn = DBContext.GetOpenConnection();
+            try
+            {
+
+                //  107 美团
+                //  110 饿了么
+                //tb/jd/eleme/meituan
+
+                Dictionary<int, string> channels = [];
+                channels.Add(107, "meituan");
+                channels.Add(110, "eleme");
+
+                int count = 0;
+                foreach (var kv in channels)
+                {
+
+                    int platform = kv.Key;
+                    string platform_name = kv.Value;
+                    int type = 2;
+                    int sub_type = 100001;
+
+                    string cacheKey = $":cps_total:{kv.Value}:{report_date:yyyyMMdd}";
+                    int req_count = await TkLogCore.GetTotalAsync(cacheKey);
+                    if (req_count == 0) continue;
+
+                    var update = new DBContext.Table("push_data_report");
+                    update.Add("req_count", req_count);
+                    update.Add("update_time", DateTime.Now);
+
+                    string filter = "report_date=@report_date AND platform=@platform AND type=@type AND sub_type=@sub_type";
+
+                    var item = new DBContext.Table(conn, "push_data_report")
+                        .Get<PushDataReportDTO>(filter, new { report_date, platform, type, sub_type });
+                    if (item == null)
+                    {
+                        update.Add("create_time", DateTime.Now);
+                        update.Add("report_date", report_date);
+                        update.Add("platform", platform);
+                        update.Add("platform_name", platform_name);
+                        update.Add("type", type);
+                        update.Add("sub_type", sub_type);
+                        update.Create();
+                        count++;
+                    }
+                    else
+                    {
+                        if (item.req_count < req_count)
+                        {
+                            var result = update.Where("id=@id", new { item.id }).Update();
+                            count++;
+                        }
+                    }
+                }
+                return count;
+            }
+            catch (Exception ex)
+            {
+                //暂时不记录日志
+                return 0;
+            }
+        }
+
 
         public async Task<int> FillDeeplinkData(DateTime reportDatetime)
         {
@@ -211,16 +279,16 @@ namespace molilian.core
                 var response = await plus.PushReportData(item, cancellationToken);
 
                 bool status = response.code == 200;
-                if (status)
+                if (!status)
                 {
-                    item.request_id = response.message;
+                    item.request_id = $"{item.request_id}:{response.message}";
                 }
 
                 new DBContext.Table("push_data_report")
                     .Add("status", status)
                     .Add("request_id", item.request_id)
                     .Add("update_time", DateTime.Now)
-                    .Where("id=@id", new { id = item.Id })
+                    .Where("id=@id", new { item.id })
                     .Update();
             }
             return count;

+ 6 - 1
molilian.core/Core/PushDataReport/PushDataReportDTO.cs

@@ -19,7 +19,7 @@ public class PushDataReportDTO
     /// </summary>
     [JsonIgnore]
     [Key]
-    public long Id { get; set; }
+    public long id { get; set; }
 
     /// <summary>
     /// 报告日期
@@ -169,6 +169,11 @@ public class PushDataReportDTO
     [JsonIgnore]
     public DateTime update_time { get; set; } = DateTime.Now;
 
+    /// <summary>
+    /// 最后推送时间
+    /// </summary>
+    [JsonIgnore]
+    public DateTime last_push_time { get; set; } = DateTime.Now;
     [JsonIgnore]
     public int status { get; set; } = 0;
 }

+ 0 - 32
molilian.core/Core/aliyun/AliyunAccountDTO.cs

@@ -1,32 +0,0 @@
-
-using dodohold.core;
-
-namespace molilian.core
-{
-    public partial class AliyunAccountDTO
-    {
-
-        [Key]
-        public int Id { get; set; }
-        public string name { get; set; } = string.Empty;
-        public string username { get; set; } = string.Empty;
-        public string password { get; set; } = string.Empty;
-        public string company { get; set; } = string.Empty;
-        public string description { get; set; } = string.Empty;
-        public string mobile { get; set; } = string.Empty;
-        public string accessKeyId { get; set; } = string.Empty;
-        public string accessKeySecret { get; set; } = string.Empty;
-        public bool status { get; set; } = false;
-        public DateTime create_time { get; set; } = DateTime.MinValue;
-
-        public DateTime last_time { get; set; } = DateTime.MinValue;
-        public decimal balance { get; set; } = 0;
-        public string regions { get; set; } = string.Empty;
-
-
-
-    }
-
-
-}
-

+ 22 - 2
molilian.core/Core/aliyun/AliyunCore.cs

@@ -11,6 +11,7 @@ using static AlibabaCloud.SDK.Ecs20140526.Models.DescribeInstancesResponseBody;
 using static AlibabaCloud.SDK.Ecs20140526.Models.DescribeNetworkInterfacesResponseBody;
 using static AlibabaCloud.SDK.Vpc20160428.Models.DescribeEipAddressesResponseBody.DescribeEipAddressesResponseBodyEipAddresses;
 using AlibabaCloud.SDK.ImageSearch20210501.Models;
+using static AlibabaCloud.SDK.Ecs20140526.Models.DescribeNetworkInterfacesResponseBody.DescribeNetworkInterfacesResponseBodyNetworkInterfaceSets;
 
 namespace molilian.core
 {
@@ -18,14 +19,19 @@ namespace molilian.core
     public partial class AliyunCore
     {
         private AliyunPlus plus;
-        public AliyunAccountDTO _account;
+        public AliyunPoolDTO _account;
 
         public AliyunCore(int id)
         {
-            _account = new DBContext.Table("aliyun_pool").Get<AliyunAccountDTO>(id);
+            _account = new DBContext.Table("aliyun_pool").Get<AliyunPoolDTO>(id);
             if (_account == null) throw new Exception("无效账号");
             plus = new AliyunPlus(_account.accessKeyId, _account.accessKeySecret);
         }
+        public AliyunCore(AliyunPoolDTO item)
+        {
+            _account = item;
+            plus = new AliyunPlus(_account.accessKeyId, _account.accessKeySecret);
+        }
 
 
         public AliyunCore(string accessKeyId, string accessKeySecret)
@@ -254,6 +260,20 @@ namespace molilian.core
             }
         }
 
+        public List<DescribeNetworkInterfacesResponseBodyNetworkInterfaceSetsNetworkInterfaceSet> DescribeNetworkInterfaces(string region, string instanceId)
+        {
+            try
+            {
+                var response = plus.DescribeNetworkInterfaces(region, instanceId);
+                var list = response.Body.NetworkInterfaceSets.NetworkInterfaceSet;
+                return list;
+            }
+            catch (Exception ex)
+            {
+                throw new Exception(ex.Message);
+            }
+        }
+
         public bool EcsAssignPrivateIpAddresses(string region, string instanceId, int count)
         {
             try

+ 148 - 1
molilian.core/Core/aliyun/AliyunPoolCore.cs

@@ -9,6 +9,7 @@ using Org.BouncyCastle.Bcpg.OpenPgp;
 using TencentCloud.Tke.V20180525.Models;
 using static molilian.core.TkPoolCore;
 using ZstdSharp.Unsafe;
+using System.Collections.Generic;
 
 namespace molilian.core
 {
@@ -76,7 +77,7 @@ namespace molilian.core
                 decimal amout = 0;
                 try
                 {
-                    AliyunCore core = new AliyunCore(item.id);
+                    AliyunCore core = new AliyunCore(item);
                     var response = core.QueryAccountBalance();
                     var balance = response.Body.Data.AvailableAmount;
                     if (decimal.TryParse(balance, out amout))
@@ -105,6 +106,152 @@ namespace molilian.core
             }
         }
 
+
+
+        public static List<AliyunEcsDTO> EcsList(AliyunPoolDTO item)
+        {
+            List<AliyunEcsDTO> result = [];
+            decimal amout = 0;
+            try
+            {
+                AliyunCore core = new AliyunCore(item);
+                var regions = item.regions.Split(',');
+                foreach (var region in regions)
+                {
+                    var instances = core.GetInstances(region);
+                    foreach (var instance in instances.Instance)
+                    {
+                        var data = new AliyunEcsDTO();
+
+                        data.cpu = (int)instance.Cpu;
+                        data.instance_id = instance.InstanceId;
+                        data.instance_name = instance.InstanceName;
+                        data.host_name = instance.HostName;
+
+                        if (DateTime.TryParse(instance.ExpiredTime, out DateTime expired_time))
+                        {
+                            data.expired_time = expired_time;
+                        }
+                        if (DateTime.TryParse(instance.CreationTime, out DateTime creation_time))
+                        {
+                            data.creation_time = creation_time;
+                        }
+                        data.memory = (int)instance.Memory / 1024;
+                        data.region_id = instance.RegionId;
+                        data.instance_type = instance.InstanceType;
+
+                        var networks = core.DescribeNetworkInterfaces(data.region_id, data.instance_id);
+
+                        data.AddressIps = new List<AddressIpDTO>();
+                        foreach (var networkInterface in networks)
+                        {
+                            //找出网卡信息
+                            string networkInterfaceId = networkInterface.NetworkInterfaceId;
+                            var privateIps = networkInterface?.PrivateIpSets;
+                            foreach (var taraget in privateIps.PrivateIpSet)
+                            {
+                                //找到当前公网IP
+                                string currentPublicIp = taraget?.AssociatedPublicIp?.PublicIpAddress;
+
+                                data.AddressIps.Add(new AddressIpDTO
+                                {
+                                    networkInterfaceId = networkInterfaceId,
+                                    privateIp = taraget.PrivateIpAddress,
+                                    publicIp = currentPublicIp,
+                                });
+                            }
+                        }
+                        result.Add(data);
+                    }
+
+                }
+
+            }
+            catch (Exception ex)
+            {
+                new LoggerLibrary("aliyun", "balance_error")
+                .Info($"Account:{item.id}\tbalance:{amout}")
+                .Info(ex.Message, ex.StackTrace)
+                .SaveAsync();
+            }
+            return result;
+        }
+
+        public static List<AliyunEcsDTO> EcsList()
+        {
+            List<AliyunEcsDTO> result = new List<AliyunEcsDTO>();
+            var list = new DBContext.Table("aliyun_pool").Where(string.Empty, new { }).Select<AliyunPoolDTO>();
+            foreach (var item in list)
+            {
+                if (string.IsNullOrEmpty(item.accessKeyId)) continue;
+
+                decimal amout = 0;
+                try
+                {
+                    AliyunCore core = new AliyunCore(item);
+                    var regions = item.regions.Split(',');
+                    foreach (var region in regions)
+                    {
+                        var instances = core.GetInstances(region);
+                        foreach (var instance in instances.Instance)
+                        {
+                            var data = new AliyunEcsDTO();
+
+                            data.cpu = (int)instance.Cpu;
+                            data.instance_id = instance.InstanceId;
+                            data.instance_name = instance.InstanceName;
+                            data.host_name = instance.HostName;
+
+                            if (DateTime.TryParse(instance.ExpiredTime, out DateTime expired_time))
+                            {
+                                data.expired_time = expired_time;
+                            }
+                            if (DateTime.TryParse(instance.CreationTime, out DateTime creation_time))
+                            {
+                                data.creation_time = creation_time;
+                            }
+                            data.memory = (int)instance.Memory / 1024;
+                            data.region_id = instance.RegionId;
+                            data.instance_type = instance.InstanceType;
+
+                            var networks = core.DescribeNetworkInterfaces(data.region_id, data.instance_id);
+
+                            data.AddressIps = new List<AddressIpDTO>();
+                            foreach (var networkInterface in networks)
+                            {
+                                //找出网卡信息
+                                string networkInterfaceId = networkInterface.NetworkInterfaceId;
+                                var privateIps = networkInterface?.PrivateIpSets;
+                                foreach (var taraget in privateIps.PrivateIpSet)
+                                {
+                                    //找到当前公网IP
+                                    string currentPublicIp = taraget?.AssociatedPublicIp?.PublicIpAddress;
+
+                                    data.AddressIps.Add(new AddressIpDTO
+                                    {
+                                        networkInterfaceId = networkInterfaceId,
+                                        privateIp = taraget.PrivateIpAddress,
+                                        publicIp = currentPublicIp,
+                                    });
+                                }
+                            }
+                            result.Add(data);
+                        }
+
+                    }
+
+                }
+                catch (Exception ex)
+                {
+                    new LoggerLibrary("aliyun", "balance_error")
+                    .Info($"Account:{item.id}\tbalance:{amout}")
+                    .Info(ex.Message, ex.StackTrace)
+                    .SaveAsync();
+                }
+            }
+            return result;
+        }
+
     }
 
 

+ 4 - 0
molilian.core/Core/log/taobao.cs

@@ -196,6 +196,10 @@ namespace molilian.core
                             break;
                     }
                 }
+                if (response.subCode == TkSubCodeEnum.ParseDeny || "接口风控".Equals(response.reason))
+                {
+                    TkPoolCore.SwitchBackup(response.end_point, response.accountId, response.accountName, "接口风控");
+                }
                 if (response.subCode == TkSubCodeEnum.Captcha || "霸下验证码".Equals(response.reason))
                 {
                     TkPoolCore.Suspend(response.end_point, response.accountId, response.accountName, "霸下验证码");

+ 29 - 0
molilian.core/Core/taoke/TkPoolCore.cs

@@ -183,6 +183,7 @@ namespace molilian.core
 
         public static void Refresh()
         {
+            _ = AllListAsync(true);
             _ = ListAsync(true);
         }
         public static void UpdateDrawBalance(string name, decimal amout)
@@ -222,6 +223,34 @@ namespace molilian.core
             EndPointCore.NotifyReload(true);
         }
 
+
+        public static bool IsNeedSwitchBackup(int accountId)
+        {
+            string cache_key = $"cache:tk_pool:{accountId}:switchBackup";
+            long count = RedisHelper.Get<int>(cache_key);
+            return count != 0;
+        }
+
+
+        public static void SwitchBackup(string endpoint, int accountId, string name, string content)
+        {
+            string cache_key = $"cache:tk_pool:{accountId}:switchBackup";
+            long count = RedisHelper.IncrBy(cache_key);
+            RedisHelper.Expire(cache_key, 3600 * 4);
+            if (count > 1) return;
+
+            //_ = ListAsync(true);
+            NotifyCore.Notify(new NifyMessage
+            {
+                message = $"【淘客{accountId}:{name}】{endpoint} 风控,切换备用接口",
+                priority = NifyMessagePriority.high,
+                tags = ["red_circle"]
+            });
+            NotifyCore.AnPushNotify("切换接口", $"【淘客{accountId}:{name}】{endpoint} 切换备用接口");
+            EndPointCore.NotifyReload(true);
+        }
+
+
         public static void Disabled(int accountId, string name, string content)
         {
 #if DEBUG

+ 1 - 0
molilian.core/DTO/alimama/TkDataDTO.cs

@@ -65,6 +65,7 @@ namespace molilian.core
         /// 初筛3
         /// </summary>
         Prelim3 = 112,
+        ParseDeny = 113,
 
     }
 

+ 54 - 0
molilian.core/DTO/aliyun/AliyunEcsDTO.cs

@@ -0,0 +1,54 @@
+
+using dodohold.core;
+using System.Text.Json;
+
+namespace molilian.core
+{
+    [Table("aliyun_ecs")]
+    public class AliyunEcsDTO
+    {
+        [Key]
+        public int id { get; set; }
+
+        public int account_id { get; set; }
+
+        public string name { get; set; } = string.Empty;
+        public string description { get; set; } = string.Empty;
+        public DateTime create_time { get; set; } = DateTime.Now;
+        public DateTime last_time { get; set; } = DateTime.Now;
+
+
+        public string instance_id { get; set; } = string.Empty;
+        public string instance_name { get; set; } = string.Empty;
+        public string host_name { get; set; } = string.Empty;
+        public string os_name { get; set; } = string.Empty;
+        public string region_id { get; set; } = string.Empty;
+        public string instance_type { get; set; } = string.Empty;
+        public int cpu { get; set; } = 0;
+        public decimal memory { get; set; } = 0;
+        public DateTime expired_time { get; set; } = DateTime.MinValue;
+        public DateTime creation_time { get; set; } = DateTime.MinValue;
+
+
+        [Column("address_ips")]
+        public string AddressIpsJson
+        {
+            get => JsonSerializer.Serialize(AddressIps);
+            set => AddressIps = string.IsNullOrEmpty(value)
+                ? new List<AddressIpDTO>()
+                : JsonSerializer.Deserialize<List<AddressIpDTO>>(value);
+        }
+
+        [NotMapped] // 这个属性不会映射到数据库
+        public List<AddressIpDTO> AddressIps { get; set; } = [];
+    }
+
+
+    public class AddressIpDTO
+    {
+        public string networkInterfaceId { get; set; } = string.Empty;
+        public string privateIp { get; set; } = string.Empty;
+        public string publicIp { get; set; } = string.Empty;
+    }
+
+}

+ 1 - 0
molilian.core/DTO/aliyun/AliyunPoolDTO.cs

@@ -26,6 +26,7 @@ namespace molilian.core
 
         public decimal balance_alert_threshold { get; set; } = 0;
         public string regions { get; set; } = string.Empty;
+        public List<AliyunEcsDTO> ecs_list { get; set; } = [];
 
     }
 

+ 12 - 1
molilian.core/Plus/Alimama/parse.cs

@@ -187,7 +187,18 @@ namespace molilian.core
             while (try_count == 0 || try_count <= _config.tk_parse_retry_count)
             {
                 if (try_count >= 3) break;
-                result = await alimamaParseAsync(result.content, result, cancellationToken);
+
+                result = await alimamaParseAsync2(result.content, result, cancellationToken);
+
+                //if (TkPoolCore.IsNeedSwitchBackup(_accountId))
+                //{
+                //    result = await alimamaParseAsync2(result.content, result, cancellationToken);
+                //}
+                //else
+                //{
+                //    result = await alimamaParseAsync(result.content, result, cancellationToken);
+                //}
+
                 if (!"该链接不支持转化,请更换链接尝试".Equals(result.message)) break;
                 try_count++;
             }

+ 315 - 16
molilian.core/Plus/Alimama/parse_2.cs

@@ -158,26 +158,30 @@ namespace molilian.core
             return Regex.IsMatch(content, pattern);
         }
 
-        public TimeSpan GetRequestTimeout(int deduction = 0)
+        public TimeSpan GetRequestTimeout()
         {
-#if DEBUG
-            return TimeSpan.FromMilliseconds(10 * 1000);
-#endif
-            int min = (int)(_config.rt_max * 0.3);
+            int min = (int)(_config.rt_max * 0.5);
+            if (_config.rt_max == 0) return TimeSpan.FromMilliseconds(1000);
+            int timeout = _config.rt_max;
+
+            timeout -= min;
+            return TimeSpan.FromMilliseconds(timeout);
+
+        }
+
+        public TimeSpan GetRequestTimeout2(int deduction = 0)
+        {
+            int min = (int)(_config.rt_max * 0.5);
             if (_config.rt_max == 0) return TimeSpan.FromMilliseconds(1000);
 
             int timeout = _config.rt_max;
-            if (deduction == 0)
-            {
-                timeout -= min;
-                return TimeSpan.FromMilliseconds(timeout);
-            }
 
             timeout -= deduction;
-            if (timeout <= min) return TimeSpan.FromMilliseconds(1);
-            return TimeSpan.FromMilliseconds(min);
+            if (timeout <= min) return TimeSpan.FromMilliseconds(min);
+            return TimeSpan.FromMilliseconds(timeout);
         }
 
+
         /// <summary>
         /// 从http获取跳转的url
         /// </summary>
@@ -212,7 +216,7 @@ namespace molilian.core
                 client.Proxy = null;
                 var response = await client.RequestAsync(url, "GET");
 #else
-                client.Timeout = GetRequestTimeout(0);
+                client.Timeout = GetRequestTimeout();
                 var response = await client.RequestAsync(url, "GET", cancellationToken);
 #endif
 
@@ -281,7 +285,7 @@ namespace molilian.core
 #if DEBUG
                 client.Proxy = null;
 #endif
-                client.Timeout = GetRequestTimeout(0);
+                client.Timeout = GetRequestTimeout();
                 var response = client.Request(url);
 
 
@@ -614,6 +618,290 @@ namespace molilian.core
             return LinkTypeEnum.unknown;
         }
 
+        public async Task<TkDataDTO> alimamaParseAsync2(string content, TkDataDTO result, CancellationToken cancellationToken = default)
+        {
+            string t = $"{DateTime.Now.Convert2UnixTimestamp(true)}";
+
+            Random random = new();
+            double randomNumber = random.NextDouble();
+            string randomString = randomNumber.ToString()[2..];
+
+            string cna = _cookies.GetContentPart("cna=", ";");
+            string firstFiveCharacters = cna[..Math.Min(5, cna.Length)];
+
+            //var variableMap = new
+            //{
+            //    url = content,
+            //    union_lens = $"b_pvid:a219t._portal_v2_tool_links_page_home_index_htm_{t}_{randomString}_{firstFiveCharacters}",
+            //    lensScene = "PUB",
+            //    spmB = "_portal_v2_tool_links_page_home_index_htm"
+            //}.Convert2Json(true).UrlEncode();
+
+            string item_id = content.GetContentPart("item.htm?id=", "");
+            var variableMap = new
+            {
+                itemId = item_id
+            }.Convert2Json(true).UrlEncode();
+
+
+            variableMap = variableMap.Replace(" ", "%20");
+            _floorId = "102359";
+            string url = "https://pub.alimama.com/openapi/param2/1/gateway.unionpub/xt.entry.json?" +
+                $"t={t}&_tb_token_={_tb_token}&floorId={_floorId}&refpid={_refpid}&variableMap={variableMap}";
+
+
+
+            Stopwatch stopwatch = Stopwatch.StartNew();
+            stopwatch.Start();
+            var client = new WebClientUtility().SetContentType("application/json;charset=utf-8")
+                        .AddHeaders("X-Requested-With", "XMLHttpRequest")
+                        .AddHeaders("Cookie", _cookies);
+            client.Proxy = _proxy;
+#if DEBUG
+            client.Proxy = null;
+#endif
+            if (!string.IsNullOrEmpty(_user_agent)) client.UserAgent = _user_agent;
+            client.Timeout = GetRequestTimeout2(result.elapsedTime2);
+            //var response = client.Request(url);
+
+#if DEBUG
+            var response = await client.RequestAsync(url, "GET");
+#else
+            var response = await client.RequestAsync(url, "GET", cancellationToken);
+#endif
+
+            stopwatch.Stop();
+            result.elapsedTime3 = (int)stopwatch.ElapsedMilliseconds;
+
+
+
+            var body = string.Empty;
+            try
+            {
+                if (!response.Successed)
+                {
+                    result.channel = TkChannelEnum.tb;
+                    result.link_type = LinkTypeEnum.unknown;
+                    result.success = false;
+                    result.message = "fail";
+
+                    if (response.ResponseException != null)
+                    {
+                        _ = new LoggerLibrary("api_error", "fail")
+                            .Info(response.ResponseException.Message, response.ResponseException.StackTrace)
+                            .SaveAsync();
+                        throw response.ResponseException;
+                    }
+
+                    return result;
+                }
+                if (response.ResponseMessage.StatusCode == System.Net.HttpStatusCode.Found)
+                {
+                    _ = new LoggerLibrary("api_error", "fail")
+                        .Info($"302:{response.ResponseMessage.Headers.Location}")
+                        .SaveAsync();
+                    throw new Exception("302 Found, was canceled");
+                }
+                JsonElement root;
+                try
+                {
+                    body = response.Body();
+                    //{"success":false,"message":"result empty"}
+
+
+                    root = body.Convert2JsonElement();
+                }
+                catch (Exception ex)
+                {
+                    _ = new LoggerLibrary("api_error", "fail")
+                        .Info(ex.Message, ex.StackTrace)
+                        .SaveAsync();
+
+                    if (body.Contains("https://g.alicdn.com/sd/punish/waf_block.html"))
+                    {
+
+                        result.channel = TkChannelEnum.tb;
+                        result.link_type = LinkTypeEnum.unknown;
+                        result.success = false;
+                        result.message = "waf_block";
+                        result.reason = "接口风控";
+                        return result;
+                    }
+                    throw new Exception(body);
+                }
+
+
+                bool success = root.Read<bool>("success", false);
+                string message = root.Read("message", string.Empty);
+                string info_message = root.PathRead("info.message", string.Empty);
+                if (!string.IsNullOrEmpty(info_message)) message = info_message;
+
+                if ("result empty".Equals(message))
+                {
+                    result.subCode = TkSubCodeEnum.NoConvert;
+
+                }
+                JsonElement item = default;
+
+                if (success)
+                {
+                    var data = root.ElementRead("data");
+                    var resultList = data.ElementRead("resultList");
+                    if (resultList.ValueKind != JsonValueKind.Array)
+                    {
+                        _ = new LoggerLibrary("api_error", "fail")
+                            .Info("resultList Undefined", body)
+                            .SaveAsync();
+                        throw new Exception("resultList Undefined");
+                    }
+                    item = resultList[0];
+                }
+
+
+
+                string taoToken = item.Read("taoToken", string.Empty);
+                string shortLinkurl = item.Read("shortLinkurl", string.Empty);
+
+                string couponLinkTaoToken = item.Read("couponLinkTaoToken", string.Empty);
+                string couponShortLinkUrl = item.Read("couponShortLinkUrl", string.Empty);
+                decimal couponAmount = item.Read<decimal>("couponAmount", 0);
+                string couponEffectiveEndTime = item.Read("couponEffectiveEndTime", string.Empty);
+                string couponEffectiveStartTime = item.Read("couponEffectiveStartTime", string.Empty);
+
+                string itemId = item.Read("itemId", string.Empty);
+                string mktId = item.Read("outputMktId", string.Empty);
+                string itemName = item.Read("itemName", string.Empty);
+                decimal promotionPrice = item.Read<decimal>("promotionPrice", 0);
+                string sellerNickName = item.Read("sellerNickName", string.Empty);
+                string shopTitle = item.Read("shopTitle", string.Empty);
+                string pic = item.Read("data.pic", string.Empty);
+                if (pic.StartsWith("//")) pic = "https:" + pic;
+
+                string qrCodeUrl = item.Read("qrCodeUrl", string.Empty);
+
+
+                if (response.ResponseMessage != null)
+                {
+
+                    switch (response.ResponseMessage.StatusCode)
+                    {
+                        case System.Net.HttpStatusCode.OK:
+                            {
+                                if (couponAmount > 0 && !string.IsNullOrEmpty(couponLinkTaoToken) && !string.IsNullOrEmpty(couponShortLinkUrl))
+                                {
+                                    taoToken = couponLinkTaoToken;
+                                    shortLinkurl = couponShortLinkUrl;
+                                }
+                                string shortLink = GetLink(taoToken);
+                                content = ReplaceUrls(content, shortLink);
+                            }
+                            break;
+                        case System.Net.HttpStatusCode.Found:
+                            string location = response.ResponseMessage.Headers.Location.OriginalString;
+                            if (!string.IsNullOrEmpty(location) && location.Contains("www.alimama.com/member/login.htm"))
+                            {
+                                success = false;
+                                message = "nologin";
+                            }
+                            break;
+                        default:
+                            {
+                                success = false;
+                                message = "other";
+                            }
+                            break;
+                    }
+                }
+                if (!success)
+                {
+                    shortLinkurl = GetLink(content);
+                    switch (message)
+                    {
+                        case "该商品已经下架或未加入淘宝客":
+                        case "该链接不支持转化,请更换链接尝试":
+                        case "result empty":
+                            result.subCode = TkSubCodeEnum.NoConvert;
+                            break;
+                        case "网络错误":
+                            result.subCode = TkSubCodeEnum.NetError;
+                            break;
+                        default:
+                            var _headers = response.ResponseMessage.Headers;
+                            var headers = "";
+                            foreach (var h in _headers)
+                            {
+                                foreach (var Value in h.Value)
+                                {
+                                    headers += $"{h.Key}: {Value}\n";
+                                }
+                            }
+                            _ = new LoggerLibrary("api_error", "fail")
+                                .Info(message, content)
+                                .Info(headers, body)
+                                .SaveAsync();
+                            break;
+                    }
+                }
+
+                shortLinkurl = GetLink(taoToken);
+                string deeplink_url = GetDeeplink(shortLinkurl);
+
+                result.channel = TkChannelEnum.tb;
+
+                if (success)
+                {
+                    result.subCode = TkSubCodeEnum.Success;
+                    switch (result.link_type)
+                    {
+                        case LinkTypeEnum.profile:
+                        case LinkTypeEnum.goods:
+                        case LinkTypeEnum.video:
+                        case LinkTypeEnum.live:
+                            break;
+                        default:
+                            result.link_type = LinkTypeEnum.goods;
+                            break;
+                    }
+                }
+
+                result.success = success;
+                result.message = message;
+                result.reason = string.Empty;
+
+                result.content = content;
+                result.couponAmount = couponAmount;
+                result.couponEffectiveEndTime = couponEffectiveEndTime;
+                result.couponEffectiveStartTime = couponEffectiveStartTime;
+                result.taoToken = taoToken;
+                if (!string.IsNullOrEmpty(shortLinkurl))
+                {
+                    result.shortLinkurl = shortLinkurl;
+                    result.deeplink_url = deeplink_url;
+                }
+                result.mktId = mktId;
+
+                result.itemId = itemId;
+                result.itemName = itemName;
+                result.promotionPrice = promotionPrice;
+                result.sellerNickName = sellerNickName;
+                result.shopTitle = shopTitle;
+                result.pic = pic;
+                result.qrCodeUrl = qrCodeUrl;
+            }
+            catch (Exception ex)
+            {
+                if (response.ResponseMessage?.StatusCode == System.Net.HttpStatusCode.OK)
+                {
+                    if (body.Contains("<p>抱歉!页面无法访问……</p>"))
+                    {
+                        throw new APIException("抱歉!页面无法访问……");
+                    }
+                }
+                throw;
+            }
+            return result;
+        }
+
         public async Task<TkDataDTO> alimamaParseAsync(string content, TkDataDTO result, CancellationToken cancellationToken = default)
         {
             string t = $"{DateTime.Now.Convert2UnixTimestamp(true)}";
@@ -650,7 +938,7 @@ namespace molilian.core
             client.Proxy = null;
 #endif
             if (!string.IsNullOrEmpty(_user_agent)) client.UserAgent = _user_agent;
-            client.Timeout = GetRequestTimeout(result.elapsedTime2);
+            client.Timeout = GetRequestTimeout2(result.elapsedTime2);
             //var response = client.Request(url);
 
 #if DEBUG
@@ -712,6 +1000,17 @@ namespace molilian.core
                         result.message = "waf_block";
                         return result;
                     }
+
+                    if (body.Contains("https://bixi.alicdn.com") && body.Contains("\"action\": \"deny\""))
+                    {
+                        result.channel = TkChannelEnum.tb;
+                        result.link_type = LinkTypeEnum.unknown;
+                        result.subCode = TkSubCodeEnum.ParseDeny;
+                        result.success = false;
+                        result.message = "waf_block";
+                        result.reason = "接口风控";
+                        return result;
+                    }
                     throw new Exception(body);
                 }
 
@@ -902,7 +1201,7 @@ namespace molilian.core
                $"t={t}&_tb_token_={_tb_token}&floorId={_floorId}&refpid={_refpid}&variableMap={variableMap}";
             client.Headers["Host"] = "pub.alimama.com";
 #endif
-            client.Timeout = GetRequestTimeout(result.elapsedTime2);
+            client.Timeout = GetRequestTimeout2(result.elapsedTime2);
             //var response = client.Request(url);
             var response = client.Request(url);
 

+ 0 - 143
molilian.core/Plus/Aliyun/Ecs.cs

@@ -630,149 +630,6 @@ namespace molilian.core
             }
             return null;
 
-            /*
-            {
-              "TotalCount": 2,
-              "NextToken": "AAAAAdDWBF2w6Olxc+cMPjUtUMqZeJtDdqvzzbLhu200mYNui74QNEqg9KVUarNzND4/xA==",
-              "PageSize": 10,
-              "RequestId": "E5C6E7D9-8A26-57EC-B7B0-7B04CF7AC822",
-              "PageNumber": 1,
-              "NetworkInterfaceSets": {
-                "NetworkInterfaceSet": [
-                  {
-                    "PrivateIpAddress": "172.26.246.236",
-                    "ServiceManaged": false,
-                    "DeleteOnRelease": true,
-                    "ResourceGroupId": "",
-                    "Attachment": {},
-                    "NetworkInterfaceId": "eni-2ze2bgtgn8187kti5xlk",
-                    "Ipv6Sets": {
-                      "Ipv6Set": []
-                    },
-                    "OwnerId": 1903512636035761,
-                    "AssociatedPublicIp": {
-                      "PublicIpAddress": "101.200.231.225"
-                    },
-                    "Status": "InUse",
-                    "NetworkInterfaceTrafficMode": "Standard",
-                    "ZoneId": "cn-beijing-g",
-                    "InstanceId": "i-2ze58hz63abqwi97eql5",
-                    "VSwitchId": "vsw-2ze1l2p0nwulsib3baj22",
-                    "NetworkInterfaceName": "eni-20241111",
-                    "MacAddress": "00:16:3e:3b:8e:f9",
-                    "SecurityGroupIds": {
-                      "SecurityGroupId": [
-                        "sg-2ze3ks3fd85brhe9c48x"
-                      ]
-                    },
-                    "SourceDestCheck": false,
-                    "Type": "Secondary",
-                    "QueueNumber": 2,
-                    "VpcId": "vpc-2zef23dd2ah5byvaampoh",
-                    "Ipv6PrefixSets": {
-                      "Ipv6PrefixSet": []
-                    },
-                    "CreationTime": "2024-11-11T08:43:05Z",
-                    "Ipv4PrefixSets": {
-                      "Ipv4PrefixSet": []
-                    },
-                    "PrivateIpSets": {
-                      "PrivateIpSet": [
-                        {
-                          "PrivateIpAddress": "172.26.246.236",
-                          "AssociatedPublicIp": {
-                            "PublicIpAddress": "101.200.231.225"
-                          },
-                          "Primary": true
-                        },
-                        {
-                          "PrivateIpAddress": "172.26.246.245",
-                          "AssociatedPublicIp": {
-                            "PublicIpAddress": "47.95.11.84"
-                          },
-                          "Primary": false
-                        },
-                        {
-                          "PrivateIpAddress": "172.26.246.246",
-                          "AssociatedPublicIp": {
-                            "PublicIpAddress": "101.201.66.83"
-                          },
-                          "Primary": false
-                        },
-                        {
-                          "PrivateIpAddress": "172.26.246.243",
-                          "AssociatedPublicIp": {
-                            "PublicIpAddress": "47.93.9.144"
-                          },
-                          "Primary": false
-                        },
-                        {
-                          "PrivateIpAddress": "172.26.246.244",
-                          "AssociatedPublicIp": {
-                            "PublicIpAddress": "47.94.193.172"
-                          },
-                          "Primary": false
-                        },
-                        {
-                          "PrivateIpAddress": "172.26.246.247",
-                          "AssociatedPublicIp": {
-                            "PublicIpAddress": "47.95.194.86"
-                          },
-                          "Primary": false
-                        }
-                      ]
-                    }
-                  },
-                  {
-                    "PrivateIpAddress": "172.26.246.235",
-                    "ServiceManaged": false,
-                    "DeleteOnRelease": true,
-                    "ResourceGroupId": "",
-                    "Attachment": {},
-                    "NetworkInterfaceId": "eni-2ze3ks3fd85brff1j4av",
-                    "Ipv6Sets": {
-                      "Ipv6Set": []
-                    },
-                    "OwnerId": 1903512636035761,
-                    "AssociatedPublicIp": {
-                      "PublicIpAddress": "47.93.249.227"
-                    },
-                    "Status": "InUse",
-                    "NetworkInterfaceTrafficMode": "Standard",
-                    "ZoneId": "cn-beijing-g",
-                    "InstanceId": "i-2ze58hz63abqwi97eql5",
-                    "VSwitchId": "vsw-2ze1l2p0nwulsib3baj22",
-                    "MacAddress": "00:16:3e:37:f1:5e",
-                    "SecurityGroupIds": {
-                      "SecurityGroupId": [
-                        "sg-2ze3ks3fd85brhe9c48x"
-                      ]
-                    },
-                    "Type": "Primary",
-                    "QueueNumber": 2,
-                    "VpcId": "vpc-2zef23dd2ah5byvaampoh",
-                    "Ipv6PrefixSets": {
-                      "Ipv6PrefixSet": []
-                    },
-                    "CreationTime": "2024-04-09T04:28:44Z",
-                    "Ipv4PrefixSets": {
-                      "Ipv4PrefixSet": []
-                    },
-                    "PrivateIpSets": {
-                      "PrivateIpSet": [
-                        {
-                          "PrivateIpAddress": "172.26.246.235",
-                          "AssociatedPublicIp": {
-                            "PublicIpAddress": "47.93.249.227"
-                          },
-                          "Primary": true
-                        }
-                      ]
-                    }
-                  }
-                ]
-              }
-            } */
         }
 
 

Certains fichiers n'ont pas été affichés car il y a eu trop de fichiers modifiés dans ce diff