// Queries workstation tasks and prints them in the frozen output format the // Tela chat UI parses (see SKILL.md — do not change the shape of this output). import { resolveApiUrl } from './tela-api.ts' type TaskQueryResult = { taskId: string reference: number | null taskName: string status: string createdAt: string approvedAt: string | null output: Record | null } type QueryResponse = { data: TaskQueryResult[] meta: { totalCount: number currentPage: number totalPages: number } } const apiUrl = resolveApiUrl(process.argv[2]) const dataToken = process.env.DATA_TOKEN if (!dataToken) { console.error('DATA_TOKEN is required') process.exit(1) } const rawArgs = process.argv[3] if (!rawArgs) { console.error('Usage: bun run ./.claude/skills/workstation/query.ts \'{"promptApplicationId": "...", ...}\'') process.exit(1) } const query = JSON.parse(rawArgs) as Record const workstationId = String(query.promptApplicationId ?? query.agentId ?? '') const response = await fetch(`${apiUrl}/task/query`, { method: 'POST', headers: { 'x-data-token': dataToken, 'Content-Type': 'application/json', }, body: JSON.stringify(query), }) if (!response.ok) { console.error(`Query failed with status ${response.status}: ${await response.text()}`) process.exit(1) } const result = await response.json() as QueryResponse function extractedFields(output: TaskQueryResult['output']): Record { if (!output) { return {} } // Full outputContent comes as { content: {...} }; a `select` projection // comes back flat. const content = output.content if (content && typeof content === 'object' && !Array.isArray(content)) { return content as Record } return output } // Task text is user data: newlines in it could forge another task record in the parsed output. function oneLine(text: string): string { return text.replace(/\r?\n|\r/g, '\\n') } const lines: string[] = [ `Querying workstation: ${workstationId}`, `Found ${result.meta.totalCount} total tasks (showing ${result.data.length})`, `Page ${result.meta.currentPage} of ${Math.max(1, result.meta.totalPages)}`, '', ] for (const task of result.data) { lines.push(`--- Task: ${oneLine(task.taskName)}${task.reference ? ` (#${task.reference})` : ''} ---`) lines.push(` ID: ${task.taskId}`) lines.push(` Status: ${task.status}`) lines.push(` Created: ${task.createdAt}`) if (task.approvedAt) { lines.push(` Approved: ${task.approvedAt}`) } const fields = extractedFields(task.output) if (Object.keys(fields).length > 0) { lines.push(' Output:') for (const [key, value] of Object.entries(fields)) { lines.push(` ${oneLine(key)}: ${typeof value === 'string' ? oneLine(value) : JSON.stringify(value)}`) } } } process.stdout.write(`${lines.join('\n')}\n`)