mirror of
https://github.com/twentyhq/twenty
synced 2026-04-21 13:37:22 +00:00
fix(ai-chat): replace hardcoded skill names with dynamic lookup in load_skills error
The load_skills tool error message hardcoded a static list of "available" skills regardless of what actually existed in the workspace. This caused the AI to retry loading nonexistent skills in a loop since the error falsely claimed they were available. https://claude.ai/code/session_01VYNqWTUP2dDJBHMhFjjCKe
This commit is contained in:
parent
086256eb8d
commit
21ddc2821c
5 changed files with 36 additions and 7 deletions
|
|
@ -83,7 +83,10 @@ describe('McpProtocolService', () => {
|
|||
},
|
||||
{
|
||||
provide: SkillService,
|
||||
useValue: { findFlatSkillsByNames: jest.fn().mockResolvedValue([]) },
|
||||
useValue: {
|
||||
findFlatSkillsByNames: jest.fn().mockResolvedValue([]),
|
||||
findAllFlatSkills: jest.fn().mockResolvedValue([]),
|
||||
},
|
||||
},
|
||||
],
|
||||
}).compile();
|
||||
|
|
|
|||
|
|
@ -148,8 +148,16 @@ export class McpProtocolService {
|
|||
inputSchema: executeToolInputSchema,
|
||||
},
|
||||
[LOAD_SKILL_TOOL_NAME]: {
|
||||
...createLoadSkillTool((names) =>
|
||||
this.skillService.findFlatSkillsByNames(names, workspace.id),
|
||||
...createLoadSkillTool(
|
||||
(names) =>
|
||||
this.skillService.findFlatSkillsByNames(names, workspace.id),
|
||||
async () => {
|
||||
const skills = await this.skillService.findAllFlatSkills(
|
||||
workspace.id,
|
||||
);
|
||||
|
||||
return skills.map((skill) => skill.name);
|
||||
},
|
||||
),
|
||||
inputSchema: zodSchema(loadSkillInputSchema),
|
||||
},
|
||||
|
|
|
|||
|
|
@ -18,6 +18,7 @@ export {
|
|||
LOAD_SKILL_TOOL_NAME,
|
||||
createLoadSkillTool,
|
||||
loadSkillInputSchema,
|
||||
type ListAvailableSkillNamesFunction,
|
||||
type LoadSkillFunction,
|
||||
type LoadSkillInput,
|
||||
type LoadSkillResult,
|
||||
|
|
|
|||
|
|
@ -24,8 +24,12 @@ export type LoadSkillResult = {
|
|||
};
|
||||
|
||||
export type LoadSkillFunction = (names: string[]) => Promise<FlatSkill[]>;
|
||||
export type ListAvailableSkillNamesFunction = () => Promise<string[]>;
|
||||
|
||||
export const createLoadSkillTool = (loadSkills: LoadSkillFunction) => ({
|
||||
export const createLoadSkillTool = (
|
||||
loadSkills: LoadSkillFunction,
|
||||
listAvailableSkillNames: ListAvailableSkillNamesFunction,
|
||||
) => ({
|
||||
description:
|
||||
'Load specialized skills for complex tasks. Returns detailed step-by-step instructions for building workflows, dashboards, manipulating data, or managing metadata. Call this before attempting complex operations.',
|
||||
inputSchema: loadSkillInputSchema,
|
||||
|
|
@ -35,9 +39,14 @@ export const createLoadSkillTool = (loadSkills: LoadSkillFunction) => ({
|
|||
const skills = await loadSkills(skillNames);
|
||||
|
||||
if (skills.length === 0) {
|
||||
const availableNames = await listAvailableSkillNames();
|
||||
|
||||
return {
|
||||
skills: [],
|
||||
message: `No skills found with names: ${skillNames.join(', ')}. Available skills: workflow-building, data-manipulation, dashboard-building, metadata-building, research, code-interpreter, xlsx, pdf, docx, pptx.`,
|
||||
message:
|
||||
availableNames.length > 0
|
||||
? `No skills found with names: ${skillNames.join(', ')}. Available skills: ${availableNames.join(', ')}.`
|
||||
: `No skills found with names: ${skillNames.join(', ')}. No skills are currently available.`,
|
||||
};
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -200,8 +200,16 @@ export class ChatExecutionService {
|
|||
toolContext,
|
||||
directTools,
|
||||
),
|
||||
[LOAD_SKILL_TOOL_NAME]: createLoadSkillTool((skillNames) =>
|
||||
this.skillService.findFlatSkillsByNames(skillNames, workspace.id),
|
||||
[LOAD_SKILL_TOOL_NAME]: createLoadSkillTool(
|
||||
(skillNames) =>
|
||||
this.skillService.findFlatSkillsByNames(skillNames, workspace.id),
|
||||
async () => {
|
||||
const skills = await this.skillService.findAllFlatSkills(
|
||||
workspace.id,
|
||||
);
|
||||
|
||||
return skills.map((skill) => skill.name);
|
||||
},
|
||||
),
|
||||
};
|
||||
|
||||
|
|
|
|||
Loading…
Reference in a new issue