refactor: classify gateway task load
This commit is contained in:
parent
191ddc6ca4
commit
71bae611fc
@ -451,6 +451,11 @@ extension AppControllerDesktopThreadActions on AppController {
|
||||
final capturedLocalAttachments = List<CollaborationAttachment>.unmodifiable(
|
||||
localAttachments,
|
||||
);
|
||||
final taskLoadClass = classifyGatewayTaskLoadInternal(message);
|
||||
final taskMetadata = Map<String, dynamic>.unmodifiable(<String, dynamic>{
|
||||
...dispatch.metadata,
|
||||
'taskLoadClass': taskLoadClass,
|
||||
});
|
||||
final executionWorkingDirectory = gatewayExecutionWorkingDirectoryInternal(
|
||||
target: currentTarget,
|
||||
workingDirectory: workingDirectory,
|
||||
@ -475,7 +480,7 @@ extension AppControllerDesktopThreadActions on AppController {
|
||||
model: model,
|
||||
routing: routing,
|
||||
agentId: dispatch.agentId ?? '',
|
||||
metadata: Map<String, dynamic>.unmodifiable(dispatch.metadata),
|
||||
metadata: taskMetadata,
|
||||
resumeSessionHint: resumeSessionHint,
|
||||
appendUserTurn: appendUserTurn,
|
||||
),
|
||||
@ -500,7 +505,7 @@ extension AppControllerDesktopThreadActions on AppController {
|
||||
model: model,
|
||||
routing: routing,
|
||||
agentId: dispatch.agentId ?? '',
|
||||
metadata: Map<String, dynamic>.unmodifiable(dispatch.metadata),
|
||||
metadata: taskMetadata,
|
||||
resumeSessionHint: resumeSessionHint,
|
||||
appendUserTurn: appendUserTurn,
|
||||
),
|
||||
@ -672,11 +677,84 @@ extension AppControllerDesktopThreadActions on AppController {
|
||||
'6. The app syncs final artifacts from currentTaskWorkspace back into localWorkspace.',
|
||||
)
|
||||
..writeln()
|
||||
..writeln('Task load classification:')
|
||||
..writeln('- class: ${classifyGatewayTaskLoadInternal(requestText)}')
|
||||
..writeln(
|
||||
'- Gateway owns execution decomposition, scheduling, retries, and resumability for this class.',
|
||||
)
|
||||
..writeln()
|
||||
..writeln(
|
||||
'Available classes: short_task, long_task, complex_long_chain_task.',
|
||||
)
|
||||
..writeln();
|
||||
buffer
|
||||
..writeln('User request:')
|
||||
..write(requestText);
|
||||
return buffer.toString();
|
||||
}
|
||||
|
||||
String classifyGatewayTaskLoadInternal(String requestText) {
|
||||
final normalized = requestText.trim().toLowerCase();
|
||||
if (normalized.isEmpty) {
|
||||
return 'short_task';
|
||||
}
|
||||
final hasChapterSplit =
|
||||
normalized.contains('拆章节') ||
|
||||
normalized.contains('chapter') ||
|
||||
normalized.contains('章节');
|
||||
final hasAgentStage =
|
||||
normalized.contains('codex') ||
|
||||
normalized.contains('agent') ||
|
||||
normalized.contains('调用');
|
||||
final hasImageStage =
|
||||
normalized.contains('gpt images') ||
|
||||
normalized.contains('images2') ||
|
||||
normalized.contains('生成图') ||
|
||||
normalized.contains('图片');
|
||||
final hasPackagingStage =
|
||||
normalized.contains('汇总排版') ||
|
||||
normalized.contains('排版') ||
|
||||
normalized.contains('制作视频') ||
|
||||
normalized.contains('视频') ||
|
||||
normalized.contains('mp4');
|
||||
final hasChainArrows =
|
||||
normalized.contains('->') || normalized.contains('→');
|
||||
if (hasChapterSplit &&
|
||||
hasAgentStage &&
|
||||
hasImageStage &&
|
||||
hasPackagingStage &&
|
||||
hasChainArrows) {
|
||||
return 'complex_long_chain_task';
|
||||
}
|
||||
const longTaskMarkers = <String>[
|
||||
'生成文件',
|
||||
'产物',
|
||||
'附件',
|
||||
'图片提示词',
|
||||
'完整调研ppt',
|
||||
'markdown格式',
|
||||
'输出markdown',
|
||||
'ppt',
|
||||
'pptx',
|
||||
'powerpoint',
|
||||
'word',
|
||||
'docx',
|
||||
'png',
|
||||
'mp4',
|
||||
'jpg',
|
||||
'markdown',
|
||||
'.md',
|
||||
'image prompt',
|
||||
'artifacts',
|
||||
'downloadurl',
|
||||
];
|
||||
if (requestText.length >= 1200 ||
|
||||
longTaskMarkers.any(normalized.contains)) {
|
||||
return 'long_task';
|
||||
}
|
||||
return 'short_task';
|
||||
}
|
||||
|
||||
bool usesOpenClawGatewayQueueInternal(
|
||||
AssistantExecutionTarget target,
|
||||
SingleAgentProvider provider,
|
||||
|
||||
@ -1143,6 +1143,86 @@ void main() {
|
||||
);
|
||||
});
|
||||
|
||||
test(
|
||||
'sendChatMessage classifies complex artifact chains for Gateway',
|
||||
() async {
|
||||
final fakeGoTaskService = _RecordingGoTaskServiceClient();
|
||||
final controller = _connectedGatewayController(fakeGoTaskService);
|
||||
addTearDown(controller.dispose);
|
||||
|
||||
await controller.ensureActiveAssistantThreadInternal();
|
||||
await controller.setAssistantExecutionTarget(
|
||||
AssistantExecutionTarget.gateway,
|
||||
);
|
||||
await controller.sendChatMessage(
|
||||
'围绕\n\n'
|
||||
'从单机权限 → 网络边界 → Web安全 → 云身份 → Zero Trust → AI Agent 身份 → AI模型与知识保护 演进\n\n'
|
||||
'拆章节 -> 每章调用 Codex -> 每章 GPT images2 生成图 -> 汇总排版 -> 制作视频',
|
||||
);
|
||||
|
||||
expect(fakeGoTaskService.requests, hasLength(1));
|
||||
final request = fakeGoTaskService.requests.single;
|
||||
expect(request.metadata['taskLoadClass'], 'complex_long_chain_task');
|
||||
expect(request.prompt, contains('Task load classification:'));
|
||||
expect(request.prompt, contains('- class: complex_long_chain_task'));
|
||||
expect(
|
||||
request.prompt,
|
||||
contains(
|
||||
'Gateway owns execution decomposition, scheduling, retries, and resumability for this class.',
|
||||
),
|
||||
);
|
||||
expect(
|
||||
request.prompt,
|
||||
isNot(contains('First write the chapter breakdown')),
|
||||
);
|
||||
expect(
|
||||
request.prompt,
|
||||
isNot(contains('Run heavyweight stages in order')),
|
||||
);
|
||||
expect(
|
||||
request.prompt,
|
||||
contains('User request:\n围绕\n\n从单机权限 → 网络边界 → Web安全'),
|
||||
);
|
||||
},
|
||||
);
|
||||
|
||||
test(
|
||||
'sendChatMessage classifies simple Gateway prompts as short tasks',
|
||||
() async {
|
||||
final fakeGoTaskService = _RecordingGoTaskServiceClient();
|
||||
final controller = _connectedGatewayController(fakeGoTaskService);
|
||||
addTearDown(controller.dispose);
|
||||
|
||||
await controller.ensureActiveAssistantThreadInternal();
|
||||
await controller.setAssistantExecutionTarget(
|
||||
AssistantExecutionTarget.gateway,
|
||||
);
|
||||
await controller.sendChatMessage('写一段普通说明');
|
||||
|
||||
expect(fakeGoTaskService.requests, hasLength(1));
|
||||
final request = fakeGoTaskService.requests.single;
|
||||
expect(request.metadata['taskLoadClass'], 'short_task');
|
||||
expect(request.prompt, contains('- class: short_task'));
|
||||
},
|
||||
);
|
||||
|
||||
test('sendChatMessage classifies artifact output as a long task', () async {
|
||||
final fakeGoTaskService = _RecordingGoTaskServiceClient();
|
||||
final controller = _connectedGatewayController(fakeGoTaskService);
|
||||
addTearDown(controller.dispose);
|
||||
|
||||
await controller.ensureActiveAssistantThreadInternal();
|
||||
await controller.setAssistantExecutionTarget(
|
||||
AssistantExecutionTarget.gateway,
|
||||
);
|
||||
await controller.sendChatMessage('生成 Markdown 和 PNG 产物');
|
||||
|
||||
expect(fakeGoTaskService.requests, hasLength(1));
|
||||
final request = fakeGoTaskService.requests.single;
|
||||
expect(request.metadata['taskLoadClass'], 'long_task');
|
||||
expect(request.prompt, contains('- class: long_task'));
|
||||
});
|
||||
|
||||
test(
|
||||
'sendChatMessage runs Gateway task with remote workspace when local workspace is unavailable',
|
||||
() async {
|
||||
|
||||
Loading…
Reference in New Issue
Block a user