|
@@ -1,4 +1,4 @@
|
|
|
-using Aspose.Cells;
|
|
|
|
|
|
|
+using Aspose.Cells;
|
|
|
using Aspose.Words;
|
|
using Aspose.Words;
|
|
|
using Aspose.Words.Drawing;
|
|
using Aspose.Words.Drawing;
|
|
|
using Aspose.Words.Tables;
|
|
using Aspose.Words.Tables;
|
|
@@ -13850,7 +13850,7 @@ FROM
|
|
|
return Ok(jw);
|
|
return Ok(jw);
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
- Console.WriteLine(chat);
|
|
|
|
|
|
|
+ //Console.WriteLine(chat);
|
|
|
|
|
|
|
|
// var chatResult = await _doubaoService.CompleteChatAsync(new List<DouBaoChatMessage> { new DouBaoChatMessage { Role = DouBaoRole.user, Content = chat } });
|
|
// var chatResult = await _doubaoService.CompleteChatAsync(new List<DouBaoChatMessage> { new DouBaoChatMessage { Role = DouBaoRole.user, Content = chat } });
|
|
|
var apiResp = await _deepSeekService.ChatAsync(chat, false, "deepseek-reasoner", 0.7f, 60000);
|
|
var apiResp = await _deepSeekService.ChatAsync(chat, false, "deepseek-reasoner", 0.7f, 60000);
|
|
@@ -13875,6 +13875,180 @@ FROM
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
+ /// <summary>
|
|
|
|
|
+ /// 请示文件内容生成 (AI 流式输出)。响应体为 NDJSON:每行 <c>{"phase":"reasoning"|"content","text":"..."}</c>,分别对应思考过程与正式结果。
|
|
|
|
|
+ /// </summary>
|
|
|
|
|
+ /// <param name="dto"></param>
|
|
|
|
|
+ /// <returns></returns>
|
|
|
|
|
+ [HttpPost]
|
|
|
|
|
+ public async Task<IActionResult> BusinessInvitationInstructionsFileContentStream(BusinessInvitationInstructionsFileDto dto)
|
|
|
|
|
+ {
|
|
|
|
|
+ if (dto.Diid < 1)
|
|
|
|
|
+ {
|
|
|
|
|
+ Response.ContentType = "text/plain; charset=utf-8";
|
|
|
|
|
+ await Response.WriteAsync("团组Id不能为空!");
|
|
|
|
|
+ return new EmptyResult();
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ var groupInfo = await _sqlSugar.Queryable<Grp_DelegationInfo>().FirstAsync(x => x.IsDel == 0 && x.Id == dto.Diid);
|
|
|
|
|
+ if (groupInfo == null)
|
|
|
|
|
+ {
|
|
|
|
|
+ Response.ContentType = "text/plain; charset=utf-8";
|
|
|
|
|
+ await Response.WriteAsync("团组信息不存在!");
|
|
|
|
|
+ return new EmptyResult();
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ var DeleClientList = _sqlSugar.Queryable<Grp_TourClientList>()
|
|
|
|
|
+ .LeftJoin<Crm_DeleClient>((tcl, dc) => tcl.ClientId == dc.Id && dc.IsDel == 0)
|
|
|
|
|
+ .LeftJoin<Crm_CustomerCompany>((tcl, dc, cc) => dc.CrmCompanyId == cc.Id && dc.IsDel == 0)
|
|
|
|
|
+ .Where((tcl, dc, cc) => tcl.IsDel == 0 && tcl.DiId == dto.Diid)
|
|
|
|
|
+ .Select((tcl, dc, cc) => new ClientInfo
|
|
|
|
|
+ {
|
|
|
|
|
+ LastName = dc.LastName,
|
|
|
|
|
+ FirstName = dc.FirstName,
|
|
|
|
|
+ Sex = dc.Sex,
|
|
|
|
|
+ Birthday = dc.BirthDay,
|
|
|
|
|
+ Company = cc.CompanyFullName,
|
|
|
|
|
+ Job = dc.Job
|
|
|
|
|
+ })
|
|
|
|
|
+ .ToList();
|
|
|
|
|
+ foreach (var item in DeleClientList)
|
|
|
|
|
+ {
|
|
|
|
|
+ EncryptionProcessor.DecryptProperties(item);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ if (!DeleClientList.Any())
|
|
|
|
|
+ {
|
|
|
|
|
+ Response.ContentType = "text/plain; charset=utf-8";
|
|
|
|
|
+ await Response.WriteAsync("团组客户信息不存在!");
|
|
|
|
|
+ return new EmptyResult();
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ var travelList = await _sqlSugar.Queryable<Grp_ApprovalTravel>()
|
|
|
|
|
+ .LeftJoin<Grp_ApprovalTravelDetails>((x, a) => x.Id == a.ParentId && a.IsDel == 0)
|
|
|
|
|
+ .Where((x, a) => x.IsDel == 0 && x.Diid == dto.Diid)
|
|
|
|
|
+ .Select((x, a) => new
|
|
|
|
|
+ {
|
|
|
|
|
+ 日期 = x.Date,
|
|
|
|
|
+ 具体时间 = a.Time,
|
|
|
|
|
+ 行程安排 = a.Details,
|
|
|
|
|
+ 数据id = a.Id,
|
|
|
|
|
+ })
|
|
|
|
|
+ .ToListAsync();
|
|
|
|
|
+
|
|
|
|
|
+ if (!travelList.Any())
|
|
|
|
|
+ {
|
|
|
|
|
+ Response.ContentType = "text/plain; charset=utf-8";
|
|
|
|
|
+ await Response.WriteAsync("团组行程信息不存在!");
|
|
|
|
|
+ return new EmptyResult();
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ string chat = string.Empty;
|
|
|
|
|
+
|
|
|
|
|
+ var templateSetting = await _sqlSugar.Queryable<Sys_SetData>().FirstAsync(x => x.Id == 1550 && x.IsDel == 0);
|
|
|
|
|
+ if (templateSetting != null && !string.IsNullOrEmpty(templateSetting.Remark))
|
|
|
|
|
+ {
|
|
|
|
|
+ var stringFormatResp = await GeneralMethod.StringFormatAsync(new StringFormatDto
|
|
|
|
|
+ {
|
|
|
|
|
+ FormatTemplate = templateSetting.Remark,
|
|
|
|
|
+ Parameters = new List<string> {
|
|
|
|
|
+ JsonConvert.SerializeObject(DeleClientList),
|
|
|
|
|
+ JsonConvert.SerializeObject(travelList)
|
|
|
|
|
+ }
|
|
|
|
|
+ });
|
|
|
|
|
+
|
|
|
|
|
+ if (stringFormatResp.Success)
|
|
|
|
|
+ {
|
|
|
|
|
+ chat = stringFormatResp.FormattedResult;
|
|
|
|
|
+ }
|
|
|
|
|
+ else
|
|
|
|
|
+ {
|
|
|
|
|
+ Response.ContentType = "text/plain; charset=utf-8";
|
|
|
|
|
+ await Response.WriteAsync("对话内容模板格式化失败! templateSetting.Id: " + templateSetting.Id + ",错误:" + stringFormatResp.Message);
|
|
|
|
|
+ return new EmptyResult();
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+ else
|
|
|
|
|
+ {
|
|
|
|
|
+ Response.ContentType = "text/plain; charset=utf-8";
|
|
|
|
|
+ await Response.WriteAsync("获取对话内容模板失败! templateSetting.Id: " + (templateSetting?.Id.ToString() ?? "无"));
|
|
|
|
|
+ return new EmptyResult();
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ //Console.WriteLine(chat);
|
|
|
|
|
+ Response.ContentType = "application/x-ndjson; charset=utf-8";
|
|
|
|
|
+ Response.Headers["Cache-Control"] = "no-cache";
|
|
|
|
|
+
|
|
|
|
|
+ string NdjsonLine(DeepSeekStreamChunk c) => JsonConvert.SerializeObject(new
|
|
|
|
|
+ {
|
|
|
|
|
+ phase = c.Phase == DeepSeekStreamPhase.Reasoning ? "reasoning" : "content",
|
|
|
|
|
+ text = c.Text
|
|
|
|
|
+ });
|
|
|
|
|
+
|
|
|
|
|
+ try
|
|
|
|
|
+ {
|
|
|
|
|
+ await foreach (var chunk in _deepSeekService.ChatStreamAsync(chat, "deepseek-reasoner", 0.7f, 60000))
|
|
|
|
|
+ {
|
|
|
|
|
+ await Response.WriteAsync(NdjsonLine(chunk) + "\n");
|
|
|
|
|
+ await Response.Body.FlushAsync();
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+ catch (Exception ex)
|
|
|
|
|
+ {
|
|
|
|
|
+ await Response.WriteAsync(JsonConvert.SerializeObject(new { phase = "error", text = ex.Message }) + "\n");
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ return new EmptyResult();
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ /// <summary>
|
|
|
|
|
+ /// 请示文件下载
|
|
|
|
|
+ /// </summary>
|
|
|
|
|
+ /// <param name="dto"></param>
|
|
|
|
|
+ /// <returns></returns>
|
|
|
|
|
+ [HttpPost]
|
|
|
|
|
+ [ProducesResponseType(typeof(JsonView), StatusCodes.Status200OK)]
|
|
|
|
|
+ public async Task<IActionResult> BusinessInvitationInstructionsFileDown(BusinessInvitationInstructionsFileDownDto dto)
|
|
|
|
|
+ {
|
|
|
|
|
+ var jw = JsonView(false);
|
|
|
|
|
+ var content = dto.Content;
|
|
|
|
|
+ var diid = dto.Diid;
|
|
|
|
|
+
|
|
|
|
|
+ if (string.IsNullOrEmpty(content))
|
|
|
|
|
+ {
|
|
|
|
|
+ jw.Msg = "请示文件内容不能为空!";
|
|
|
|
|
+ return Ok(jw);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ var groupInfo = await _sqlSugar.Queryable<Grp_DelegationInfo>().FirstAsync(x => x.IsDel == 0 && x.Id == diid);
|
|
|
|
|
+ if (groupInfo == null)
|
|
|
|
|
+ {
|
|
|
|
|
+ jw.Msg = "团组信息不存在!";
|
|
|
|
|
+ return Ok(jw);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ string outputPath = $"{AppSettingsHelper.Get("GrpFileBasePath")}/商邀相关文件/{groupInfo.TeamName}请示文件.docx";
|
|
|
|
|
+
|
|
|
|
|
+ try
|
|
|
|
|
+ {
|
|
|
|
|
+ string json = content;
|
|
|
|
|
+ byte[] wordBytes = JsonToWordHelper.ConvertJsonToWord(json);
|
|
|
|
|
+ System.IO.File.WriteAllBytes(outputPath, wordBytes);
|
|
|
|
|
+
|
|
|
|
|
+ //WordExporter.MarkdownToWord(chatResult, outputPath);
|
|
|
|
|
+ string url = outputPath.Replace(AppSettingsHelper.Get("GrpFileBasePath"), AppSettingsHelper.Get("GrpFileBaseUrl") + AppSettingsHelper.Get("GrpFileFtpPath"));
|
|
|
|
|
+
|
|
|
|
|
+ return Ok(JsonView(true, "请示文件生成成功!", url));
|
|
|
|
|
+ }
|
|
|
|
|
+ catch (Exception ex)
|
|
|
|
|
+ {
|
|
|
|
|
+ jw.Msg = "请示文件生成失败!" + ex.Message;
|
|
|
|
|
+ return Ok(jw);
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+
|
|
|
|
|
+
|
|
|
// [HttpPost("export-word")]
|
|
// [HttpPost("export-word")]
|
|
|
// public IActionResult ExportWord([FromBody] string json)
|
|
// public IActionResult ExportWord([FromBody] string json)
|
|
|
// {
|
|
// {
|
|
@@ -14087,13 +14261,19 @@ FROM
|
|
|
[HttpGet("chat-stream")]
|
|
[HttpGet("chat-stream")]
|
|
|
public async Task ChatStream([FromQuery] string question)
|
|
public async Task ChatStream([FromQuery] string question)
|
|
|
{
|
|
{
|
|
|
- Response.ContentType = "text/plain; charset=utf-8";
|
|
|
|
|
|
|
+ Response.ContentType = "application/x-ndjson; charset=utf-8";
|
|
|
Response.Headers.CacheControl = "no-cache";
|
|
Response.Headers.CacheControl = "no-cache";
|
|
|
|
|
|
|
|
|
|
+ string NdjsonLine(DeepSeekStreamChunk c) => JsonConvert.SerializeObject(new
|
|
|
|
|
+ {
|
|
|
|
|
+ phase = c.Phase == DeepSeekStreamPhase.Reasoning ? "reasoning" : "content",
|
|
|
|
|
+ text = c.Text
|
|
|
|
|
+ });
|
|
|
|
|
+
|
|
|
await foreach (var chunk in _deepSeekService.ChatStreamAsync(question))
|
|
await foreach (var chunk in _deepSeekService.ChatStreamAsync(question))
|
|
|
{
|
|
{
|
|
|
- await Response.WriteAsync(chunk);
|
|
|
|
|
- await Response.Body.FlushAsync(); // 尽快把本段发给客户端(视反向代理是否缓冲而定)
|
|
|
|
|
|
|
+ await Response.WriteAsync(NdjsonLine(chunk) + "\n");
|
|
|
|
|
+ await Response.Body.FlushAsync();
|
|
|
}
|
|
}
|
|
|
}
|
|
}
|
|
|
|
|
|