mirror of
https://github.com/Abdulazizzn/n8n-enterprise-unlocked.git
synced 2026-09-05 01:56:33 +02:00
feat(editor): Improve manual description in nodes as tools (#15373)
This commit is contained in:
+5
-3
@@ -25,6 +25,10 @@ describe('createNodeAsTool', () => {
|
||||
description: {
|
||||
name: 'TestNode',
|
||||
description: 'Test node description',
|
||||
defaults: {
|
||||
name: 'Test Node',
|
||||
},
|
||||
properties: [],
|
||||
},
|
||||
});
|
||||
const node = mock<INode>({ name: 'Test_Node' });
|
||||
@@ -54,9 +58,7 @@ describe('createNodeAsTool', () => {
|
||||
|
||||
expect(tool).toBeDefined();
|
||||
expect(tool.name).toBe('Test_Node');
|
||||
expect(tool.description).toBe(
|
||||
'Test node description\n Resource: testResource\n Operation: testOperation',
|
||||
);
|
||||
expect(tool.description).toBe('testOperation testResource in Test Node');
|
||||
expect(tool.schema).toBeDefined();
|
||||
});
|
||||
|
||||
|
||||
+8
-27
@@ -1,6 +1,11 @@
|
||||
import { DynamicStructuredTool } from '@langchain/core/tools';
|
||||
import { generateZodSchema, NodeOperationError, traverseNodeParameters } from 'n8n-workflow';
|
||||
import type { IDataObject, INode, INodeType, FromAIArgument } from 'n8n-workflow';
|
||||
import {
|
||||
generateZodSchema,
|
||||
NodeOperationError,
|
||||
traverseNodeParameters,
|
||||
NodeHelpers,
|
||||
} from 'n8n-workflow';
|
||||
import { z } from 'zod';
|
||||
|
||||
export type CreateNodeAsToolOptions = {
|
||||
@@ -83,31 +88,6 @@ function getSchema(node: INode) {
|
||||
return z.object(schemaObj).required();
|
||||
}
|
||||
|
||||
/**
|
||||
* Generates a description for a node based on the provided parameters.
|
||||
* @param node The node type.
|
||||
* @param nodeParameters The parameters of the node.
|
||||
* @returns A string description for the node.
|
||||
*/
|
||||
function makeDescription(node: INode, nodeType: INodeType): string {
|
||||
if (node.parameters.descriptionType === 'auto') {
|
||||
const resource = node.parameters.resource as string;
|
||||
const operation = node.parameters.operation as string;
|
||||
let description = nodeType.description.description;
|
||||
if (resource) {
|
||||
description += `\n Resource: ${resource}`;
|
||||
}
|
||||
if (operation) {
|
||||
description += `\n Operation: ${operation}`;
|
||||
}
|
||||
return description.trim();
|
||||
}
|
||||
|
||||
// Users can define custom descriptions when `descriptionType` is manual or not included
|
||||
// in the node's properties, e.g. when the node has neither `operation` or `resource`
|
||||
return (node.parameters.toolDescription as string) ?? nodeType.description.description;
|
||||
}
|
||||
|
||||
/**
|
||||
* Converts a node name to a valid tool name by replacing special characters with underscores
|
||||
* and collapsing consecutive underscores into a single one.
|
||||
@@ -123,8 +103,9 @@ export function nodeNameToToolName(node: INode): string {
|
||||
*/
|
||||
function createTool(options: CreateNodeAsToolOptions) {
|
||||
const { node, nodeType, handleToolInvocation } = options;
|
||||
|
||||
const schema = getSchema(node);
|
||||
const description = makeDescription(node, nodeType);
|
||||
const description = NodeHelpers.getToolDescriptionForNode(node, nodeType);
|
||||
const nodeName = nodeNameToToolName(node);
|
||||
const name = nodeName || nodeType.description.name;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user