(component: ComponentDefinition)
| 219 | * - z.record(...) → { type: 'object', additionalProperties: {...} } |
| 220 | */ |
| 221 | export function getToolSchema(component: ComponentDefinition): ToolInputSchema { |
| 222 | const inputsSchema = component.inputs; |
| 223 | const parametersSchema = component.parameters; |
| 224 | |
| 225 | // 1. Generate full JSON Schema using Zod's built-in |
| 226 | const fullSchema = ( |
| 227 | inputsSchema as { toJSONSchema(): Record<string, unknown> } |
| 228 | ).toJSONSchema() as { |
| 229 | properties?: Record<string, unknown>; |
| 230 | required?: string[]; |
| 231 | }; |
| 232 | |
| 233 | // 2. Get action input IDs (credentials excluded) - reuse existing function! |
| 234 | const actionInputIds = getActionInputIds(component); |
| 235 | const exposedParamIds = getExposedParameterIds(component); |
| 236 | |
| 237 | // 3. Filter properties to only include action inputs |
| 238 | const filteredProperties = pick( |
| 239 | (fullSchema.properties ?? {}) as Record<string, unknown>, |
| 240 | actionInputIds |
| 241 | ); |
| 242 | |
| 243 | // 4. Filter required array |
| 244 | const filteredRequired = (fullSchema.required ?? []).filter((id: string) => |
| 245 | actionInputIds.includes(id) |
| 246 | ); |
| 247 | |
| 248 | // 5. Add descriptions from port metadata |
| 249 | const inputs = extractPorts(component.inputs); |
| 250 | for (const input of inputs) { |
| 251 | if (actionInputIds.includes(input.id)) { |
| 252 | const prop = filteredProperties[input.id] as Record<string, unknown> | undefined; |
| 253 | if (prop && !prop.description && (input.description ?? input.label)) { |
| 254 | prop.description = input.description ?? input.label; |
| 255 | } |
| 256 | } |
| 257 | } |
| 258 | |
| 259 | // 6. Use explicit inputSchema if provided (overrides inferred schema) |
| 260 | if (component.toolProvider?.inputSchema) { |
| 261 | const override = component.toolProvider.inputSchema; |
| 262 | // Merge or replace depending on needs - for now we just use it as is if provided |
| 263 | return override; |
| 264 | } |
| 265 | |
| 266 | // 7. Add exposed parameters (if any) |
| 267 | if (parametersSchema && exposedParamIds.length > 0) { |
| 268 | const paramSchema = ( |
| 269 | parametersSchema as { toJSONSchema(): Record<string, unknown> } |
| 270 | ).toJSONSchema() as { |
| 271 | properties?: Record<string, unknown>; |
| 272 | required?: string[]; |
| 273 | }; |
| 274 | |
| 275 | const paramProperties = pick( |
| 276 | (paramSchema.properties ?? {}) as Record<string, unknown>, |
| 277 | exposedParamIds |
| 278 | ); |
no test coverage detected