|
|
@@ -0,0 +1,137 @@
|
|
|
+package com.zsjz.ai.module.agent.service;
|
|
|
+
|
|
|
+import com.zsjz.ai.module.agent.WorkspaceManagerFactory;
|
|
|
+import com.zsjz.ai.module.agent.config.EtlProperties;
|
|
|
+import com.zsjz.ai.module.agent.followup.FollowupService;
|
|
|
+import com.zsjz.ai.module.agent.intent.IntentService;
|
|
|
+import com.zsjz.ai.module.agent.mapper.AgentChatSessionMapper;
|
|
|
+import com.zsjz.ai.module.agent.mapper.AgentModelMapper;
|
|
|
+import com.zsjz.ai.module.agent.mapper.SqlQueryMapper;
|
|
|
+import com.zsjz.ai.module.agent.python.PythonExecutor;
|
|
|
+import com.zsjz.ai.module.agent.rag.RagSchemaService;
|
|
|
+import com.zsjz.ai.module.agent.sql.SqlResultStore;
|
|
|
+import com.zsjz.ai.module.agent.tools.AgentToolRegistry;
|
|
|
+import com.zsjz.ai.module.call.service.CallContinuousService;
|
|
|
+import com.zsjz.ai.module.call.service.CallNightService;
|
|
|
+import com.zsjz.ai.module.call.service.CallRecordService;
|
|
|
+import com.zsjz.ai.module.call.service.CallSensitiveService;
|
|
|
+import com.zsjz.ai.module.dm.ai.FileAiProfileService;
|
|
|
+import com.zsjz.ai.module.graph.service.GraphService;
|
|
|
+import com.zsjz.ai.module.person.service.DataProfileService;
|
|
|
+import com.zsjz.ai.module.person.service.IntimacyService;
|
|
|
+import com.zsjz.ai.module.person.service.PersonBasicInfoService;
|
|
|
+import com.zsjz.ai.module.person.service.PersonGroupService;
|
|
|
+import com.zsjz.ai.module.plat.mapper.CaseInfoMapper;
|
|
|
+import com.zsjz.ai.module.plat.mapper.TableFieldMapper;
|
|
|
+import com.zsjz.ai.module.plat.mapper.TableInfoMapper;
|
|
|
+import com.zsjz.ai.module.track.service.TrackCellTowerService;
|
|
|
+import com.zsjz.ai.module.track.service.TrackEnLocalService;
|
|
|
+import com.zsjz.ai.module.track.service.TrackExpressInfoService;
|
|
|
+import com.zsjz.ai.module.track.service.TrackMeetService;
|
|
|
+import com.zsjz.ai.module.track.service.TrackTogetherLiveService;
|
|
|
+import com.zsjz.ai.module.track.service.TrackTogetherTravelService;
|
|
|
+import com.zsjz.ai.module.trans.service.TransBigService;
|
|
|
+import com.zsjz.ai.module.trans.service.TransCardHoldService;
|
|
|
+import com.zsjz.ai.module.trans.service.TransCashFlowService;
|
|
|
+import com.zsjz.ai.module.trans.service.TransContinuousService;
|
|
|
+import com.zsjz.ai.module.trans.service.TransFastFundFlowService;
|
|
|
+import com.zsjz.ai.module.trans.service.TransFinancialService;
|
|
|
+import com.zsjz.ai.module.trans.service.TransFixedDepositService;
|
|
|
+import com.zsjz.ai.module.trans.service.TransFrequencyService;
|
|
|
+import com.zsjz.ai.module.trans.service.TransFundFlowService;
|
|
|
+import com.zsjz.ai.module.trans.service.TransRecordService;
|
|
|
+import com.zsjz.ai.module.trans.service.TransSensitiveService;
|
|
|
+import io.agentscope.core.tool.Toolkit;
|
|
|
+import org.junit.jupiter.api.DisplayName;
|
|
|
+import org.junit.jupiter.api.Test;
|
|
|
+
|
|
|
+import java.util.HashSet;
|
|
|
+import java.util.List;
|
|
|
+import java.util.Optional;
|
|
|
+import java.util.Set;
|
|
|
+import java.util.stream.Collectors;
|
|
|
+
|
|
|
+import static org.junit.jupiter.api.Assertions.assertEquals;
|
|
|
+import static org.junit.jupiter.api.Assertions.assertFalse;
|
|
|
+import static org.junit.jupiter.api.Assertions.assertNotNull;
|
|
|
+import static org.junit.jupiter.api.Assertions.assertTrue;
|
|
|
+import static org.mockito.Mockito.mock;
|
|
|
+
|
|
|
+/**
|
|
|
+ * 「插件与技能」页的工具清单契约:清单必须来自 <b>agent 自己</b>的工具装配。
|
|
|
+ *
|
|
|
+ * <p>守两件事:
|
|
|
+ * <ol>
|
|
|
+ * <li>枚举用具全部组激活,否则未激活组的工具不进 schema,页面上会「少工具」;</li>
|
|
|
+ * <li>基础工具({@code execute_sql} 等)与业务工具的分界正确 ——
|
|
|
+ * 这份清单不依赖 MCP(MCP 只服务外部客户端,与 agent 有什么工具是两件事)。</li>
|
|
|
+ * </ol>
|
|
|
+ */
|
|
|
+class AgentCapabilityToolkitTest {
|
|
|
+
|
|
|
+ private static AgentService agentService() {
|
|
|
+ AgentToolRegistry registry = new AgentToolRegistry(
|
|
|
+ mock(SqlResultStore.class),
|
|
|
+ mock(CallRecordService.class), mock(CallNightService.class),
|
|
|
+ mock(CallContinuousService.class), mock(CallSensitiveService.class),
|
|
|
+ mock(TransBigService.class), mock(TransCardHoldService.class),
|
|
|
+ mock(TransCashFlowService.class), mock(TransContinuousService.class),
|
|
|
+ mock(TransFastFundFlowService.class), mock(TransFinancialService.class),
|
|
|
+ mock(TransFixedDepositService.class), mock(TransFrequencyService.class),
|
|
|
+ mock(TransFundFlowService.class), mock(TransRecordService.class),
|
|
|
+ mock(TransSensitiveService.class),
|
|
|
+ mock(TrackCellTowerService.class), mock(TrackEnLocalService.class),
|
|
|
+ mock(TrackExpressInfoService.class), mock(TrackMeetService.class),
|
|
|
+ mock(TrackTogetherLiveService.class), mock(TrackTogetherTravelService.class),
|
|
|
+ mock(GraphService.class),
|
|
|
+ mock(DataProfileService.class), mock(IntimacyService.class),
|
|
|
+ mock(PersonBasicInfoService.class), mock(PersonGroupService.class),
|
|
|
+ mock(FileAiProfileService.class));
|
|
|
+ return new AgentService(
|
|
|
+ mock(AgentModelFactory.class),
|
|
|
+ mock(AgentModelMapper.class),
|
|
|
+ Optional.empty(),
|
|
|
+ mock(RagSchemaService.class),
|
|
|
+ mock(EtlProperties.class),
|
|
|
+ mock(IntentService.class),
|
|
|
+ mock(FollowupService.class),
|
|
|
+ mock(SqlQueryMapper.class),
|
|
|
+ mock(SqlResultStore.class),
|
|
|
+ mock(TableInfoMapper.class),
|
|
|
+ mock(TableFieldMapper.class),
|
|
|
+ mock(PythonExecutor.class),
|
|
|
+ mock(AgentChatSessionMapper.class),
|
|
|
+ mock(CaseInfoMapper.class),
|
|
|
+ new WorkspaceManagerFactory(),
|
|
|
+ registry);
|
|
|
+ }
|
|
|
+
|
|
|
+ @Test
|
|
|
+ @DisplayName("能力清单:业务组全激活、每组可取到,基础工具与业务工具分界正确")
|
|
|
+ void capabilityToolkitExposesEverything() {
|
|
|
+ Toolkit toolkit = agentService().buildCapabilityToolkit();
|
|
|
+
|
|
|
+ Set<String> businessNames = new HashSet<>();
|
|
|
+ for (String group : AgentToolRegistry.registeredGroupNames()) {
|
|
|
+ assertNotNull(toolkit.getToolGroup(group), "组取不到: " + group);
|
|
|
+ businessNames.addAll(toolkit.getToolGroup(group).getTools());
|
|
|
+ }
|
|
|
+ // 全组激活:67 个业务工具都应在 schema 里(默认只装备 person 时会只剩 24 个)
|
|
|
+ Set<String> schemaNames = toolkit.getToolSchemas().stream()
|
|
|
+ .map(schema -> schema.getName())
|
|
|
+ .collect(Collectors.toSet());
|
|
|
+ assertTrue(schemaNames.containsAll(businessNames),
|
|
|
+ "有业务工具没进 schema,页面上会看不到它们");
|
|
|
+ assertEquals(67, businessNames.size(), "业务工具总数");
|
|
|
+
|
|
|
+ // 基础工具:不属于任何业务组、会话里始终可用(mocked 环境下 RAG/Python 视为不可用)
|
|
|
+ Set<String> baseNames = schemaNames.stream()
|
|
|
+ .filter(name -> !businessNames.contains(name))
|
|
|
+ .collect(Collectors.toSet());
|
|
|
+ assertTrue(baseNames.contains("execute_sql"), "SQL 工具应属于基础工具: " + baseNames);
|
|
|
+ assertTrue(baseNames.contains("get_current_workspace"), "工作区查询应属于基础工具");
|
|
|
+ assertFalse(baseNames.contains("list_person_names"), "业务工具不该被算进基础工具");
|
|
|
+ // 元工具由 builder.enableMetaTool(true) 注册,不在这份枚举容器里
|
|
|
+ assertFalse(baseNames.contains("reset_equipped_tools"));
|
|
|
+ }
|
|
|
+}
|