openpencil/packages/core/src/tools/schema.ts
Danila Poyarkov 9784544f1f Clean up tools/schema, add geometry.ts, isMixed helper, fix imports, add tests
- Strip tools/schema.ts from 1831 to 65 lines (remove duplicate tool defs)
- Fix tools/index.ts to export ALL_TOOLS from registry instead of schema
- Fix renderJsx → renderJSX typo in tools/create.ts and structure.ts
- Add geometry.ts with shared rotation/coordinate math utilities
- Add isArrayMixed() helper to use-multi-props.ts, deduplicate FillSection/StrokeSection/EffectsSection
- Fix broken test imports: use @open-pencil/core instead of relative paths into packages/core/src/
- Merge duplicate import statements across all test files
- Export profiler internals and style-run helpers from core index.ts
- Add 6 new test files: color, undo, snap, vector, style-runs, text-editor (98 new tests)
- Update renderer-effects test for renderer/ directory split
2026-03-06 22:33:10 +03:00

66 lines
1.7 KiB
TypeScript

/**
* Tool definition schema.
*
* Each tool is defined once with typed params and an execute function
* that operates on FigmaAPI. Adapters for AI chat (valibot), CLI (citty),
* and MCP (JSON Schema) are generated from these definitions.
*/
import type { FigmaAPI, FigmaNodeProxy } from '../figma-api'
export type ParamType = 'string' | 'number' | 'boolean' | 'color' | 'string[]'
export interface ParamDef {
type: ParamType
description: string
required?: boolean
default?: unknown
enum?: string[]
min?: number
max?: number
}
export interface ToolDef {
name: string
description: string
mutates?: boolean
params: Record<string, ParamDef>
execute: (figma: FigmaAPI, args: Record<string, any>) => unknown
}
type ResolvedType<T extends ParamType> = T extends 'string'
? string
: T extends 'number'
? number
: T extends 'boolean'
? boolean
: T extends 'color'
? string
: T extends 'string[]'
? string[]
: never
type ResolvedParams<P extends Record<string, ParamDef>> = {
[K in keyof P as P[K]['required'] extends true ? K : never]: ResolvedType<P[K]['type']>
} & {
[K in keyof P as P[K]['required'] extends true ? never : K]?: ResolvedType<P[K]['type']>
}
export function defineTool<P extends Record<string, ParamDef>>(def: {
name: string
description: string
mutates?: boolean
params: P
execute: (figma: FigmaAPI, args: ResolvedParams<P>) => unknown
}): ToolDef {
return def as unknown as ToolDef
}
export function nodeToResult(node: FigmaNodeProxy): Record<string, unknown> {
return node.toJSON()
}
export function nodeSummary(node: FigmaNodeProxy): { id: string; name: string; type: string } {
return { id: node.id, name: node.name, type: node.type }
}