TestController.cs 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409
  1. using System.Collections.Concurrent;
  2. using System.Data;
  3. using System.IO;
  4. using DotNetCore.CAP;
  5. using Fw.Utility.Client;
  6. using Google.Protobuf.WellKnownTypes;
  7. using Hotline.Ai.Visit;
  8. using Hotline.Application.ExportExcel;
  9. using Hotline.CallCenter.BlackLists;
  10. using Hotline.CallCenter.Calls;
  11. using Hotline.CallCenter.Devices;
  12. using Hotline.CallCenter.Ivrs;
  13. using Hotline.FlowEngine.WorkflowModules;
  14. using Hotline.FlowEngine.Workflows;
  15. using Hotline.Identity.Roles;
  16. using Hotline.Import;
  17. using Hotline.Orders;
  18. using Hotline.Realtimes;
  19. using Hotline.Repository.SqlSugar;
  20. using Hotline.Repository.SqlSugar.Ts;
  21. using Hotline.Settings.TimeLimits;
  22. using Hotline.Share.Dtos.FlowEngine;
  23. using Hotline.Share.Dtos.Realtime;
  24. using Hotline.Share.Enums.Settings;
  25. using Hotline.Share.Mq;
  26. using Hotline.Users;
  27. using MediatR;
  28. using Microsoft.AspNetCore.Authorization;
  29. using Microsoft.AspNetCore.Components.Routing;
  30. using Microsoft.AspNetCore.Http;
  31. using Microsoft.AspNetCore.Mvc;
  32. using Microsoft.AspNetCore.Routing.Template;
  33. using Microsoft.Extensions.Options;
  34. using MiniExcelLibs;
  35. using NewRock.Sdk;
  36. using NewRock.Sdk.Security;
  37. using SqlSugar;
  38. using SqlSugar.SplitTableExtensions;
  39. using Tr.Sdk;
  40. using XC.RSAUtil;
  41. using XF.Domain.Authentications;
  42. using XF.Domain.Cache;
  43. using XF.Domain.Entities;
  44. using XF.Domain.Exceptions;
  45. using XF.Domain.Filters;
  46. using XF.Domain.Locks;
  47. using XF.Domain.Queues;
  48. using XF.Domain.Repository;
  49. using XF.EasyCaching;
  50. namespace Hotline.Api.Controllers;
  51. /// <summary>
  52. ///
  53. /// </summary>
  54. [AllowAnonymous]
  55. public class TestController : BaseController
  56. {
  57. private readonly ILogger<TestController> _logger;
  58. private readonly IAuthorizeGenerator _authorizeGenerator;
  59. private readonly IOptionsSnapshot<CallCenterConfiguration> _options;
  60. private readonly ISessionContext _sessionContext;
  61. private readonly IRepository<User> _userRepository;
  62. private readonly ITypedCache<User> _cache;
  63. private readonly IRealtimeService _realtimeService;
  64. private readonly IBlacklistDomainService _blacklistDomainService;
  65. private readonly IIvrDomainService _ivrDomainService;
  66. private readonly ISugarUnitOfWork<HotlineDbContext> _uow;
  67. private readonly IRepository<Role> _roleRepository;
  68. private readonly IMediator _mediator;
  69. private readonly IDistributedLock _distributedLock;
  70. private readonly IRepository<OrderUrge> _orderUrgeRepository;
  71. private readonly IRepositoryTextSearch<OrderTs> _repositoryts;
  72. private readonly ITimeLimitDomainService _timeLimitDomainService;
  73. private readonly IWfModuleDomainService _wfModuleDomainService;
  74. private readonly IDaySettingRepository _daySettingRepository;
  75. private readonly ITrClient _trClient;
  76. private readonly ICapPublisher _capPublisher;
  77. private readonly IQueue _queue;
  78. private readonly IExportApplication _exportApplication;
  79. private readonly IAiVisitService _aiVisitService;
  80. private readonly IRepository<WorkflowTrace> _workflowTraceRepository;
  81. private readonly IRepository<WorkflowStepHandler> _workflowStepHandleRepository;
  82. //private readonly ITypedCache<List<User>> _cache;
  83. //private readonly ICacheManager<User> _cache;
  84. public TestController(
  85. INewRockClient client,
  86. ILogger<TestController> logger,
  87. IAuthorizeGenerator authorizeGenerator,
  88. IOptionsSnapshot<CallCenterConfiguration> options,
  89. ISessionContext sessionContext,
  90. IRepository<User> userRepository,
  91. //ICacheManager<User> cache
  92. //ITypedCache<List<User>> cache
  93. ITypedCache<User> cache,
  94. IRealtimeService realtimeService,
  95. IBlacklistDomainService blacklistDomainService,
  96. IIvrDomainService ivrDomainService,
  97. ISugarUnitOfWork<HotlineDbContext> uow,
  98. IRepository<Role> roleRepository,
  99. IMediator mediator,
  100. IDistributedLock distributedLock,
  101. IRepository<OrderUrge> orderUrgeRepository,
  102. IRepositoryTextSearch<OrderTs> repositoryts,
  103. ITimeLimitDomainService timeLimitDomainService,
  104. IWfModuleDomainService wfModuleDomainService,
  105. IDaySettingRepository daySettingRepository,
  106. ITrClient trClient,
  107. ICapPublisher capPublisher,
  108. IQueue queue,
  109. IExportApplication exportApplication,
  110. IAiVisitService aiVisitService,
  111. IRepository<WorkflowTrace> workflowTraceRepository,
  112. IRepository<WorkflowStepHandler> workflowStepHandleRepository)
  113. {
  114. _logger = logger;
  115. _authorizeGenerator = authorizeGenerator;
  116. _options = options;
  117. _sessionContext = sessionContext;
  118. _userRepository = userRepository;
  119. _cache = cache;
  120. _realtimeService = realtimeService;
  121. _blacklistDomainService = blacklistDomainService;
  122. _ivrDomainService = ivrDomainService;
  123. _uow = uow;
  124. _roleRepository = roleRepository;
  125. _mediator = mediator;
  126. _distributedLock = distributedLock;
  127. _orderUrgeRepository = orderUrgeRepository;
  128. _repositoryts = repositoryts;
  129. _timeLimitDomainService = timeLimitDomainService;
  130. _wfModuleDomainService = wfModuleDomainService;
  131. _daySettingRepository = daySettingRepository;
  132. _trClient = trClient;
  133. _capPublisher = capPublisher;
  134. _queue = queue;
  135. _exportApplication = exportApplication;
  136. _aiVisitService = aiVisitService;
  137. _workflowTraceRepository = workflowTraceRepository;
  138. _workflowStepHandleRepository = workflowStepHandleRepository;
  139. }
  140. [HttpGet("testo")]
  141. public async Task<OpenResponse> TestOrigin()
  142. {
  143. var now = DateTime.Now.ToString();
  144. return OpenResponse.Ok(now);
  145. }
  146. [HttpPost("import")]
  147. [AllowAnonymous]
  148. public async Task<List<ExcelContent>> Import(IFormFile file)
  149. {
  150. //var FileName = file.FileName;
  151. //var fileExtension = Path.GetExtension(FileName);
  152. ////新文件名
  153. //var newFileName = DateTime.Now.ToString("yyyyMMddhhmmss");
  154. ////文件保存路径
  155. //var filePath = Path.Combine(Directory.GetCurrentDirectory(), "wwwroot", "Upload", newFileName);
  156. ////判断路径是否存在
  157. //if (!Directory.Exists(filePath))
  158. //{
  159. // //创建路径
  160. // Directory.CreateDirectory(filePath);
  161. //}
  162. //filePath = Path.Combine(filePath, newFileName+ fileExtension);
  163. using (var stream = new MemoryStream())
  164. {
  165. file.CopyTo(stream);
  166. var list = MiniExcel.Query<ExcelContent>(stream).ToList();
  167. //Directory.Delete(filePath, true);
  168. return list;
  169. }
  170. }
  171. [AllowAnonymous]
  172. [HttpGet("export")]
  173. public async Task<object> Export()
  174. {
  175. List<ExcelContent> list = new List<ExcelContent>();
  176. ExcelContent excelContent = new ExcelContent() { ExternalId = "123123" };
  177. list.Add(excelContent);
  178. return _exportApplication.ExportData<ExcelContent>(list, "demo.xlsx");
  179. }
  180. [HttpGet("time")]
  181. [AllowAnonymous]
  182. public async Task<OpenResponse> GetTime(string batchId, string taskId)
  183. {
  184. //await _repositoryts.AddVectorAsync("f595e730-909a-45e4-9138-a84bf15f4662", DateTime.Now,
  185. // new List<string> { "xx", "bb" }, HttpContext.RequestAborted);
  186. //var result = await _repositoryts.SearchAsync(new List<string> { "bb" }, HttpContext.RequestAborted);
  187. //await _repositoryts.UpdateVectorAsync("f595e730-909a-45e4-9138-a84bf15f4662",
  188. // new List<string> { "ss", "bb" }, HttpContext.RequestAborted);
  189. //_uow.Db.Ado.SqlQueryAsync<OrderUrge>("SELECT to_tsvector('fat cats ate fat rats') @@ to_tsquery('fat & rat')")
  190. //var tests = _uowWex.Db.Ado.SqlQuery<Test>("select * from view_telinfo_full where IsSynch=@IsSynch", new { IsSynch = 0 });
  191. //var a = _uowWex.Db.Ado.ExecuteCommand("update telinfo set IsSynch=1 where GUID=@CallId", new { CallId = "b1f97f3c-88b6-4f42-b8de-83ed448854b0" });
  192. //var rsp = await _wexClient.QueryTelsAsync(new QueryTelRequest { }, HttpContext.RequestAborted);
  193. //int a = _timeLimitDomainService.CalcWorkTime(DateTime.Now, DateTime.Parse("2023-09-11 16:21:00"));
  194. //int m = _timeLimitDomainService.CalcWorkTime(DateTime.Parse("2023-09-19 12:00:00"), DateTime.Parse("2023-09-20 18:00:00"), false);
  195. //var r = _timeLimitDomainService.CalcEndTime(DateTime.Parse("2024-03-07 14:09:45"), ETimeType.WorkDay,1,false,80);
  196. //var r = _timeLimitDomainService.CalcExpiredTime(DateTime.Parse("2024-02-29 10:12:33"), Share.Enums.FlowEngine.EFlowDirection.OrgToCenter, "10");
  197. //await _wfModuleDomainService.PersistenceModulesAsync(HttpContext.RequestAborted);
  198. //var rsp = await _daprClient.InvokeMethodAsync<ApiResponse<string>>(HttpMethod.Get, "identity", "api/v1/Test/time", HttpContext.RequestAborted);
  199. //var rsp1 = await _daprClient.InvokeMethodAsync<int, ApiResponse<string>>(HttpMethod.Post, "identity", "api/v1/Test/time1", 222, HttpContext.RequestAborted);
  200. //var a = await _trClient.QueryTelsAsync(new Tr.Sdk.Tels.QueryTelRequest() { }, HttpContext.RequestAborted);
  201. //await _daySettingRepository.IsWorkDay(DateTime.Now);
  202. //var r = _timeLimitDomainService.CalcWorkTime(DateTime.Parse("2024-3-22 05:00:00"), DateTime.Parse("2024-3-22 06:00:00"), false);
  203. //var r = _timeLimitDomainService.CalcWorkTime(DateTime.Parse("2024-3-24 17:20:00"), DateTime.Parse("2024-3-24 17:21:00"), false);
  204. //await _aiVisitService.QueryAiVisitTask(batchId, taskId, HttpContext.RequestAborted);
  205. var r = _timeLimitDomainService.CalcWorkTimeReduce(DateTime.Now, 5);
  206. return OpenResponse.Ok(DateTime.Now.ToString("F"));
  207. }
  208. [HttpGet("pgsql")]
  209. public async Task<string> Pgsql()
  210. {
  211. var role = new Role
  212. {
  213. Name = $"test_role_{TimeOnly.FromDateTime(DateTime.Now)}",
  214. DisplayName = "test_role_display",
  215. ClientId = "test"
  216. };
  217. var roleId = await _roleRepository.AddAsync(role, HttpContext.RequestAborted);
  218. role.Description = "Description";
  219. await _roleRepository.UpdateAsync(role, HttpContext.RequestAborted);
  220. return roleId;
  221. }
  222. [AllowAnonymous]
  223. [HttpGet("roles")]
  224. public async Task<List<Role>> GetRoles()
  225. {
  226. using var lockManager = new LockManager(_distributedLock, $"{nameof(TestController)}.{nameof(GetRoles)}");
  227. lockManager.InvokeInLock(() => { Console.WriteLine("do something"); }, TimeSpan.FromSeconds(10));
  228. await lockManager.InvokeInLockAsync(
  229. d => _roleRepository.Queryable(includeDeleted: true).ToListAsync(),
  230. TimeSpan.FromSeconds(10),
  231. HttpContext.RequestAborted);
  232. var a = await _roleRepository.Queryable()
  233. //.Where(d => !d.IsDeleted)
  234. .ToListAsync();
  235. //var a = await db.Queryable<Role>().ToListAsync();
  236. var b = await _roleRepository.Queryable(includeDeleted: true).ToListAsync();
  237. return a;
  238. }
  239. //[AllowAnonymous]
  240. [HttpGet("hash")]
  241. public async Task Hash()
  242. {
  243. var s = _sessionContext;
  244. }
  245. /// <summary>
  246. /// signalR测试(method: Ring)
  247. /// </summary>
  248. /// <returns></returns>
  249. [HttpGet("ring")]
  250. public async Task RingTest()
  251. {
  252. await _realtimeService.RingAsync(_sessionContext.RequiredUserId,
  253. new RingDto { Id = new Guid().ToString(), From = _sessionContext.Phone ?? "未知号码", To = "12345" },
  254. HttpContext.RequestAborted);
  255. }
  256. /// <summary>
  257. /// signalR测试(method: Answered)
  258. /// </summary>
  259. /// <returns></returns>
  260. [HttpGet("answered")]
  261. public async Task AnsweredTest()
  262. {
  263. await _realtimeService.AnsweredAsync(_sessionContext.RequiredUserId,
  264. new AnsweredDto() { Id = new Guid().ToString(), From = _sessionContext.Phone ?? "未知号码", To = "12345" },
  265. HttpContext.RequestAborted);
  266. }
  267. /// <summary>
  268. /// signalR测试(method: Bye)
  269. /// </summary>
  270. /// <returns></returns>
  271. [HttpGet("bye")]
  272. public async Task ByeTest()
  273. {
  274. await _realtimeService.ByeAsync(_sessionContext.RequiredUserId, new ByeDto() { Id = new Guid().ToString() },
  275. HttpContext.RequestAborted);
  276. }
  277. /// <summary>
  278. ///
  279. /// </summary>
  280. /// <returns></returns>
  281. [AllowAnonymous]
  282. [HttpGet("t2")]
  283. public async Task GetVoiceEndAnswerAsyncTest()
  284. {
  285. //var answer = await _ivrDomainService.GetVoiceEndAnswerAsync("3", HttpContext.RequestAborted);
  286. //Console.WriteLine(answer.Content);
  287. throw new UserFriendlyException(2001, "test");
  288. }
  289. [HttpGet("wfdefine")]
  290. public async Task GetWorkflowDefine([FromQuery] string id)
  291. {
  292. var query = _workflowTraceRepository.Queryable()
  293. .LeftJoin<Workflow>((t, w) => t.WorkflowId == w.Id)
  294. .LeftJoin<Order>((t, w, o) => w.ExternalId == o.Id)
  295. .Where((t, w, o) => o.No.Length == 14);
  296. if (!string.IsNullOrEmpty(id))
  297. query = query.Where(d => d.WorkflowId == id);
  298. var list = await query
  299. .Select((t, w, o) => new { t, w, o })
  300. .ToListAsync(HttpContext.RequestAborted);
  301. var toUsers = list.Where(d => d.t.FlowAssignType == EFlowAssignType.User).ToList();
  302. var userIds = toUsers.SelectMany(d => d.t.Handlers).Select(d => d.Key).Distinct().ToList();
  303. var users = await _userRepository.Queryable()
  304. .Includes(d => d.Organization)
  305. .Where(d => userIds.Contains(d.Id))
  306. .ToListAsync(HttpContext.RequestAborted);
  307. //var orgTraces = list.Where(d => d.FlowAssignType == EFlowAssignType.Org).ToList();
  308. var stepHandlers = new List<WorkflowStepHandler>();
  309. foreach (var toUser in toUsers)
  310. {
  311. foreach (var traceHandler in toUser.t.Handlers)
  312. {
  313. var user = users.FirstOrDefault(d => d.Id == traceHandler.Key);
  314. if (user != null)
  315. stepHandlers.Add(new WorkflowStepHandler
  316. {
  317. WorkflowId = toUser.w.Id,
  318. ExternalId = toUser.w.ExternalId,
  319. WorkflowStepId = toUser.t.StepId,
  320. FlowAssignType = toUser.t.FlowAssignType.Value,
  321. UserId = user.Id,
  322. Username = user.Name,
  323. OrgId = user.OrgId,
  324. OrgName = user.Organization.Name,
  325. IsActualHandler = user.Id == toUser.t.HandlerId
  326. });
  327. }
  328. }
  329. var toOrgs = list.Where(d => d.t.FlowAssignType == EFlowAssignType.Org).ToList();
  330. foreach (var toOrg in toOrgs)
  331. {
  332. foreach (var handler in toOrg.t.Handlers)
  333. {
  334. stepHandlers.Add(new WorkflowStepHandler
  335. {
  336. WorkflowId = toOrg.w.Id,
  337. ExternalId = toOrg.w.ExternalId,
  338. WorkflowStepId = toOrg.t.StepId,
  339. FlowAssignType = toOrg.t.FlowAssignType.Value,
  340. OrgId = handler.Key,
  341. OrgName = handler.Value,
  342. IsActualHandler = handler.Key == toOrg.t.HandlerOrgId
  343. });
  344. }
  345. }
  346. _logger.LogInformation($"生成handlers: {stepHandlers.Count} 条");
  347. await _workflowStepHandleRepository.AddRangeAsync(stepHandlers, HttpContext.RequestAborted);
  348. }
  349. [AllowAnonymous]
  350. [HttpPost("t3")]
  351. public Task<int> TestDaprPubsub(int data)
  352. {
  353. _logger.LogDebug("receive dapr event, params: {0}", data);
  354. return Task.FromResult(data);
  355. }
  356. [HttpGet("rsa")]
  357. public async Task<string> Rsa()
  358. {
  359. var keyList = RsaKeyGenerator.Pkcs1Key(2048, true);
  360. var privateKey = keyList[0];
  361. var publicKey = keyList[1];
  362. return $"{publicKey} \r\n {privateKey}";
  363. }
  364. }