refactor(work-service,print-worker): 优化代码结构与错误处理
1. 提取评分prompt构建逻辑减少重复代码 2. 移除冗余的参考答案图片循环逻辑 3. 重构打印服务的错误回调逻辑,统一失败处理流程 4. 新增打印服务的任务取消处理逻辑
This commit is contained in:
@ -47,10 +47,11 @@ public class AutoDotCodeConsumer(
|
||||
|
||||
using var scope = scopeFactory.CreateScope();
|
||||
var dbContext = scope.ServiceProvider.GetRequiredService<ISqlSugarClient>();
|
||||
JournalPagePrintDto? request = null;
|
||||
|
||||
try
|
||||
{
|
||||
var request = JsonSerializer.Deserialize<JournalPagePrintDto>(message, new JsonSerializerOptions
|
||||
request = JsonSerializer.Deserialize<JournalPagePrintDto>(message, new JsonSerializerOptions
|
||||
{
|
||||
PropertyNameCaseInsensitive = true
|
||||
});
|
||||
@ -72,6 +73,7 @@ public class AutoDotCodeConsumer(
|
||||
if (string.IsNullOrWhiteSpace(journalPdfKey))
|
||||
{
|
||||
logger.LogError("书籍上传 PDF 文件地址为空,JournalId: {JournalId}", request.JournalId);
|
||||
await TryCallbackCodeFailAsync(request, cancellationToken);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -79,6 +81,7 @@ public class AutoDotCodeConsumer(
|
||||
if (pdfStream == null)
|
||||
{
|
||||
logger.LogError("获取书籍上传 PDF 文件失败,OSS Key: {OssKey}", journalPdfKey);
|
||||
await TryCallbackCodeFailAsync(request, cancellationToken);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -93,6 +96,7 @@ public class AutoDotCodeConsumer(
|
||||
if (dotFile == null)
|
||||
{
|
||||
logger.LogError("配置打印数据错误,点阵文件不存在,DotId: {DotId}", dotId);
|
||||
await TryCallbackCodeFailAsync(request, cancellationToken);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -101,7 +105,7 @@ public class AutoDotCodeConsumer(
|
||||
if (!File.Exists(exePath))
|
||||
{
|
||||
logger.LogError("PrintTool.exe 不存在,路径:{ExePath}", exePath);
|
||||
await ExecuteUpdateJournalStatusAsync(BuildFailResponse(request), cancellationToken);
|
||||
await TryCallbackCodeFailAsync(request, cancellationToken);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -109,7 +113,7 @@ public class AutoDotCodeConsumer(
|
||||
if (!File.Exists(xmlPath))
|
||||
{
|
||||
logger.LogError("铺码授权文件不存在,路径:{XmlPath}", xmlPath);
|
||||
await ExecuteUpdateJournalStatusAsync(BuildFailResponse(request), cancellationToken);
|
||||
await TryCallbackCodeFailAsync(request, cancellationToken);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -126,7 +130,7 @@ public class AutoDotCodeConsumer(
|
||||
if (dotFileDetailList.Count < pageNumMax)
|
||||
{
|
||||
logger.LogError("点阵页码余量不足,DotId: {DotId}, Need: {Need}, Available: {Available}", dotId, pageNumMax, dotFileDetailList.Count);
|
||||
await ExecuteUpdateJournalStatusAsync(BuildFailResponse(request), cancellationToken);
|
||||
await TryCallbackCodeFailAsync(request, cancellationToken);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -138,7 +142,7 @@ public class AutoDotCodeConsumer(
|
||||
if (printResult.Timeout || printResult.ExitCode != 0)
|
||||
{
|
||||
logger.LogError("执行 PrintTool.exe 失败,退出码:{ExitCode},错误信息:{ErrorMessage}", printResult.ExitCode, printResult.Error);
|
||||
await ExecuteUpdateJournalStatusAsync(BuildFailResponse(request, dotFileDetailPageName), cancellationToken);
|
||||
await TryCallbackCodeFailAsync(request, cancellationToken, dotFileDetailPageName);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -150,8 +154,7 @@ public class AutoDotCodeConsumer(
|
||||
|
||||
if (!ValidatePrintOutput(printResult.Output, dotFileDetailPageName, dPrint))
|
||||
{
|
||||
statusModel.Status = JournalStatusEnum.CodeFail;
|
||||
await ExecuteUpdateJournalStatusAsync(statusModel, cancellationToken);
|
||||
await TryCallbackCodeFailAsync(request, cancellationToken, dotFileDetailPageName);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -192,10 +195,18 @@ public class AutoDotCodeConsumer(
|
||||
logger.LogError("回调接口修改书籍状态失败,JournalId: {JournalId},接口返回消息:{Message}", statusModel.JournalId, callbackResponse.Message);
|
||||
}
|
||||
}
|
||||
catch (OperationCanceledException) when (cancellationToken.IsCancellationRequested)
|
||||
{
|
||||
logger.LogWarning("自动铺码处理已取消,JournalId: {JournalId}", request?.JournalId);
|
||||
throw;
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
logger.LogError(ex, "自动铺码处理失败");
|
||||
throw;
|
||||
if (request != null)
|
||||
{
|
||||
await TryCallbackCodeFailAsync(request, CancellationToken.None);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -298,6 +309,26 @@ public class AutoDotCodeConsumer(
|
||||
return new CallbackUpdateJournalStatusResponse();
|
||||
}
|
||||
|
||||
private async Task TryCallbackCodeFailAsync(JournalPagePrintDto request, CancellationToken cancellationToken, string[]? pageNo = null)
|
||||
{
|
||||
try
|
||||
{
|
||||
var callbackResponse = await ExecuteUpdateJournalStatusAsync(BuildFailResponse(request, pageNo), cancellationToken);
|
||||
if (!callbackResponse.IsSuccess)
|
||||
{
|
||||
logger.LogError("回调接口修改书籍为铺码失败状态失败,JournalId: {JournalId},接口返回消息:{Message}", request.JournalId, callbackResponse.Message);
|
||||
}
|
||||
}
|
||||
catch (OperationCanceledException) when (cancellationToken.IsCancellationRequested)
|
||||
{
|
||||
throw;
|
||||
}
|
||||
catch (Exception callbackEx)
|
||||
{
|
||||
logger.LogError(callbackEx, "铺码失败后请求回调接口失败,JournalId: {JournalId}", request.JournalId);
|
||||
}
|
||||
}
|
||||
|
||||
private static JournalPagePrintDto BuildFailResponse(JournalPagePrintDto request, string[]? pageNo = null)
|
||||
{
|
||||
return new JournalPagePrintDto
|
||||
|
||||
@ -233,13 +233,14 @@ public class JournalTaskReceiveConsumer(
|
||||
{
|
||||
throw new InvalidOperationException("AI聊天服务配置不完整,请检查 AiChat 配置节点");
|
||||
}
|
||||
|
||||
var answerMapPrompt = BuildScorePrompt(scoreUnit, referenceAnswerMap);
|
||||
logger.LogInformation(answerMapPrompt);
|
||||
var content = new List<object>
|
||||
{
|
||||
new
|
||||
{
|
||||
type = "text",
|
||||
text = BuildScorePrompt(scoreUnit, referenceAnswerMap)
|
||||
text = answerMapPrompt
|
||||
}
|
||||
};
|
||||
|
||||
@ -251,7 +252,7 @@ public class JournalTaskReceiveConsumer(
|
||||
content.Add(new
|
||||
{
|
||||
type = "text",
|
||||
text = $"以下为任务 {context.Task.Id} 的学生作答图片,共 {answerImages.Count} 张。"
|
||||
text = $"以下是学生作答图片,共 {answerImages.Count} 张。"
|
||||
});
|
||||
|
||||
foreach (var answerImage in answerImages)
|
||||
@ -269,31 +270,6 @@ public class JournalTaskReceiveConsumer(
|
||||
throw new InvalidOperationException($"评分单元 {scoreUnit.GroupId} 缺少答案图片");
|
||||
}
|
||||
|
||||
foreach (var context in scoreUnit.Questions)
|
||||
{
|
||||
referenceAnswerMap.TryGetValue(context.Task.Id, out var referenceAnswers);
|
||||
var referenceAnswerImages = await BuildReferenceAnswerImageContentsAsync(context.Task.Id, referenceAnswers ?? [], cancellationToken);
|
||||
if (referenceAnswerImages.Count == 0)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
content.Add(new
|
||||
{
|
||||
type = "text",
|
||||
text = $"以下为任务 {context.Task.Id} 的参考答案图片,共 {referenceAnswerImages.Count} 张。参考答案不是必有,评分时以题目Prompt和学生答案为主。"
|
||||
});
|
||||
|
||||
foreach (var referenceAnswerImage in referenceAnswerImages)
|
||||
{
|
||||
content.Add(new
|
||||
{
|
||||
type = "image_url",
|
||||
image_url = new { url = referenceAnswerImage.DataUrl }
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
var requestBody = new
|
||||
{
|
||||
model,
|
||||
@ -403,6 +379,7 @@ public class JournalTaskReceiveConsumer(
|
||||
prompt.AppendLine(" \"Completion\": 100,");
|
||||
prompt.AppendLine(" \"Result\": \"50字内的中文评语\"");
|
||||
prompt.AppendLine("}");
|
||||
|
||||
return prompt.ToString();
|
||||
}
|
||||
|
||||
|
||||
@ -1,4 +1,4 @@
|
||||
<Project Sdk="Microsoft.NET.Sdk.Web">
|
||||
<Project Sdk="Microsoft.NET.Sdk.Web">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFramework>net8.0</TargetFramework>
|
||||
|
||||
Reference in New Issue
Block a user