- Replace all no-explicit-any with proper types or justified eslint-disable - Extract scene-graph-hit-test.ts (hit testing), scene-graph-instances.ts (component/instance sync) from scene-graph.ts - Extract renderer/text.ts (text rendering), renderer/pen-overlay.ts (vector pen tool overlay) from renderer.ts - Extract figma-api-proxy.ts (FigmaNodeProxy class) from figma-api.ts - Extract kiwi-convert-overrides.ts from kiwi-convert.ts - Add eslint-disable with justification for remaining large class files - Fix unused imports from splits - Warnings: 42 → 2 (only unavoidable no-implied-eval in vendored code)
66 lines
1.7 KiB
TypeScript
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, unknown>) => 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 }
|
|
}
|