RefundOrders.cs 18 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424
  1. using dodohold.core;
  2. using System.Text.Json;
  3. namespace molilian.core
  4. {
  5. public partial class AlimamaPlus
  6. {
  7. private const string base_refund_orders_url = "https://pub.alimama.com/openapi/param2/1/gateway.unionpub/report.publisher.getRefundOrderDetail.json";
  8. public async Task<int> GetHistoryRefundOrdersAsync(int sleep, DateTime startTime, DateTime endTime)
  9. {
  10. // 隐藏号不同步任何订单数据
  11. if (_account.is_hide) return 0;
  12. //DateTime endTime = DateTime.Now;
  13. //DateTime startTime = endTime.AddDays(-90);
  14. //if (_accountId == 3) endTime = DateTime.Parse("2024-04-07");
  15. //#if DEBUG
  16. // startTime = DateTime.Parse("2024-05-01");
  17. // endTime = DateTime.Parse("2024-06-01");
  18. // int total = 0;
  19. // List<DateTime> orderTimes = new List<DateTime>();
  20. // for (DateTime date = startTime; date <= endTime; date = date.AddDays(1))
  21. // {
  22. // orderTimes.Add(date);
  23. // }
  24. //#else
  25. //当日往前查询
  26. (int total, DateTime max_modifiedTime, List<DateTime> orderTimes) = await GetTkRefundOrdersAsync(startTime, endTime, DateTime.MinValue, false, sleep);
  27. //#endif
  28. string sql = @"
  29. UPDATE tk_report tr
  30. JOIN (
  31. SELECT
  32. accountId, DATE(tbTradeCreateTime) AS date, SUM(refundFee) AS refund_order_ord_amt,
  33. COUNT(*) AS refund_order_ord_num, SUM(showReturnFee) AS refund_order_ord_tfee
  34. FROM tk_refund_order_details
  35. WHERE DATE(tbTradeCreateTime) IN @orderTimes AND refundStatus=2 AND accountId=@accountId
  36. GROUP BY DATE(tbTradeCreateTime), accountId
  37. ) AS sub
  38. ON tr.accountId = sub.accountId AND tr.report_date = sub.date
  39. SET tr.refund_order_ord_amt = sub.refund_order_ord_amt,
  40. tr.refund_order_ord_tfee = sub.refund_order_ord_tfee,
  41. tr.refund_order_ord_num = sub.refund_order_ord_num;";
  42. DBContext.Execute(sql, new { accountId = _accountId, orderTimes });
  43. sql = @"
  44. UPDATE tk_report tr
  45. JOIN (
  46. SELECT
  47. accountId, DATE(tbTradeCreateTime) AS date, SUM(refundFee) AS refund_order_ord_amt,
  48. COUNT(*) AS refund_order_ord_num, SUM(showReturnFee) AS refund_order_ord_tfee
  49. FROM tk_refund_order_details
  50. WHERE DATE(tbTradeCreateTime) IN @orderTimes AND refundStatus=4 AND accountId=@accountId
  51. GROUP BY DATE(tbTradeCreateTime), accountId
  52. ) AS sub
  53. ON tr.accountId = sub.accountId AND tr.report_date = sub.date
  54. SET tr.refund_order_ord_amt_4 = sub.refund_order_ord_amt,
  55. tr.refund_order_ord_tfee_4 = sub.refund_order_ord_tfee,
  56. tr.refund_order_ord_num_4 = sub.refund_order_ord_num;";
  57. DBContext.Execute(sql, new { accountId = _accountId, orderTimes });
  58. sql = @"
  59. UPDATE tk_report tr
  60. JOIN (
  61. SELECT
  62. accountId, DATE(RefundCreateTime) AS date,
  63. SUM(showReturnFee) AS refund_order_ord_tfee
  64. FROM tk_refund_order_details
  65. WHERE DATE(RefundCreateTime) IN @orderTimes AND accountId=@accountId
  66. GROUP BY DATE(RefundCreateTime), accountId
  67. ) AS sub
  68. ON tr.accountId = sub.accountId AND tr.report_date = sub.date
  69. SET tr.refund_order_ord_freeze_tfee = 0-sub.refund_order_ord_tfee;";
  70. DBContext.Execute(sql, new { accountId = _accountId, orderTimes });
  71. sql = @"
  72. UPDATE tk_report tr
  73. JOIN (
  74. SELECT
  75. accountId, DATE(RefundFinishTime) AS date,
  76. SUM(showReturnFee) AS refund_order_ord_tfee
  77. FROM tk_refund_order_details
  78. WHERE DATE(RefundFinishTime) IN @orderTimes AND refundStatus=2 AND accountId=@accountId
  79. GROUP BY DATE(RefundFinishTime), accountId
  80. ) AS sub
  81. ON tr.accountId = sub.accountId AND tr.report_date = sub.date
  82. SET tr.refund_order_ord_deduct_tfee = 0-sub.refund_order_ord_tfee;";
  83. DBContext.Execute(sql, new { accountId = _accountId, orderTimes });
  84. sql = @"
  85. UPDATE tk_report tr
  86. JOIN (
  87. SELECT
  88. accountId, DATE(RefundFinishTime) AS date,
  89. SUM(showReturnFee) AS refund_order_ord_tfee
  90. FROM tk_refund_order_details
  91. WHERE DATE(RefundFinishTime) IN @orderTimes AND refundStatus IN (2,3) AND accountId=@accountId
  92. GROUP BY DATE(RefundFinishTime), accountId
  93. ) AS sub
  94. ON tr.accountId = sub.accountId AND tr.report_date = sub.date
  95. SET tr.refund_order_ord_unfreeze_tfee = sub.refund_order_ord_tfee;";
  96. DBContext.Execute(sql, new { accountId = _accountId, orderTimes });
  97. //refundStatus3 失败
  98. //2 成功
  99. //4创建
  100. //public decimal refund_order_ord_deduct_tfee { get; set; } = 0;
  101. //public decimal refund_order_ord_freeze_tfee { get; set; } = 0;
  102. //public decimal refund_order_ord_unfreeze_tfee { get; set; } = 0;
  103. return total;
  104. }
  105. public async Task<int> GetIncyRefundOrdersAsync(int sleep)
  106. {
  107. // 隐藏号不同步任何订单数据
  108. if (_account.is_hide) return 0;
  109. string cacheKey = $":cache:GetIncyRefundOrders:{_accountId}";
  110. DateTime endTime = DateTime.Now;
  111. DateTime startTime = endTime.AddDays(-1);
  112. DateTime last_modifiedTime = RedisHelper.Get<DateTime>(cacheKey);
  113. ////找出数据库最新的一天
  114. //var last = new DBContext.Table("tk_order_details")
  115. // .Order("modifiedTime DESC")
  116. // .Get<TkRefundOrderDetailDTO>("accountId=@accountId", new { accountId = _accountId });
  117. if (last_modifiedTime != DateTime.MinValue)
  118. {
  119. startTime = last_modifiedTime;
  120. }
  121. else
  122. {
  123. last_modifiedTime = startTime;
  124. }
  125. //当日往前查询
  126. (int total, DateTime max_modifiedTime, List<DateTime> orderTimes) = await GetTkRefundOrdersAsync(startTime, endTime, last_modifiedTime, true, sleep);
  127. if (max_modifiedTime != DateTime.MinValue)
  128. {
  129. RedisHelper.Set(cacheKey, max_modifiedTime);
  130. }
  131. string sql = @"
  132. UPDATE tk_report tr
  133. JOIN (
  134. SELECT
  135. accountId, DATE(tbTradeCreateTime) AS date, SUM(refundFee) AS refund_order_ord_amt,
  136. COUNT(*) AS refund_order_ord_num, SUM(showReturnFee) AS refund_order_ord_tfee
  137. FROM tk_refund_order_details
  138. WHERE DATE(tbTradeCreateTime) IN @orderTimes AND refundStatus=2 AND accountId=@accountId
  139. GROUP BY DATE(tbTradeCreateTime), accountId
  140. ) AS sub
  141. ON tr.accountId = sub.accountId AND tr.report_date = sub.date
  142. SET tr.refund_order_ord_amt = sub.refund_order_ord_amt,
  143. tr.refund_order_ord_tfee = sub.refund_order_ord_tfee,
  144. tr.refund_order_ord_num = sub.refund_order_ord_num;";
  145. DBContext.Execute(sql, new { accountId = _accountId, orderTimes });
  146. sql = @"
  147. UPDATE tk_report tr
  148. JOIN (
  149. SELECT
  150. accountId, DATE(tbTradeCreateTime) AS date, SUM(refundFee) AS refund_order_ord_amt,
  151. COUNT(*) AS refund_order_ord_num, SUM(showReturnFee) AS refund_order_ord_tfee
  152. FROM tk_refund_order_details
  153. WHERE DATE(tbTradeCreateTime) IN @orderTimes AND refundStatus=4 AND accountId=@accountId
  154. GROUP BY DATE(tbTradeCreateTime), accountId
  155. ) AS sub
  156. ON tr.accountId = sub.accountId AND tr.report_date = sub.date
  157. SET tr.refund_order_ord_amt_4 = sub.refund_order_ord_amt,
  158. tr.refund_order_ord_tfee_4 = sub.refund_order_ord_tfee,
  159. tr.refund_order_ord_num_4 = sub.refund_order_ord_num;";
  160. DBContext.Execute(sql, new { accountId = _accountId, orderTimes });
  161. sql = @"
  162. UPDATE tk_report tr
  163. JOIN (
  164. SELECT
  165. accountId, DATE(RefundCreateTime) AS date,
  166. SUM(showReturnFee) AS refund_order_ord_tfee
  167. FROM tk_refund_order_details
  168. WHERE DATE(RefundCreateTime) IN @orderTimes AND accountId=@accountId
  169. GROUP BY DATE(RefundCreateTime), accountId
  170. ) AS sub
  171. ON tr.accountId = sub.accountId AND tr.report_date = sub.date
  172. SET tr.refund_order_ord_freeze_tfee = 0-sub.refund_order_ord_tfee;";
  173. DBContext.Execute(sql, new { accountId = _accountId, orderTimes });
  174. sql = @"
  175. UPDATE tk_report tr
  176. JOIN (
  177. SELECT
  178. accountId, DATE(RefundFinishTime) AS date,
  179. SUM(showReturnFee) AS refund_order_ord_tfee
  180. FROM tk_refund_order_details
  181. WHERE DATE(RefundFinishTime) IN @orderTimes AND refundStatus=2 AND accountId=@accountId
  182. GROUP BY DATE(RefundFinishTime), accountId
  183. ) AS sub
  184. ON tr.accountId = sub.accountId AND tr.report_date = sub.date
  185. SET tr.refund_order_ord_deduct_tfee = 0-sub.refund_order_ord_tfee;";
  186. DBContext.Execute(sql, new { accountId = _accountId, orderTimes });
  187. sql = @"
  188. UPDATE tk_report tr
  189. JOIN (
  190. SELECT
  191. accountId, DATE(RefundFinishTime) AS date,
  192. SUM(showReturnFee) AS refund_order_ord_tfee
  193. FROM tk_refund_order_details
  194. WHERE DATE(RefundFinishTime) IN @orderTimes AND refundStatus IN (2,3) AND accountId=@accountId
  195. GROUP BY DATE(RefundFinishTime), accountId
  196. ) AS sub
  197. ON tr.accountId = sub.accountId AND tr.report_date = sub.date
  198. SET tr.refund_order_ord_unfreeze_tfee = sub.refund_order_ord_tfee;";
  199. DBContext.Execute(sql, new { accountId = _accountId, orderTimes });
  200. return total;
  201. }
  202. public async Task<(int, DateTime, List<DateTime>)> GetTkRefundOrdersAsync(DateTime startTime, DateTime endTime, DateTime last_modifiedTime, bool desc = true, int sleep = 100)
  203. {
  204. List<DateTime> orderTimes = [];
  205. // 确保 startTime 小于 endTime
  206. if (startTime > endTime)
  207. {
  208. (startTime, endTime) = (endTime, startTime);
  209. }
  210. DateTime max_modifiedTime = last_modifiedTime;
  211. int pageNo = 1;
  212. string positionIndex = string.Empty;
  213. int pageSize = 100;
  214. bool hasNext = true;
  215. int total = 0;
  216. while (hasNext)
  217. {
  218. var ts = DateTime.Now.Convert2UnixTimestamp(true);
  219. //string jumpType = desc ? pageNo == 1 ? "0" : "1" : "-1";
  220. string jumpType = pageNo == 1 ? "0" : "1";
  221. //string queryType = "1";
  222. //1 创建时间;3结算时间 2付款时间 4更新时间
  223. //string queryType = "2";
  224. string queryType = desc ? "4" : "2";
  225. string url = $"{base_refund_orders_url}?t={ts}&_tb_token_={_tb_token}&pageNo={pageNo}&pageSize={pageSize}&startTime={startTime:yyyy-MM-dd}&endTime={endTime:yyyy-MM-dd}&payStatus=&queryType={queryType}&toPage=1&perPageSize={pageSize * 2}&jumpType={jumpType}&isFullRefund=0&memberType=&positionIndex={positionIndex.UrlEncode()}";
  226. string body = "";
  227. JsonElement data;
  228. try
  229. {
  230. for (var i = 1; i <= 5; i++)
  231. {
  232. var client = new WebClientUtility().SetContentType("application/json;charset=utf-8")
  233. .AddHeaders("X-Requested-With", "XMLHttpRequest")
  234. .AddHeaders("Cookie", _cookies);
  235. #if DEBUG
  236. #else
  237. client.Proxy = _proxy;
  238. #endif
  239. if (!string.IsNullOrEmpty(_user_agent)) client.UserAgent = _user_agent;
  240. var response = client.Request(url);
  241. if (response.ResponseException != null)
  242. {
  243. _ = new LoggerLibrary("api_error", "fail")
  244. .Info(response.ResponseException.Message, response.ResponseException.StackTrace)
  245. .SaveAsync();
  246. throw response.ResponseException;
  247. }
  248. body = response.Body();
  249. if (body.Contains("{\"action\":\"captcha\""))
  250. {
  251. RiskControlCore.SetRiskCookie($"tb:{_accountId}", "滑块");
  252. string message = $"【GetTkRefundOrders】【{_accountId}:{_accountName}】第 {i} 次出现滑动验证码";
  253. //NotifyCore.Notify(new NifyMessage
  254. //{
  255. // message = message,
  256. // priority = NifyMessagePriority.high,
  257. // tags = ["red_circle"]
  258. //});
  259. await Task.Delay(i * 60 * 1000);
  260. continue;
  261. }
  262. if (body.Contains("\"resultCode\":500"))
  263. {
  264. string message = $"【GetTkRefundOrders】【{_accountId}:{_accountName}】第 {i} 次出现错误\n{body}";
  265. NotifyCore.Notify(new NifyMessage
  266. {
  267. message = message,
  268. priority = NifyMessagePriority.high,
  269. tags = ["red_circle"]
  270. });
  271. await Task.Delay(i * 60 * 1000);
  272. continue;
  273. }
  274. break;
  275. }
  276. var root = body.Convert2JsonElement();
  277. var success = root.Read<bool>("success");
  278. data = root.ElementRead("data");
  279. //{"code":601,"info":{"ok":false,"message":"nologin"}}
  280. if (!success && body.Contains("nologin"))
  281. {
  282. (success, string message) = RenewCookie();
  283. if (!success)
  284. {
  285. TkPoolCore.Disabled(_accountId, _accountName, $"{body}", _account.is_hide);
  286. }
  287. return (0, DateTime.MinValue, new List<DateTime>());
  288. }
  289. if (!success)
  290. {
  291. throw new APIException(body);
  292. }
  293. }
  294. catch (Exception ex)
  295. {
  296. throw new APIException(body);
  297. }
  298. using var conn = DBContext.GetOpenConnection();
  299. conn.Open();
  300. try
  301. {
  302. foreach (var order in data.ElementRead("result").EnumerateArray())
  303. {
  304. TkRefundOrderDetailDTO item = order.GetRawText().Convert2Object<TkRefundOrderDetailDTO>();
  305. // 处理每个订单数据
  306. item.accountId = _accountId;
  307. item.accountName = _company;
  308. if (item.ModifiedTime > max_modifiedTime) max_modifiedTime = item.ModifiedTime;
  309. if (last_modifiedTime != DateTime.MinValue && last_modifiedTime >= item.ModifiedTime)
  310. {
  311. return (total, max_modifiedTime, orderTimes);
  312. }
  313. //进行订单和转链匹配
  314. orderTimes.Add(item.TbTradeCreateTime.Date);
  315. switch (item.RefundStatus)
  316. {
  317. case 4:
  318. orderTimes.Add(item.RefundCreateTime.Date);
  319. break;
  320. case 2:
  321. case 3:
  322. orderTimes.Add(item.RefundFinishTime.Date);
  323. break;
  324. }
  325. if (item.ShowReturnFee == 0)
  326. {
  327. item.ShowReturnFee = Math.Round(item.PubShareFee / item.AlipayTotalPrice * item.RefundFee, 2);
  328. }
  329. int? id = conn.Replace(item);
  330. if (id != null)
  331. {
  332. item.id = (int)id;
  333. }
  334. total++;
  335. }
  336. }
  337. catch (Exception ex)
  338. {
  339. throw;
  340. }
  341. finally
  342. {
  343. conn.Dispose();
  344. }
  345. pageNo++;
  346. hasNext = data.Read<bool>("hasNext");
  347. positionIndex = data.Read<string>("positionIndex");
  348. if (sleep > 0) await Task.Delay(sleep);
  349. }
  350. return (total, max_modifiedTime, orderTimes);
  351. }
  352. }
  353. }