@zhanngning/hecode 0.5.0 → 0.6.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +3 -0
- package/dist/index.js +12 -9
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
- package/skills/content/SKILL.md +77 -0
- package/skills/data-analysis/SKILL.md +76 -0
- package/skills/translate/SKILL.md +75 -0
package/README.md
CHANGED
|
@@ -148,6 +148,9 @@ Hecode uses a skill-based architecture to handle different tasks. Each skill pro
|
|
|
148
148
|
| `refactor` | refactor, 重构, optimize, 优化, improve, clean | Improve code quality while preserving behavior |
|
|
149
149
|
| `security` | security, 安全, vulnerability, 漏洞, audit | Identify and fix security vulnerabilities |
|
|
150
150
|
| `perf` | performance, 性能, optimize, speed, slow, benchmark | Performance optimization |
|
|
151
|
+
| `content` | content, 内容, 文章, article, blog, 博客, 公众号 | Content creation for various platforms |
|
|
152
|
+
| `data-analysis` | data, 数据, analysis, 分析, chart, 图表, visualization | Data analysis and visualization |
|
|
153
|
+
| `translate` | translate, 翻译, 英文, 中文, english, chinese | Translation between languages |
|
|
151
154
|
| `ppt` | ppt, presentation, slides, 演示, 幻灯片, 汇报 | Create professional presentations |
|
|
152
155
|
| `planning` | plan, planning, project, roadmap, 项目, 计划, 规划 | Create project plans and roadmaps |
|
|
153
156
|
| `finance` | finance, 股票, 金融, 研究报告, stock | Financial analysis and research reports |
|
package/dist/index.js
CHANGED
|
@@ -5,8 +5,9 @@ import {
|
|
|
5
5
|
|
|
6
6
|
// src/cli/commands.ts
|
|
7
7
|
import { Command } from "commander";
|
|
8
|
-
import {
|
|
9
|
-
import { join as join5 } from "path";
|
|
8
|
+
import { readFileSync } from "fs";
|
|
9
|
+
import { join as join5, dirname } from "path";
|
|
10
|
+
import { fileURLToPath } from "url";
|
|
10
11
|
|
|
11
12
|
// src/cli/config.ts
|
|
12
13
|
import { readFile, mkdir, writeFile } from "fs/promises";
|
|
@@ -503,17 +504,19 @@ function handleCommand(input, orchestrator, session) {
|
|
|
503
504
|
}
|
|
504
505
|
|
|
505
506
|
// src/cli/commands.ts
|
|
506
|
-
|
|
507
|
+
function getVersion() {
|
|
507
508
|
try {
|
|
508
|
-
const
|
|
509
|
-
const
|
|
509
|
+
const __filename = fileURLToPath(import.meta.url);
|
|
510
|
+
const __dirname = dirname(__filename);
|
|
511
|
+
const pkgPath = join5(__dirname, "../../package.json");
|
|
512
|
+
const pkg = JSON.parse(readFileSync(pkgPath, "utf-8"));
|
|
510
513
|
return pkg.version;
|
|
511
514
|
} catch {
|
|
512
|
-
return "0.
|
|
515
|
+
return "0.6.0";
|
|
513
516
|
}
|
|
514
517
|
}
|
|
515
|
-
|
|
516
|
-
const version =
|
|
518
|
+
function createProgram() {
|
|
519
|
+
const version = getVersion();
|
|
517
520
|
const program2 = new Command();
|
|
518
521
|
program2.name("hecode").description("Hecode \u2014 Your AI Coding Assistant CLI").version(version).option("-m, --model <model>", "Model to use (e.g. openai:gpt-4o, claude:sonnet)").option("-s, --skill <skill>", "Skill to activate").argument("[prompt...]", "Single-shot prompt (non-interactive)").action(async (prompt, opts) => {
|
|
519
522
|
const config = await loadConfig();
|
|
@@ -539,6 +542,6 @@ async function createProgram() {
|
|
|
539
542
|
}
|
|
540
543
|
|
|
541
544
|
// src/index.ts
|
|
542
|
-
var program =
|
|
545
|
+
var program = createProgram();
|
|
543
546
|
program.parse();
|
|
544
547
|
//# sourceMappingURL=index.js.map
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/cli/commands.ts","../src/cli/config.ts","../src/models/openai.ts","../src/models/anthropic.ts","../src/models/ollama.ts","../src/models/factory.ts","../src/cli/repl.ts","../src/memory/session.ts","../src/skills/loader.ts","../src/index.ts"],"sourcesContent":["import { Command } from \"commander\";\nimport { readFile } from \"node:fs/promises\";\nimport { join } from \"node:path\";\nimport { loadConfig } from \"./config.js\";\nimport { createProvider, parseModelString } from \"../models/factory.js\";\nimport { startREPL } from \"./repl.js\";\n\nasync function getVersion(): Promise<string> {\n try {\n const pkgPath = join(import.meta.dirname, \"../../package.json\");\n const pkg = JSON.parse(await readFile(pkgPath, \"utf-8\"));\n return pkg.version;\n } catch {\n return \"0.0.0\";\n }\n}\n\nexport async function createProgram(): Promise<Command> {\n const version = await getVersion();\n const program = new Command();\n\n program\n .name(\"hecode\")\n .description(\"Hecode — Your AI Coding Assistant CLI\")\n .version(version)\n .option(\"-m, --model <model>\", \"Model to use (e.g. openai:gpt-4o, claude:sonnet)\")\n .option(\"-s, --skill <skill>\", \"Skill to activate\")\n .argument(\"[prompt...]\", \"Single-shot prompt (non-interactive)\")\n .action(async (prompt: string[], opts: { model?: string; skill?: string }) => {\n const config = await loadConfig();\n const modelStr = opts.model ?? config.defaultModel;\n const { provider, model } = parseModelString(modelStr);\n const modelConfig = config.models[provider] ?? {};\n if (model) modelConfig.model = model;\n const modelProvider = createProvider(provider, modelConfig as Record<string, unknown>);\n\n if (prompt.length) {\n const { Orchestrator } = await import(\"../core/orchestrator.js\");\n const orch = new Orchestrator({ model: modelProvider });\n const result = await orch.run(prompt.join(\" \"));\n console.log(result);\n } else {\n await startREPL(modelProvider, { skillName: opts.skill });\n }\n });\n\n program\n .command(\"config\")\n .description(\"Show or edit configuration\")\n .action(async () => {\n const config = await loadConfig();\n console.log(JSON.stringify(config, null, 2));\n });\n\n return program;\n}\n","import { readFile, mkdir, writeFile } from \"node:fs/promises\";\nimport { join } from \"node:path\";\nimport { homedir } from \"node:os\";\nimport type { Config } from \"../core/types.js\";\n\nconst CONFIG_DIR = join(homedir(), \".hecode\");\nconst CONFIG_FILE = join(CONFIG_DIR, \"config.json\");\n\nexport async function loadConfig(): Promise<Config> {\n try {\n const raw = await readFile(CONFIG_FILE, \"utf-8\");\n return JSON.parse(raw);\n } catch {\n return { defaultModel: \"openai:gpt-4o\", models: {} };\n }\n}\n\nexport async function saveConfig(config: Config): Promise<void> {\n await mkdir(CONFIG_DIR, { recursive: true });\n await writeFile(CONFIG_FILE, JSON.stringify(config, null, 2), \"utf-8\");\n}\n","import OpenAI from \"openai\";\nimport type { ModelProvider, Message, Tool, Response, Chunk } from \"../core/types.js\";\n\nexport class OpenAIProvider implements ModelProvider {\n name = \"openai\";\n private client: OpenAI;\n private model: string;\n\n constructor(config: { apiKey?: string; baseUrl?: string; model?: string }) {\n this.client = new OpenAI({\n apiKey: config.apiKey ?? process.env.OPENAI_API_KEY,\n baseURL: config.baseUrl,\n });\n this.model = config.model ?? \"gpt-4o\";\n }\n\n async chat(messages: Message[], tools?: Tool[]): Promise<Response> {\n const params: OpenAI.ChatCompletionCreateParams = {\n model: this.model,\n messages: this.convertMessages(messages),\n ...(tools?.length && { tools: this.convertTools(tools) }),\n };\n const completion = await this.client.chat.completions.create(params);\n const choice = completion.choices[0]!;\n return {\n content: choice.message.content ?? \"\",\n tool_calls: choice.message.tool_calls\n ?.filter((tc) => tc.type === \"function\")\n .map((tc) => ({\n id: tc.id,\n type: \"function\" as const,\n function: { name: tc.function.name, arguments: tc.function.arguments },\n })),\n usage: completion.usage\n ? { prompt: completion.usage.prompt_tokens, completion: completion.usage.completion_tokens }\n : undefined,\n };\n }\n\n async *stream(messages: Message[], tools?: Tool[]): AsyncIterable<Chunk> {\n const stream = await this.client.chat.completions.create({\n model: this.model,\n messages: this.convertMessages(messages),\n stream: true,\n ...(tools?.length && { tools: this.convertTools(tools) }),\n });\n for await (const chunk of stream) {\n const delta = chunk.choices[0]?.delta;\n if (!delta) continue;\n yield {\n content: delta.content ?? undefined,\n tool_calls: delta.tool_calls?.map((tc) => ({\n id: tc.id ?? \"\",\n type: \"function\" as const,\n function: { name: tc.function?.name ?? \"\", arguments: tc.function?.arguments ?? \"\" },\n })),\n done: chunk.choices[0]?.finish_reason != null,\n };\n }\n }\n\n private convertMessages(messages: Message[]): OpenAI.ChatCompletionMessageParam[] {\n return messages.map((m) => {\n if (m.role === \"tool\") {\n return { role: \"tool\" as const, content: m.content, tool_call_id: m.tool_call_id! };\n }\n if (m.role === \"assistant\" && m.tool_calls?.length) {\n return {\n role: \"assistant\" as const,\n content: m.content,\n tool_calls: m.tool_calls.map((tc) => ({\n id: tc.id,\n type: \"function\" as const,\n function: tc.function,\n })),\n };\n }\n return { role: m.role as \"system\" | \"user\" | \"assistant\", content: m.content };\n });\n }\n\n private convertTools(tools: Tool[]): OpenAI.ChatCompletionTool[] {\n return tools.map((t) => ({\n type: \"function\" as const,\n function: { name: t.name, description: t.description, parameters: t.parameters },\n }));\n }\n}\n","import Anthropic from \"@anthropic-ai/sdk\";\nimport type { ModelProvider, Message, Tool, Response, Chunk } from \"../core/types.js\";\n\nexport class AnthropicProvider implements ModelProvider {\n name = \"anthropic\";\n private client: Anthropic;\n private model: string;\n\n constructor(config: { apiKey?: string; model?: string }) {\n this.client = new Anthropic({ apiKey: config.apiKey ?? process.env.ANTHROPIC_API_KEY });\n this.model = config.model ?? \"claude-sonnet-4-20250514\";\n }\n\n async chat(messages: Message[], tools?: Tool[]): Promise<Response> {\n const system = messages.find((m) => m.role === \"system\")?.content ?? \"\";\n const convMessages = messages.filter((m) => m.role !== \"system\");\n const params: Anthropic.MessageCreateParams = {\n model: this.model,\n max_tokens: 8192,\n system,\n messages: this.convertMessages(convMessages),\n ...(tools?.length && { tools: this.convertTools(tools) }),\n };\n const msg = await this.client.messages.create(params);\n const textBlock = msg.content.find((b) => b.type === \"text\");\n const toolBlocks = msg.content.filter((b) => b.type === \"tool_use\");\n return {\n content: textBlock?.text ?? \"\",\n tool_calls: toolBlocks.map((tb) => ({\n id: tb.id,\n type: \"function\" as const,\n function: { name: tb.name, arguments: JSON.stringify(tb.input) },\n })),\n usage: { prompt: msg.usage.input_tokens, completion: msg.usage.output_tokens },\n };\n }\n\n async *stream(messages: Message[], tools?: Tool[]): AsyncIterable<Chunk> {\n const system = messages.find((m) => m.role === \"system\")?.content ?? \"\";\n const convMessages = messages.filter((m) => m.role !== \"system\");\n const stream = this.client.messages.stream({\n model: this.model,\n max_tokens: 8192,\n system,\n messages: this.convertMessages(convMessages),\n ...(tools?.length && { tools: this.convertTools(tools) }),\n });\n for await (const event of stream) {\n if (event.type === \"content_block_delta\" && event.delta.type === \"text_delta\") {\n yield { content: event.delta.text, done: false };\n }\n }\n yield { content: undefined, done: true };\n }\n\n private convertMessages(messages: Message[]): Anthropic.MessageParam[] {\n return messages.map((m) => ({\n role: m.role === \"assistant\" ? \"assistant\" : \"user\",\n content: m.content,\n }));\n }\n\n private convertTools(tools: Tool[]): Anthropic.Tool[] {\n return tools.map((t) => ({\n name: t.name,\n description: t.description,\n input_schema: t.parameters as Anthropic.Tool[\"input_schema\"],\n }));\n }\n}\n","import type { ModelProvider, Message, Tool, Response, Chunk } from \"../core/types.js\";\n\nexport class OllamaProvider implements ModelProvider {\n name = \"ollama\";\n private baseUrl: string;\n private model: string;\n\n constructor(config: { baseUrl?: string; model?: string }) {\n this.baseUrl = config.baseUrl ?? \"http://localhost:11434\";\n this.model = config.model ?? \"llama3.1\";\n }\n\n async chat(messages: Message[], tools?: Tool[]): Promise<Response> {\n const res = await fetch(`${this.baseUrl}/api/chat`, {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify({\n model: this.model,\n messages: messages.map((m) => ({ role: m.role, content: m.content })),\n stream: false,\n ...(tools?.length && { tools: this.convertTools(tools) }),\n }),\n });\n const data = (await res.json()) as any;\n return {\n content: data.message?.content ?? \"\",\n tool_calls: data.message?.tool_calls?.map((tc: any, i: number) => ({\n id: `call_${i}`,\n type: \"function\" as const,\n function: {\n name: tc.function?.name ?? \"\",\n arguments: JSON.stringify(tc.function?.arguments ?? {}),\n },\n })),\n };\n }\n\n async *stream(messages: Message[], tools?: Tool[]): AsyncIterable<Chunk> {\n const res = await fetch(`${this.baseUrl}/api/chat`, {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify({\n model: this.model,\n messages: messages.map((m) => ({ role: m.role, content: m.content })),\n stream: true,\n ...(tools?.length && { tools: this.convertTools(tools) }),\n }),\n });\n const reader = res.body!.getReader();\n const decoder = new TextDecoder();\n let buffer = \"\";\n while (true) {\n const { done, value } = await reader.read();\n if (done) break;\n buffer += decoder.decode(value, { stream: true });\n const lines = buffer.split(\"\\n\");\n buffer = lines.pop()!;\n for (const line of lines) {\n if (!line.trim()) continue;\n const data = JSON.parse(line);\n yield {\n content: data.message?.content ?? undefined,\n done: data.done ?? false,\n };\n }\n }\n yield { done: true };\n }\n\n private convertTools(tools: Tool[]) {\n return tools.map((t) => ({\n type: \"function\",\n function: {\n name: t.name,\n description: t.description,\n parameters: t.parameters,\n },\n }));\n }\n}\n","import type { ModelProvider } from \"../core/types.js\";\nimport { OpenAIProvider } from \"./openai.js\";\nimport { AnthropicProvider } from \"./anthropic.js\";\nimport { OllamaProvider } from \"./ollama.js\";\n\ntype ProviderFactory = (config: Record<string, unknown>) => ModelProvider;\n\nconst registry = new Map<string, ProviderFactory>();\n\nregistry.set(\"openai\", (c) => new OpenAIProvider(c as any));\nregistry.set(\"claude\", (c) => new AnthropicProvider(c as any));\nregistry.set(\"anthropic\", (c) => new AnthropicProvider(c as any));\nregistry.set(\"ollama\", (c) => new OllamaProvider(c as any));\n\nexport function registerProvider(name: string, factory: ProviderFactory) {\n registry.set(name, factory);\n}\n\nexport function createProvider(name: string, config: Record<string, unknown>): ModelProvider {\n const factory = registry.get(name);\n if (!factory)\n throw new Error(\n `Unknown model provider: ${name}. Available: ${[...registry.keys()].join(\", \")}`,\n );\n return factory(config);\n}\n\nexport function parseModelString(modelStr: string): { provider: string; model: string } {\n const [provider, ...rest] = modelStr.split(\":\");\n return { provider: provider!, model: rest.join(\":\") || \"\" };\n}\n","import * as readline from \"node:readline\";\nimport chalk from \"chalk\";\nimport { join } from \"node:path\";\nimport { Orchestrator } from \"../core/orchestrator.js\";\nimport { SessionMemory } from \"../memory/session.js\";\nimport { loadSkills, matchSkill } from \"../skills/loader.js\";\nimport type { ModelProvider, ToolResult } from \"../core/types.js\";\n\nexport async function startREPL(\n model: ModelProvider,\n opts?: { skillName?: string },\n): Promise<void> {\n const session = new SessionMemory();\n const skillsDir = join(process.cwd(), \"skills\");\n const skills = await loadSkills(skillsDir);\n\n let skillInstructions: string | undefined;\n if (opts?.skillName) {\n const skill = skills.find((s) => s.name === opts.skillName);\n if (skill) skillInstructions = skill.instructions;\n }\n\n const orchestrator = new Orchestrator({\n model,\n skillInstructions,\n onToolStart: (name) => console.log(chalk.yellow(` ⚙ ${name}...`)),\n onToolEnd: (_name, result: ToolResult) => {\n if (result.error) console.log(chalk.red(` ✗ ${_name}: ${result.error}`));\n else console.log(chalk.green(` ✓ ${_name}`));\n },\n });\n\n const rl = readline.createInterface({\n input: process.stdin,\n output: process.stdout,\n prompt: chalk.cyan(\"hecode> \"),\n });\n\n const logo = chalk.cyan(`\n ██╗ ██╗███████╗ ██████╗ ██████╗ ██████╗ ███████╗\n ██║ ██║██╔════╝██╔════╝██╔═══██╗██╔══██╗██╔════╝\n ███████║█████╗ ██║ ██║ ██║██║ ██║█████╗ \n ██╔══██║██╔══╝ ██║ ██║ ██║██║ ██║██╔══╝ \n ██║ ██║███████╗╚██████╗╚██████╔╝██████╔╝███████╗\n ╚═╝ ╚═╝╚══════╝ ╚═════╝ ╚═════╝ ╚═════╝ ╚══════╝\n `);\n\n console.log(logo);\n console.log(chalk.bold.white(\" Your AI Coding Assistant\") + chalk.gray(\" v0.2.0\"));\n console.log(chalk.gray(\" ─────────────────────────────────────────────\"));\n console.log(chalk.gray(` Session: ${session.sessionId}`));\n if (skills.length) {\n console.log(chalk.gray(` Skills: ${skills.map((s) => s.name).join(\", \")}`));\n }\n console.log(chalk.gray(\" ─────────────────────────────────────────────\"));\n console.log(chalk.gray(\" Type /help for commands, Ctrl+C to exit\\n\"));\n rl.prompt();\n\n rl.on(\"line\", async (line) => {\n const input = line.trim();\n if (!input) {\n rl.prompt();\n return;\n }\n\n if (input.startsWith(\"/\")) {\n handleCommand(input, orchestrator, session);\n rl.prompt();\n return;\n }\n\n // Auto-match skill if not already set\n if (!skillInstructions) {\n const matched = matchSkill(skills, input);\n if (matched) {\n console.log(chalk.gray(` [skill: ${matched.name}]`));\n }\n }\n\n try {\n process.stdout.write(chalk.white(\"\\n\"));\n for await (const token of orchestrator.runStream(input)) {\n process.stdout.write(token);\n }\n process.stdout.write(\"\\n\\n\");\n\n // Auto-save session after each exchange\n await session.save(orchestrator.getMessages());\n } catch (e: any) {\n console.log(chalk.red(`\\nError: ${e.message}\\n`));\n }\n\n rl.prompt();\n });\n\n rl.on(\"close\", () => {\n console.log(chalk.gray(\"\\nGoodbye!\"));\n process.exit(0);\n });\n}\n\nfunction handleCommand(\n input: string,\n orchestrator: Orchestrator,\n session: SessionMemory,\n): void {\n const cmd = input.split(\" \")[0];\n switch (cmd) {\n case \"/help\":\n console.log(\n chalk.cyan(`\n /help — Show this help\n /clear — Clear conversation\n /history — Show message count\n /save — Save session manually\n /session — Show session ID\n /exit — Exit Hecode\n `),\n );\n break;\n case \"/clear\":\n orchestrator.clearMessages();\n console.log(chalk.gray(\"Conversation cleared.\"));\n break;\n case \"/history\":\n console.log(chalk.gray(`Messages: ${orchestrator.getMessages().length}`));\n break;\n case \"/save\":\n session.save(orchestrator.getMessages()).then(() => {\n console.log(chalk.gray(\"Session saved.\"));\n });\n break;\n case \"/session\":\n console.log(chalk.gray(`Session ID: ${session.sessionId}`));\n break;\n case \"/exit\":\n process.exit(0);\n default:\n console.log(chalk.red(`Unknown command: ${cmd}`));\n }\n}\n","import { readFile, writeFile, mkdir } from \"node:fs/promises\";\nimport { join } from \"node:path\";\nimport { homedir } from \"node:os\";\nimport { randomUUID } from \"node:crypto\";\nimport type { Message } from \"../core/types.js\";\n\nconst SESSIONS_DIR = join(homedir(), \".hecode\", \"sessions\");\n\nexport interface Session {\n id: string;\n messages: Message[];\n createdAt: string;\n updatedAt: string;\n}\n\nexport class SessionMemory {\n private sessionDir: string;\n\n constructor(sessionId?: string) {\n const id = sessionId ?? randomUUID().slice(0, 12);\n this.sessionDir = join(SESSIONS_DIR, id);\n }\n\n get sessionId(): string {\n return this.sessionDir.split(/[\\\\/]/).pop()!;\n }\n\n async save(messages: Message[]): Promise<void> {\n await mkdir(this.sessionDir, { recursive: true });\n const session: Session = {\n id: this.sessionId,\n messages,\n createdAt: new Date().toISOString(),\n updatedAt: new Date().toISOString(),\n };\n await writeFile(\n join(this.sessionDir, \"session.json\"),\n JSON.stringify(session, null, 2),\n );\n }\n\n async load(): Promise<Message[]> {\n try {\n const raw = await readFile(\n join(this.sessionDir, \"session.json\"),\n \"utf-8\",\n );\n const session: Session = JSON.parse(raw);\n return session.messages;\n } catch {\n return [];\n }\n }\n\n async saveCheckpoint(data: Record<string, unknown>): Promise<void> {\n await mkdir(this.sessionDir, { recursive: true });\n await writeFile(\n join(this.sessionDir, \"checkpoint.md\"),\n JSON.stringify(data, null, 2),\n );\n }\n\n async saveNote(content: string): Promise<void> {\n await mkdir(this.sessionDir, { recursive: true });\n const notePath = join(this.sessionDir, \"notes.md\");\n let existing = \"\";\n try {\n existing = await readFile(notePath, \"utf-8\");\n } catch {}\n await writeFile(notePath, existing + \"\\n\\n\" + content);\n }\n}\n","import { readFile, readdir } from \"node:fs/promises\";\nimport { join } from \"node:path\";\n\nexport interface Skill {\n name: string;\n description: string;\n trigger: string;\n instructions: string;\n priority: number;\n tools?: string[];\n}\n\ninterface SkillCache {\n skills: Skill[];\n timestamp: number;\n dir: string;\n}\n\nconst CACHE_TTL = 60 * 1000; // 1 minute\nlet skillCache: SkillCache | null = null;\n\nexport async function loadSkills(skillsDir: string): Promise<Skill[]> {\n // Return cached skills if valid\n if (skillCache && skillCache.dir === skillsDir && Date.now() - skillCache.timestamp < CACHE_TTL) {\n return skillCache.skills;\n }\n\n const skills: Skill[] = [];\n try {\n const entries = await readdir(skillsDir, { withFileTypes: true });\n for (const entry of entries) {\n if (!entry.isDirectory()) continue;\n const skillPath = join(skillsDir, entry.name, \"SKILL.md\");\n try {\n const content = await readFile(skillPath, \"utf-8\");\n const skill = parseSkill(entry.name, content);\n if (skill) skills.push(skill);\n } catch {\n // SKILL.md doesn't exist, skip\n }\n }\n } catch (err) {\n console.warn(`Warning: Could not load skills from ${skillsDir}:`, err);\n }\n\n // Sort by priority (higher priority first)\n skills.sort((a, b) => b.priority - a.priority);\n\n // Update cache\n skillCache = {\n skills,\n timestamp: Date.now(),\n dir: skillsDir,\n };\n\n return skills;\n}\n\nfunction parseSkill(name: string, content: string): Skill | null {\n const descMatch = content.match(/^#\\s+(.+)$/m);\n const triggerMatch = content.match(/trigger:\\s*(.+)/i);\n const priorityMatch = content.match(/priority:\\s*(\\d+)/i);\n if (!descMatch) return null;\n\n return {\n name,\n description: descMatch[1] ?? name,\n trigger: triggerMatch?.[1] ?? \"\",\n priority: priorityMatch ? parseInt(priorityMatch[1], 10) : 0,\n instructions: content,\n };\n}\n\nexport function matchSkill(skills: Skill[], userMessage: string): Skill | null {\n const lower = userMessage.toLowerCase();\n const words = lower.split(/\\s+/);\n\n for (const skill of skills) {\n if (!skill.trigger) continue;\n\n const triggers = skill.trigger.split(\",\").map((t) => t.trim().toLowerCase());\n\n for (const trigger of triggers) {\n // Check for exact word match or phrase match\n if (words.includes(trigger) || lower.includes(` ${trigger} `) || lower.startsWith(`${trigger} `) || lower.endsWith(` ${trigger}`)) {\n return skill;\n }\n }\n }\n\n return null;\n}\n\nexport function clearSkillCache(): void {\n skillCache = null;\n}\n","#!/usr/bin/env node\nimport { createProgram } from \"./cli/commands.js\";\n\nconst program = await createProgram();\nprogram.parse();\n"],"mappings":"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","names":["readFile","join","join","readFile","writeFile","mkdir","join","homedir","readFile","join","join","join","readFile","program","Orchestrator"]}
|
|
1
|
+
{"version":3,"sources":["../src/cli/commands.ts","../src/cli/config.ts","../src/models/openai.ts","../src/models/anthropic.ts","../src/models/ollama.ts","../src/models/factory.ts","../src/cli/repl.ts","../src/memory/session.ts","../src/skills/loader.ts","../src/index.ts"],"sourcesContent":["import { Command } from \"commander\";\nimport { readFileSync } from \"node:fs\";\nimport { join, dirname } from \"node:path\";\nimport { fileURLToPath } from \"node:url\";\nimport { loadConfig } from \"./config.js\";\nimport { createProvider, parseModelString } from \"../models/factory.js\";\nimport { startREPL } from \"./repl.js\";\n\nfunction getVersion(): string {\n try {\n const __filename = fileURLToPath(import.meta.url);\n const __dirname = dirname(__filename);\n const pkgPath = join(__dirname, \"../../package.json\");\n const pkg = JSON.parse(readFileSync(pkgPath, \"utf-8\"));\n return pkg.version;\n } catch {\n return \"0.6.0\";\n }\n}\n\nexport function createProgram(): Command {\n const version = getVersion();\n const program = new Command();\n\n program\n .name(\"hecode\")\n .description(\"Hecode — Your AI Coding Assistant CLI\")\n .version(version)\n .option(\"-m, --model <model>\", \"Model to use (e.g. openai:gpt-4o, claude:sonnet)\")\n .option(\"-s, --skill <skill>\", \"Skill to activate\")\n .argument(\"[prompt...]\", \"Single-shot prompt (non-interactive)\")\n .action(async (prompt: string[], opts: { model?: string; skill?: string }) => {\n const config = await loadConfig();\n const modelStr = opts.model ?? config.defaultModel;\n const { provider, model } = parseModelString(modelStr);\n const modelConfig = config.models[provider] ?? {};\n if (model) modelConfig.model = model;\n const modelProvider = createProvider(provider, modelConfig as Record<string, unknown>);\n\n if (prompt.length) {\n const { Orchestrator } = await import(\"../core/orchestrator.js\");\n const orch = new Orchestrator({ model: modelProvider });\n const result = await orch.run(prompt.join(\" \"));\n console.log(result);\n } else {\n await startREPL(modelProvider, { skillName: opts.skill });\n }\n });\n\n program\n .command(\"config\")\n .description(\"Show or edit configuration\")\n .action(async () => {\n const config = await loadConfig();\n console.log(JSON.stringify(config, null, 2));\n });\n\n return program;\n}\n","import { readFile, mkdir, writeFile } from \"node:fs/promises\";\nimport { join } from \"node:path\";\nimport { homedir } from \"node:os\";\nimport type { Config } from \"../core/types.js\";\n\nconst CONFIG_DIR = join(homedir(), \".hecode\");\nconst CONFIG_FILE = join(CONFIG_DIR, \"config.json\");\n\nexport async function loadConfig(): Promise<Config> {\n try {\n const raw = await readFile(CONFIG_FILE, \"utf-8\");\n return JSON.parse(raw);\n } catch {\n return { defaultModel: \"openai:gpt-4o\", models: {} };\n }\n}\n\nexport async function saveConfig(config: Config): Promise<void> {\n await mkdir(CONFIG_DIR, { recursive: true });\n await writeFile(CONFIG_FILE, JSON.stringify(config, null, 2), \"utf-8\");\n}\n","import OpenAI from \"openai\";\nimport type { ModelProvider, Message, Tool, Response, Chunk } from \"../core/types.js\";\n\nexport class OpenAIProvider implements ModelProvider {\n name = \"openai\";\n private client: OpenAI;\n private model: string;\n\n constructor(config: { apiKey?: string; baseUrl?: string; model?: string }) {\n this.client = new OpenAI({\n apiKey: config.apiKey ?? process.env.OPENAI_API_KEY,\n baseURL: config.baseUrl,\n });\n this.model = config.model ?? \"gpt-4o\";\n }\n\n async chat(messages: Message[], tools?: Tool[]): Promise<Response> {\n const params: OpenAI.ChatCompletionCreateParams = {\n model: this.model,\n messages: this.convertMessages(messages),\n ...(tools?.length && { tools: this.convertTools(tools) }),\n };\n const completion = await this.client.chat.completions.create(params);\n const choice = completion.choices[0]!;\n return {\n content: choice.message.content ?? \"\",\n tool_calls: choice.message.tool_calls\n ?.filter((tc) => tc.type === \"function\")\n .map((tc) => ({\n id: tc.id,\n type: \"function\" as const,\n function: { name: tc.function.name, arguments: tc.function.arguments },\n })),\n usage: completion.usage\n ? { prompt: completion.usage.prompt_tokens, completion: completion.usage.completion_tokens }\n : undefined,\n };\n }\n\n async *stream(messages: Message[], tools?: Tool[]): AsyncIterable<Chunk> {\n const stream = await this.client.chat.completions.create({\n model: this.model,\n messages: this.convertMessages(messages),\n stream: true,\n ...(tools?.length && { tools: this.convertTools(tools) }),\n });\n for await (const chunk of stream) {\n const delta = chunk.choices[0]?.delta;\n if (!delta) continue;\n yield {\n content: delta.content ?? undefined,\n tool_calls: delta.tool_calls?.map((tc) => ({\n id: tc.id ?? \"\",\n type: \"function\" as const,\n function: { name: tc.function?.name ?? \"\", arguments: tc.function?.arguments ?? \"\" },\n })),\n done: chunk.choices[0]?.finish_reason != null,\n };\n }\n }\n\n private convertMessages(messages: Message[]): OpenAI.ChatCompletionMessageParam[] {\n return messages.map((m) => {\n if (m.role === \"tool\") {\n return { role: \"tool\" as const, content: m.content, tool_call_id: m.tool_call_id! };\n }\n if (m.role === \"assistant\" && m.tool_calls?.length) {\n return {\n role: \"assistant\" as const,\n content: m.content,\n tool_calls: m.tool_calls.map((tc) => ({\n id: tc.id,\n type: \"function\" as const,\n function: tc.function,\n })),\n };\n }\n return { role: m.role as \"system\" | \"user\" | \"assistant\", content: m.content };\n });\n }\n\n private convertTools(tools: Tool[]): OpenAI.ChatCompletionTool[] {\n return tools.map((t) => ({\n type: \"function\" as const,\n function: { name: t.name, description: t.description, parameters: t.parameters },\n }));\n }\n}\n","import Anthropic from \"@anthropic-ai/sdk\";\nimport type { ModelProvider, Message, Tool, Response, Chunk } from \"../core/types.js\";\n\nexport class AnthropicProvider implements ModelProvider {\n name = \"anthropic\";\n private client: Anthropic;\n private model: string;\n\n constructor(config: { apiKey?: string; model?: string }) {\n this.client = new Anthropic({ apiKey: config.apiKey ?? process.env.ANTHROPIC_API_KEY });\n this.model = config.model ?? \"claude-sonnet-4-20250514\";\n }\n\n async chat(messages: Message[], tools?: Tool[]): Promise<Response> {\n const system = messages.find((m) => m.role === \"system\")?.content ?? \"\";\n const convMessages = messages.filter((m) => m.role !== \"system\");\n const params: Anthropic.MessageCreateParams = {\n model: this.model,\n max_tokens: 8192,\n system,\n messages: this.convertMessages(convMessages),\n ...(tools?.length && { tools: this.convertTools(tools) }),\n };\n const msg = await this.client.messages.create(params);\n const textBlock = msg.content.find((b) => b.type === \"text\");\n const toolBlocks = msg.content.filter((b) => b.type === \"tool_use\");\n return {\n content: textBlock?.text ?? \"\",\n tool_calls: toolBlocks.map((tb) => ({\n id: tb.id,\n type: \"function\" as const,\n function: { name: tb.name, arguments: JSON.stringify(tb.input) },\n })),\n usage: { prompt: msg.usage.input_tokens, completion: msg.usage.output_tokens },\n };\n }\n\n async *stream(messages: Message[], tools?: Tool[]): AsyncIterable<Chunk> {\n const system = messages.find((m) => m.role === \"system\")?.content ?? \"\";\n const convMessages = messages.filter((m) => m.role !== \"system\");\n const stream = this.client.messages.stream({\n model: this.model,\n max_tokens: 8192,\n system,\n messages: this.convertMessages(convMessages),\n ...(tools?.length && { tools: this.convertTools(tools) }),\n });\n for await (const event of stream) {\n if (event.type === \"content_block_delta\" && event.delta.type === \"text_delta\") {\n yield { content: event.delta.text, done: false };\n }\n }\n yield { content: undefined, done: true };\n }\n\n private convertMessages(messages: Message[]): Anthropic.MessageParam[] {\n return messages.map((m) => ({\n role: m.role === \"assistant\" ? \"assistant\" : \"user\",\n content: m.content,\n }));\n }\n\n private convertTools(tools: Tool[]): Anthropic.Tool[] {\n return tools.map((t) => ({\n name: t.name,\n description: t.description,\n input_schema: t.parameters as Anthropic.Tool[\"input_schema\"],\n }));\n }\n}\n","import type { ModelProvider, Message, Tool, Response, Chunk } from \"../core/types.js\";\n\nexport class OllamaProvider implements ModelProvider {\n name = \"ollama\";\n private baseUrl: string;\n private model: string;\n\n constructor(config: { baseUrl?: string; model?: string }) {\n this.baseUrl = config.baseUrl ?? \"http://localhost:11434\";\n this.model = config.model ?? \"llama3.1\";\n }\n\n async chat(messages: Message[], tools?: Tool[]): Promise<Response> {\n const res = await fetch(`${this.baseUrl}/api/chat`, {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify({\n model: this.model,\n messages: messages.map((m) => ({ role: m.role, content: m.content })),\n stream: false,\n ...(tools?.length && { tools: this.convertTools(tools) }),\n }),\n });\n const data = (await res.json()) as any;\n return {\n content: data.message?.content ?? \"\",\n tool_calls: data.message?.tool_calls?.map((tc: any, i: number) => ({\n id: `call_${i}`,\n type: \"function\" as const,\n function: {\n name: tc.function?.name ?? \"\",\n arguments: JSON.stringify(tc.function?.arguments ?? {}),\n },\n })),\n };\n }\n\n async *stream(messages: Message[], tools?: Tool[]): AsyncIterable<Chunk> {\n const res = await fetch(`${this.baseUrl}/api/chat`, {\n method: \"POST\",\n headers: { \"Content-Type\": \"application/json\" },\n body: JSON.stringify({\n model: this.model,\n messages: messages.map((m) => ({ role: m.role, content: m.content })),\n stream: true,\n ...(tools?.length && { tools: this.convertTools(tools) }),\n }),\n });\n const reader = res.body!.getReader();\n const decoder = new TextDecoder();\n let buffer = \"\";\n while (true) {\n const { done, value } = await reader.read();\n if (done) break;\n buffer += decoder.decode(value, { stream: true });\n const lines = buffer.split(\"\\n\");\n buffer = lines.pop()!;\n for (const line of lines) {\n if (!line.trim()) continue;\n const data = JSON.parse(line);\n yield {\n content: data.message?.content ?? undefined,\n done: data.done ?? false,\n };\n }\n }\n yield { done: true };\n }\n\n private convertTools(tools: Tool[]) {\n return tools.map((t) => ({\n type: \"function\",\n function: {\n name: t.name,\n description: t.description,\n parameters: t.parameters,\n },\n }));\n }\n}\n","import type { ModelProvider } from \"../core/types.js\";\nimport { OpenAIProvider } from \"./openai.js\";\nimport { AnthropicProvider } from \"./anthropic.js\";\nimport { OllamaProvider } from \"./ollama.js\";\n\ntype ProviderFactory = (config: Record<string, unknown>) => ModelProvider;\n\nconst registry = new Map<string, ProviderFactory>();\n\nregistry.set(\"openai\", (c) => new OpenAIProvider(c as any));\nregistry.set(\"claude\", (c) => new AnthropicProvider(c as any));\nregistry.set(\"anthropic\", (c) => new AnthropicProvider(c as any));\nregistry.set(\"ollama\", (c) => new OllamaProvider(c as any));\n\nexport function registerProvider(name: string, factory: ProviderFactory) {\n registry.set(name, factory);\n}\n\nexport function createProvider(name: string, config: Record<string, unknown>): ModelProvider {\n const factory = registry.get(name);\n if (!factory)\n throw new Error(\n `Unknown model provider: ${name}. Available: ${[...registry.keys()].join(\", \")}`,\n );\n return factory(config);\n}\n\nexport function parseModelString(modelStr: string): { provider: string; model: string } {\n const [provider, ...rest] = modelStr.split(\":\");\n return { provider: provider!, model: rest.join(\":\") || \"\" };\n}\n","import * as readline from \"node:readline\";\nimport chalk from \"chalk\";\nimport { join } from \"node:path\";\nimport { Orchestrator } from \"../core/orchestrator.js\";\nimport { SessionMemory } from \"../memory/session.js\";\nimport { loadSkills, matchSkill } from \"../skills/loader.js\";\nimport type { ModelProvider, ToolResult } from \"../core/types.js\";\n\nexport async function startREPL(\n model: ModelProvider,\n opts?: { skillName?: string },\n): Promise<void> {\n const session = new SessionMemory();\n const skillsDir = join(process.cwd(), \"skills\");\n const skills = await loadSkills(skillsDir);\n\n let skillInstructions: string | undefined;\n if (opts?.skillName) {\n const skill = skills.find((s) => s.name === opts.skillName);\n if (skill) skillInstructions = skill.instructions;\n }\n\n const orchestrator = new Orchestrator({\n model,\n skillInstructions,\n onToolStart: (name) => console.log(chalk.yellow(` ⚙ ${name}...`)),\n onToolEnd: (_name, result: ToolResult) => {\n if (result.error) console.log(chalk.red(` ✗ ${_name}: ${result.error}`));\n else console.log(chalk.green(` ✓ ${_name}`));\n },\n });\n\n const rl = readline.createInterface({\n input: process.stdin,\n output: process.stdout,\n prompt: chalk.cyan(\"hecode> \"),\n });\n\n const logo = chalk.cyan(`\n ██╗ ██╗███████╗ ██████╗ ██████╗ ██████╗ ███████╗\n ██║ ██║██╔════╝██╔════╝██╔═══██╗██╔══██╗██╔════╝\n ███████║█████╗ ██║ ██║ ██║██║ ██║█████╗ \n ██╔══██║██╔══╝ ██║ ██║ ██║██║ ██║██╔══╝ \n ██║ ██║███████╗╚██████╗╚██████╔╝██████╔╝███████╗\n ╚═╝ ╚═╝╚══════╝ ╚═════╝ ╚═════╝ ╚═════╝ ╚══════╝\n `);\n\n console.log(logo);\n console.log(chalk.bold.white(\" Your AI Coding Assistant\") + chalk.gray(\" v0.2.0\"));\n console.log(chalk.gray(\" ─────────────────────────────────────────────\"));\n console.log(chalk.gray(` Session: ${session.sessionId}`));\n if (skills.length) {\n console.log(chalk.gray(` Skills: ${skills.map((s) => s.name).join(\", \")}`));\n }\n console.log(chalk.gray(\" ─────────────────────────────────────────────\"));\n console.log(chalk.gray(\" Type /help for commands, Ctrl+C to exit\\n\"));\n rl.prompt();\n\n rl.on(\"line\", async (line) => {\n const input = line.trim();\n if (!input) {\n rl.prompt();\n return;\n }\n\n if (input.startsWith(\"/\")) {\n handleCommand(input, orchestrator, session);\n rl.prompt();\n return;\n }\n\n // Auto-match skill if not already set\n if (!skillInstructions) {\n const matched = matchSkill(skills, input);\n if (matched) {\n console.log(chalk.gray(` [skill: ${matched.name}]`));\n }\n }\n\n try {\n process.stdout.write(chalk.white(\"\\n\"));\n for await (const token of orchestrator.runStream(input)) {\n process.stdout.write(token);\n }\n process.stdout.write(\"\\n\\n\");\n\n // Auto-save session after each exchange\n await session.save(orchestrator.getMessages());\n } catch (e: any) {\n console.log(chalk.red(`\\nError: ${e.message}\\n`));\n }\n\n rl.prompt();\n });\n\n rl.on(\"close\", () => {\n console.log(chalk.gray(\"\\nGoodbye!\"));\n process.exit(0);\n });\n}\n\nfunction handleCommand(\n input: string,\n orchestrator: Orchestrator,\n session: SessionMemory,\n): void {\n const cmd = input.split(\" \")[0];\n switch (cmd) {\n case \"/help\":\n console.log(\n chalk.cyan(`\n /help — Show this help\n /clear — Clear conversation\n /history — Show message count\n /save — Save session manually\n /session — Show session ID\n /exit — Exit Hecode\n `),\n );\n break;\n case \"/clear\":\n orchestrator.clearMessages();\n console.log(chalk.gray(\"Conversation cleared.\"));\n break;\n case \"/history\":\n console.log(chalk.gray(`Messages: ${orchestrator.getMessages().length}`));\n break;\n case \"/save\":\n session.save(orchestrator.getMessages()).then(() => {\n console.log(chalk.gray(\"Session saved.\"));\n });\n break;\n case \"/session\":\n console.log(chalk.gray(`Session ID: ${session.sessionId}`));\n break;\n case \"/exit\":\n process.exit(0);\n default:\n console.log(chalk.red(`Unknown command: ${cmd}`));\n }\n}\n","import { readFile, writeFile, mkdir } from \"node:fs/promises\";\nimport { join } from \"node:path\";\nimport { homedir } from \"node:os\";\nimport { randomUUID } from \"node:crypto\";\nimport type { Message } from \"../core/types.js\";\n\nconst SESSIONS_DIR = join(homedir(), \".hecode\", \"sessions\");\n\nexport interface Session {\n id: string;\n messages: Message[];\n createdAt: string;\n updatedAt: string;\n}\n\nexport class SessionMemory {\n private sessionDir: string;\n\n constructor(sessionId?: string) {\n const id = sessionId ?? randomUUID().slice(0, 12);\n this.sessionDir = join(SESSIONS_DIR, id);\n }\n\n get sessionId(): string {\n return this.sessionDir.split(/[\\\\/]/).pop()!;\n }\n\n async save(messages: Message[]): Promise<void> {\n await mkdir(this.sessionDir, { recursive: true });\n const session: Session = {\n id: this.sessionId,\n messages,\n createdAt: new Date().toISOString(),\n updatedAt: new Date().toISOString(),\n };\n await writeFile(\n join(this.sessionDir, \"session.json\"),\n JSON.stringify(session, null, 2),\n );\n }\n\n async load(): Promise<Message[]> {\n try {\n const raw = await readFile(\n join(this.sessionDir, \"session.json\"),\n \"utf-8\",\n );\n const session: Session = JSON.parse(raw);\n return session.messages;\n } catch {\n return [];\n }\n }\n\n async saveCheckpoint(data: Record<string, unknown>): Promise<void> {\n await mkdir(this.sessionDir, { recursive: true });\n await writeFile(\n join(this.sessionDir, \"checkpoint.md\"),\n JSON.stringify(data, null, 2),\n );\n }\n\n async saveNote(content: string): Promise<void> {\n await mkdir(this.sessionDir, { recursive: true });\n const notePath = join(this.sessionDir, \"notes.md\");\n let existing = \"\";\n try {\n existing = await readFile(notePath, \"utf-8\");\n } catch {}\n await writeFile(notePath, existing + \"\\n\\n\" + content);\n }\n}\n","import { readFile, readdir } from \"node:fs/promises\";\nimport { join } from \"node:path\";\n\nexport interface Skill {\n name: string;\n description: string;\n trigger: string;\n instructions: string;\n priority: number;\n tools?: string[];\n}\n\ninterface SkillCache {\n skills: Skill[];\n timestamp: number;\n dir: string;\n}\n\nconst CACHE_TTL = 60 * 1000; // 1 minute\nlet skillCache: SkillCache | null = null;\n\nexport async function loadSkills(skillsDir: string): Promise<Skill[]> {\n // Return cached skills if valid\n if (skillCache && skillCache.dir === skillsDir && Date.now() - skillCache.timestamp < CACHE_TTL) {\n return skillCache.skills;\n }\n\n const skills: Skill[] = [];\n try {\n const entries = await readdir(skillsDir, { withFileTypes: true });\n for (const entry of entries) {\n if (!entry.isDirectory()) continue;\n const skillPath = join(skillsDir, entry.name, \"SKILL.md\");\n try {\n const content = await readFile(skillPath, \"utf-8\");\n const skill = parseSkill(entry.name, content);\n if (skill) skills.push(skill);\n } catch {\n // SKILL.md doesn't exist, skip\n }\n }\n } catch (err) {\n console.warn(`Warning: Could not load skills from ${skillsDir}:`, err);\n }\n\n // Sort by priority (higher priority first)\n skills.sort((a, b) => b.priority - a.priority);\n\n // Update cache\n skillCache = {\n skills,\n timestamp: Date.now(),\n dir: skillsDir,\n };\n\n return skills;\n}\n\nfunction parseSkill(name: string, content: string): Skill | null {\n const descMatch = content.match(/^#\\s+(.+)$/m);\n const triggerMatch = content.match(/trigger:\\s*(.+)/i);\n const priorityMatch = content.match(/priority:\\s*(\\d+)/i);\n if (!descMatch) return null;\n\n return {\n name,\n description: descMatch[1] ?? name,\n trigger: triggerMatch?.[1] ?? \"\",\n priority: priorityMatch ? parseInt(priorityMatch[1], 10) : 0,\n instructions: content,\n };\n}\n\nexport function matchSkill(skills: Skill[], userMessage: string): Skill | null {\n const lower = userMessage.toLowerCase();\n const words = lower.split(/\\s+/);\n\n for (const skill of skills) {\n if (!skill.trigger) continue;\n\n const triggers = skill.trigger.split(\",\").map((t) => t.trim().toLowerCase());\n\n for (const trigger of triggers) {\n // Check for exact word match or phrase match\n if (words.includes(trigger) || lower.includes(` ${trigger} `) || lower.startsWith(`${trigger} `) || lower.endsWith(` ${trigger}`)) {\n return skill;\n }\n }\n }\n\n return null;\n}\n\nexport function clearSkillCache(): void {\n skillCache = null;\n}\n","#!/usr/bin/env node\nimport { createProgram } from \"./cli/commands.js\";\n\nconst program = createProgram();\nprogram.parse();\n"],"mappings":";;;;;;AAAA,SAAS,eAAe;AACxB,SAAS,oBAAoB;AAC7B,SAAS,QAAAA,OAAM,eAAe;AAC9B,SAAS,qBAAqB;;;ACH9B,SAAS,UAAU,OAAO,iBAAiB;AAC3C,SAAS,YAAY;AACrB,SAAS,eAAe;AAGxB,IAAM,aAAa,KAAK,QAAQ,GAAG,SAAS;AAC5C,IAAM,cAAc,KAAK,YAAY,aAAa;AAElD,eAAsB,aAA8B;AAClD,MAAI;AACF,UAAM,MAAM,MAAM,SAAS,aAAa,OAAO;AAC/C,WAAO,KAAK,MAAM,GAAG;AAAA,EACvB,QAAQ;AACN,WAAO,EAAE,cAAc,iBAAiB,QAAQ,CAAC,EAAE;AAAA,EACrD;AACF;;;ACfA,OAAO,YAAY;AAGZ,IAAM,iBAAN,MAA8C;AAAA,EACnD,OAAO;AAAA,EACC;AAAA,EACA;AAAA,EAER,YAAY,QAA+D;AACzE,SAAK,SAAS,IAAI,OAAO;AAAA,MACvB,QAAQ,OAAO,UAAU,QAAQ,IAAI;AAAA,MACrC,SAAS,OAAO;AAAA,IAClB,CAAC;AACD,SAAK,QAAQ,OAAO,SAAS;AAAA,EAC/B;AAAA,EAEA,MAAM,KAAK,UAAqB,OAAmC;AACjE,UAAM,SAA4C;AAAA,MAChD,OAAO,KAAK;AAAA,MACZ,UAAU,KAAK,gBAAgB,QAAQ;AAAA,MACvC,GAAI,OAAO,UAAU,EAAE,OAAO,KAAK,aAAa,KAAK,EAAE;AAAA,IACzD;AACA,UAAM,aAAa,MAAM,KAAK,OAAO,KAAK,YAAY,OAAO,MAAM;AACnE,UAAM,SAAS,WAAW,QAAQ,CAAC;AACnC,WAAO;AAAA,MACL,SAAS,OAAO,QAAQ,WAAW;AAAA,MACnC,YAAY,OAAO,QAAQ,YACvB,OAAO,CAAC,OAAO,GAAG,SAAS,UAAU,EACtC,IAAI,CAAC,QAAQ;AAAA,QACZ,IAAI,GAAG;AAAA,QACP,MAAM;AAAA,QACN,UAAU,EAAE,MAAM,GAAG,SAAS,MAAM,WAAW,GAAG,SAAS,UAAU;AAAA,MACvE,EAAE;AAAA,MACJ,OAAO,WAAW,QACd,EAAE,QAAQ,WAAW,MAAM,eAAe,YAAY,WAAW,MAAM,kBAAkB,IACzF;AAAA,IACN;AAAA,EACF;AAAA,EAEA,OAAO,OAAO,UAAqB,OAAsC;AACvE,UAAM,SAAS,MAAM,KAAK,OAAO,KAAK,YAAY,OAAO;AAAA,MACvD,OAAO,KAAK;AAAA,MACZ,UAAU,KAAK,gBAAgB,QAAQ;AAAA,MACvC,QAAQ;AAAA,MACR,GAAI,OAAO,UAAU,EAAE,OAAO,KAAK,aAAa,KAAK,EAAE;AAAA,IACzD,CAAC;AACD,qBAAiB,SAAS,QAAQ;AAChC,YAAM,QAAQ,MAAM,QAAQ,CAAC,GAAG;AAChC,UAAI,CAAC,MAAO;AACZ,YAAM;AAAA,QACJ,SAAS,MAAM,WAAW;AAAA,QAC1B,YAAY,MAAM,YAAY,IAAI,CAAC,QAAQ;AAAA,UACzC,IAAI,GAAG,MAAM;AAAA,UACb,MAAM;AAAA,UACN,UAAU,EAAE,MAAM,GAAG,UAAU,QAAQ,IAAI,WAAW,GAAG,UAAU,aAAa,GAAG;AAAA,QACrF,EAAE;AAAA,QACF,MAAM,MAAM,QAAQ,CAAC,GAAG,iBAAiB;AAAA,MAC3C;AAAA,IACF;AAAA,EACF;AAAA,EAEQ,gBAAgB,UAA0D;AAChF,WAAO,SAAS,IAAI,CAAC,MAAM;AACzB,UAAI,EAAE,SAAS,QAAQ;AACrB,eAAO,EAAE,MAAM,QAAiB,SAAS,EAAE,SAAS,cAAc,EAAE,aAAc;AAAA,MACpF;AACA,UAAI,EAAE,SAAS,eAAe,EAAE,YAAY,QAAQ;AAClD,eAAO;AAAA,UACL,MAAM;AAAA,UACN,SAAS,EAAE;AAAA,UACX,YAAY,EAAE,WAAW,IAAI,CAAC,QAAQ;AAAA,YACpC,IAAI,GAAG;AAAA,YACP,MAAM;AAAA,YACN,UAAU,GAAG;AAAA,UACf,EAAE;AAAA,QACJ;AAAA,MACF;AACA,aAAO,EAAE,MAAM,EAAE,MAAyC,SAAS,EAAE,QAAQ;AAAA,IAC/E,CAAC;AAAA,EACH;AAAA,EAEQ,aAAa,OAA4C;AAC/D,WAAO,MAAM,IAAI,CAAC,OAAO;AAAA,MACvB,MAAM;AAAA,MACN,UAAU,EAAE,MAAM,EAAE,MAAM,aAAa,EAAE,aAAa,YAAY,EAAE,WAAW;AAAA,IACjF,EAAE;AAAA,EACJ;AACF;;;ACvFA,OAAO,eAAe;AAGf,IAAM,oBAAN,MAAiD;AAAA,EACtD,OAAO;AAAA,EACC;AAAA,EACA;AAAA,EAER,YAAY,QAA6C;AACvD,SAAK,SAAS,IAAI,UAAU,EAAE,QAAQ,OAAO,UAAU,QAAQ,IAAI,kBAAkB,CAAC;AACtF,SAAK,QAAQ,OAAO,SAAS;AAAA,EAC/B;AAAA,EAEA,MAAM,KAAK,UAAqB,OAAmC;AACjE,UAAM,SAAS,SAAS,KAAK,CAAC,MAAM,EAAE,SAAS,QAAQ,GAAG,WAAW;AACrE,UAAM,eAAe,SAAS,OAAO,CAAC,MAAM,EAAE,SAAS,QAAQ;AAC/D,UAAM,SAAwC;AAAA,MAC5C,OAAO,KAAK;AAAA,MACZ,YAAY;AAAA,MACZ;AAAA,MACA,UAAU,KAAK,gBAAgB,YAAY;AAAA,MAC3C,GAAI,OAAO,UAAU,EAAE,OAAO,KAAK,aAAa,KAAK,EAAE;AAAA,IACzD;AACA,UAAM,MAAM,MAAM,KAAK,OAAO,SAAS,OAAO,MAAM;AACpD,UAAM,YAAY,IAAI,QAAQ,KAAK,CAAC,MAAM,EAAE,SAAS,MAAM;AAC3D,UAAM,aAAa,IAAI,QAAQ,OAAO,CAAC,MAAM,EAAE,SAAS,UAAU;AAClE,WAAO;AAAA,MACL,SAAS,WAAW,QAAQ;AAAA,MAC5B,YAAY,WAAW,IAAI,CAAC,QAAQ;AAAA,QAClC,IAAI,GAAG;AAAA,QACP,MAAM;AAAA,QACN,UAAU,EAAE,MAAM,GAAG,MAAM,WAAW,KAAK,UAAU,GAAG,KAAK,EAAE;AAAA,MACjE,EAAE;AAAA,MACF,OAAO,EAAE,QAAQ,IAAI,MAAM,cAAc,YAAY,IAAI,MAAM,cAAc;AAAA,IAC/E;AAAA,EACF;AAAA,EAEA,OAAO,OAAO,UAAqB,OAAsC;AACvE,UAAM,SAAS,SAAS,KAAK,CAAC,MAAM,EAAE,SAAS,QAAQ,GAAG,WAAW;AACrE,UAAM,eAAe,SAAS,OAAO,CAAC,MAAM,EAAE,SAAS,QAAQ;AAC/D,UAAM,SAAS,KAAK,OAAO,SAAS,OAAO;AAAA,MACzC,OAAO,KAAK;AAAA,MACZ,YAAY;AAAA,MACZ;AAAA,MACA,UAAU,KAAK,gBAAgB,YAAY;AAAA,MAC3C,GAAI,OAAO,UAAU,EAAE,OAAO,KAAK,aAAa,KAAK,EAAE;AAAA,IACzD,CAAC;AACD,qBAAiB,SAAS,QAAQ;AAChC,UAAI,MAAM,SAAS,yBAAyB,MAAM,MAAM,SAAS,cAAc;AAC7E,cAAM,EAAE,SAAS,MAAM,MAAM,MAAM,MAAM,MAAM;AAAA,MACjD;AAAA,IACF;AACA,UAAM,EAAE,SAAS,QAAW,MAAM,KAAK;AAAA,EACzC;AAAA,EAEQ,gBAAgB,UAA+C;AACrE,WAAO,SAAS,IAAI,CAAC,OAAO;AAAA,MAC1B,MAAM,EAAE,SAAS,cAAc,cAAc;AAAA,MAC7C,SAAS,EAAE;AAAA,IACb,EAAE;AAAA,EACJ;AAAA,EAEQ,aAAa,OAAiC;AACpD,WAAO,MAAM,IAAI,CAAC,OAAO;AAAA,MACvB,MAAM,EAAE;AAAA,MACR,aAAa,EAAE;AAAA,MACf,cAAc,EAAE;AAAA,IAClB,EAAE;AAAA,EACJ;AACF;;;ACnEO,IAAM,iBAAN,MAA8C;AAAA,EACnD,OAAO;AAAA,EACC;AAAA,EACA;AAAA,EAER,YAAY,QAA8C;AACxD,SAAK,UAAU,OAAO,WAAW;AACjC,SAAK,QAAQ,OAAO,SAAS;AAAA,EAC/B;AAAA,EAEA,MAAM,KAAK,UAAqB,OAAmC;AACjE,UAAM,MAAM,MAAM,MAAM,GAAG,KAAK,OAAO,aAAa;AAAA,MAClD,QAAQ;AAAA,MACR,SAAS,EAAE,gBAAgB,mBAAmB;AAAA,MAC9C,MAAM,KAAK,UAAU;AAAA,QACnB,OAAO,KAAK;AAAA,QACZ,UAAU,SAAS,IAAI,CAAC,OAAO,EAAE,MAAM,EAAE,MAAM,SAAS,EAAE,QAAQ,EAAE;AAAA,QACpE,QAAQ;AAAA,QACR,GAAI,OAAO,UAAU,EAAE,OAAO,KAAK,aAAa,KAAK,EAAE;AAAA,MACzD,CAAC;AAAA,IACH,CAAC;AACD,UAAM,OAAQ,MAAM,IAAI,KAAK;AAC7B,WAAO;AAAA,MACL,SAAS,KAAK,SAAS,WAAW;AAAA,MAClC,YAAY,KAAK,SAAS,YAAY,IAAI,CAAC,IAAS,OAAe;AAAA,QACjE,IAAI,QAAQ,CAAC;AAAA,QACb,MAAM;AAAA,QACN,UAAU;AAAA,UACR,MAAM,GAAG,UAAU,QAAQ;AAAA,UAC3B,WAAW,KAAK,UAAU,GAAG,UAAU,aAAa,CAAC,CAAC;AAAA,QACxD;AAAA,MACF,EAAE;AAAA,IACJ;AAAA,EACF;AAAA,EAEA,OAAO,OAAO,UAAqB,OAAsC;AACvE,UAAM,MAAM,MAAM,MAAM,GAAG,KAAK,OAAO,aAAa;AAAA,MAClD,QAAQ;AAAA,MACR,SAAS,EAAE,gBAAgB,mBAAmB;AAAA,MAC9C,MAAM,KAAK,UAAU;AAAA,QACnB,OAAO,KAAK;AAAA,QACZ,UAAU,SAAS,IAAI,CAAC,OAAO,EAAE,MAAM,EAAE,MAAM,SAAS,EAAE,QAAQ,EAAE;AAAA,QACpE,QAAQ;AAAA,QACR,GAAI,OAAO,UAAU,EAAE,OAAO,KAAK,aAAa,KAAK,EAAE;AAAA,MACzD,CAAC;AAAA,IACH,CAAC;AACD,UAAM,SAAS,IAAI,KAAM,UAAU;AACnC,UAAM,UAAU,IAAI,YAAY;AAChC,QAAI,SAAS;AACb,WAAO,MAAM;AACX,YAAM,EAAE,MAAM,MAAM,IAAI,MAAM,OAAO,KAAK;AAC1C,UAAI,KAAM;AACV,gBAAU,QAAQ,OAAO,OAAO,EAAE,QAAQ,KAAK,CAAC;AAChD,YAAM,QAAQ,OAAO,MAAM,IAAI;AAC/B,eAAS,MAAM,IAAI;AACnB,iBAAW,QAAQ,OAAO;AACxB,YAAI,CAAC,KAAK,KAAK,EAAG;AAClB,cAAM,OAAO,KAAK,MAAM,IAAI;AAC5B,cAAM;AAAA,UACJ,SAAS,KAAK,SAAS,WAAW;AAAA,UAClC,MAAM,KAAK,QAAQ;AAAA,QACrB;AAAA,MACF;AAAA,IACF;AACA,UAAM,EAAE,MAAM,KAAK;AAAA,EACrB;AAAA,EAEQ,aAAa,OAAe;AAClC,WAAO,MAAM,IAAI,CAAC,OAAO;AAAA,MACvB,MAAM;AAAA,MACN,UAAU;AAAA,QACR,MAAM,EAAE;AAAA,QACR,aAAa,EAAE;AAAA,QACf,YAAY,EAAE;AAAA,MAChB;AAAA,IACF,EAAE;AAAA,EACJ;AACF;;;ACxEA,IAAM,WAAW,oBAAI,IAA6B;AAElD,SAAS,IAAI,UAAU,CAAC,MAAM,IAAI,eAAe,CAAQ,CAAC;AAC1D,SAAS,IAAI,UAAU,CAAC,MAAM,IAAI,kBAAkB,CAAQ,CAAC;AAC7D,SAAS,IAAI,aAAa,CAAC,MAAM,IAAI,kBAAkB,CAAQ,CAAC;AAChE,SAAS,IAAI,UAAU,CAAC,MAAM,IAAI,eAAe,CAAQ,CAAC;AAMnD,SAAS,eAAe,MAAc,QAAgD;AAC3F,QAAM,UAAU,SAAS,IAAI,IAAI;AACjC,MAAI,CAAC;AACH,UAAM,IAAI;AAAA,MACR,2BAA2B,IAAI,gBAAgB,CAAC,GAAG,SAAS,KAAK,CAAC,EAAE,KAAK,IAAI,CAAC;AAAA,IAChF;AACF,SAAO,QAAQ,MAAM;AACvB;AAEO,SAAS,iBAAiB,UAAuD;AACtF,QAAM,CAAC,UAAU,GAAG,IAAI,IAAI,SAAS,MAAM,GAAG;AAC9C,SAAO,EAAE,UAAqB,OAAO,KAAK,KAAK,GAAG,KAAK,GAAG;AAC5D;;;AC9BA,YAAY,cAAc;AAC1B,OAAO,WAAW;AAClB,SAAS,QAAAC,aAAY;;;ACFrB,SAAS,YAAAC,WAAU,aAAAC,YAAW,SAAAC,cAAa;AAC3C,SAAS,QAAAC,aAAY;AACrB,SAAS,WAAAC,gBAAe;AACxB,SAAS,kBAAkB;AAG3B,IAAM,eAAeD,MAAKC,SAAQ,GAAG,WAAW,UAAU;AASnD,IAAM,gBAAN,MAAoB;AAAA,EACjB;AAAA,EAER,YAAY,WAAoB;AAC9B,UAAM,KAAK,aAAa,WAAW,EAAE,MAAM,GAAG,EAAE;AAChD,SAAK,aAAaD,MAAK,cAAc,EAAE;AAAA,EACzC;AAAA,EAEA,IAAI,YAAoB;AACtB,WAAO,KAAK,WAAW,MAAM,OAAO,EAAE,IAAI;AAAA,EAC5C;AAAA,EAEA,MAAM,KAAK,UAAoC;AAC7C,UAAMD,OAAM,KAAK,YAAY,EAAE,WAAW,KAAK,CAAC;AAChD,UAAM,UAAmB;AAAA,MACvB,IAAI,KAAK;AAAA,MACT;AAAA,MACA,YAAW,oBAAI,KAAK,GAAE,YAAY;AAAA,MAClC,YAAW,oBAAI,KAAK,GAAE,YAAY;AAAA,IACpC;AACA,UAAMD;AAAA,MACJE,MAAK,KAAK,YAAY,cAAc;AAAA,MACpC,KAAK,UAAU,SAAS,MAAM,CAAC;AAAA,IACjC;AAAA,EACF;AAAA,EAEA,MAAM,OAA2B;AAC/B,QAAI;AACF,YAAM,MAAM,MAAMH;AAAA,QAChBG,MAAK,KAAK,YAAY,cAAc;AAAA,QACpC;AAAA,MACF;AACA,YAAM,UAAmB,KAAK,MAAM,GAAG;AACvC,aAAO,QAAQ;AAAA,IACjB,QAAQ;AACN,aAAO,CAAC;AAAA,IACV;AAAA,EACF;AAAA,EAEA,MAAM,eAAe,MAA8C;AACjE,UAAMD,OAAM,KAAK,YAAY,EAAE,WAAW,KAAK,CAAC;AAChD,UAAMD;AAAA,MACJE,MAAK,KAAK,YAAY,eAAe;AAAA,MACrC,KAAK,UAAU,MAAM,MAAM,CAAC;AAAA,IAC9B;AAAA,EACF;AAAA,EAEA,MAAM,SAAS,SAAgC;AAC7C,UAAMD,OAAM,KAAK,YAAY,EAAE,WAAW,KAAK,CAAC;AAChD,UAAM,WAAWC,MAAK,KAAK,YAAY,UAAU;AACjD,QAAI,WAAW;AACf,QAAI;AACF,iBAAW,MAAMH,UAAS,UAAU,OAAO;AAAA,IAC7C,QAAQ;AAAA,IAAC;AACT,UAAMC,WAAU,UAAU,WAAW,SAAS,OAAO;AAAA,EACvD;AACF;;;ACvEA,SAAS,YAAAI,WAAU,eAAe;AAClC,SAAS,QAAAC,aAAY;AAiBrB,IAAM,YAAY,KAAK;AACvB,IAAI,aAAgC;AAEpC,eAAsB,WAAW,WAAqC;AAEpE,MAAI,cAAc,WAAW,QAAQ,aAAa,KAAK,IAAI,IAAI,WAAW,YAAY,WAAW;AAC/F,WAAO,WAAW;AAAA,EACpB;AAEA,QAAM,SAAkB,CAAC;AACzB,MAAI;AACF,UAAM,UAAU,MAAM,QAAQ,WAAW,EAAE,eAAe,KAAK,CAAC;AAChE,eAAW,SAAS,SAAS;AAC3B,UAAI,CAAC,MAAM,YAAY,EAAG;AAC1B,YAAM,YAAYA,MAAK,WAAW,MAAM,MAAM,UAAU;AACxD,UAAI;AACF,cAAM,UAAU,MAAMD,UAAS,WAAW,OAAO;AACjD,cAAM,QAAQ,WAAW,MAAM,MAAM,OAAO;AAC5C,YAAI,MAAO,QAAO,KAAK,KAAK;AAAA,MAC9B,QAAQ;AAAA,MAER;AAAA,IACF;AAAA,EACF,SAAS,KAAK;AACZ,YAAQ,KAAK,uCAAuC,SAAS,KAAK,GAAG;AAAA,EACvE;AAGA,SAAO,KAAK,CAAC,GAAG,MAAM,EAAE,WAAW,EAAE,QAAQ;AAG7C,eAAa;AAAA,IACX;AAAA,IACA,WAAW,KAAK,IAAI;AAAA,IACpB,KAAK;AAAA,EACP;AAEA,SAAO;AACT;AAEA,SAAS,WAAW,MAAc,SAA+B;AAC/D,QAAM,YAAY,QAAQ,MAAM,aAAa;AAC7C,QAAM,eAAe,QAAQ,MAAM,kBAAkB;AACrD,QAAM,gBAAgB,QAAQ,MAAM,oBAAoB;AACxD,MAAI,CAAC,UAAW,QAAO;AAEvB,SAAO;AAAA,IACL;AAAA,IACA,aAAa,UAAU,CAAC,KAAK;AAAA,IAC7B,SAAS,eAAe,CAAC,KAAK;AAAA,IAC9B,UAAU,gBAAgB,SAAS,cAAc,CAAC,GAAG,EAAE,IAAI;AAAA,IAC3D,cAAc;AAAA,EAChB;AACF;AAEO,SAAS,WAAW,QAAiB,aAAmC;AAC7E,QAAM,QAAQ,YAAY,YAAY;AACtC,QAAM,QAAQ,MAAM,MAAM,KAAK;AAE/B,aAAW,SAAS,QAAQ;AAC1B,QAAI,CAAC,MAAM,QAAS;AAEpB,UAAM,WAAW,MAAM,QAAQ,MAAM,GAAG,EAAE,IAAI,CAAC,MAAM,EAAE,KAAK,EAAE,YAAY,CAAC;AAE3E,eAAW,WAAW,UAAU;AAE9B,UAAI,MAAM,SAAS,OAAO,KAAK,MAAM,SAAS,IAAI,OAAO,GAAG,KAAK,MAAM,WAAW,GAAG,OAAO,GAAG,KAAK,MAAM,SAAS,IAAI,OAAO,EAAE,GAAG;AACjI,eAAO;AAAA,MACT;AAAA,IACF;AAAA,EACF;AAEA,SAAO;AACT;;;AFnFA,eAAsB,UACpB,OACA,MACe;AACf,QAAM,UAAU,IAAI,cAAc;AAClC,QAAM,YAAYE,MAAK,QAAQ,IAAI,GAAG,QAAQ;AAC9C,QAAM,SAAS,MAAM,WAAW,SAAS;AAEzC,MAAI;AACJ,MAAI,MAAM,WAAW;AACnB,UAAM,QAAQ,OAAO,KAAK,CAAC,MAAM,EAAE,SAAS,KAAK,SAAS;AAC1D,QAAI,MAAO,qBAAoB,MAAM;AAAA,EACvC;AAEA,QAAM,eAAe,IAAI,aAAa;AAAA,IACpC;AAAA,IACA;AAAA,IACA,aAAa,CAAC,SAAS,QAAQ,IAAI,MAAM,OAAO,YAAO,IAAI,KAAK,CAAC;AAAA,IACjE,WAAW,CAAC,OAAO,WAAuB;AACxC,UAAI,OAAO,MAAO,SAAQ,IAAI,MAAM,IAAI,YAAO,KAAK,KAAK,OAAO,KAAK,EAAE,CAAC;AAAA,UACnE,SAAQ,IAAI,MAAM,MAAM,YAAO,KAAK,EAAE,CAAC;AAAA,IAC9C;AAAA,EACF,CAAC;AAED,QAAM,KAAc,yBAAgB;AAAA,IAClC,OAAO,QAAQ;AAAA,IACf,QAAQ,QAAQ;AAAA,IAChB,QAAQ,MAAM,KAAK,UAAU;AAAA,EAC/B,CAAC;AAED,QAAM,OAAO,MAAM,KAAK;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,GAOvB;AAED,UAAQ,IAAI,IAAI;AAChB,UAAQ,IAAI,MAAM,KAAK,MAAM,4BAA4B,IAAI,MAAM,KAAK,SAAS,CAAC;AAClF,UAAQ,IAAI,MAAM,KAAK,kRAAiD,CAAC;AACzE,UAAQ,IAAI,MAAM,KAAK,cAAc,QAAQ,SAAS,EAAE,CAAC;AACzD,MAAI,OAAO,QAAQ;AACjB,YAAQ,IAAI,MAAM,KAAK,cAAc,OAAO,IAAI,CAAC,MAAM,EAAE,IAAI,EAAE,KAAK,IAAI,CAAC,EAAE,CAAC;AAAA,EAC9E;AACA,UAAQ,IAAI,MAAM,KAAK,kRAAiD,CAAC;AACzE,UAAQ,IAAI,MAAM,KAAK,6CAA6C,CAAC;AACrE,KAAG,OAAO;AAEV,KAAG,GAAG,QAAQ,OAAO,SAAS;AAC5B,UAAM,QAAQ,KAAK,KAAK;AACxB,QAAI,CAAC,OAAO;AACV,SAAG,OAAO;AACV;AAAA,IACF;AAEA,QAAI,MAAM,WAAW,GAAG,GAAG;AACzB,oBAAc,OAAO,cAAc,OAAO;AAC1C,SAAG,OAAO;AACV;AAAA,IACF;AAGA,QAAI,CAAC,mBAAmB;AACtB,YAAM,UAAU,WAAW,QAAQ,KAAK;AACxC,UAAI,SAAS;AACX,gBAAQ,IAAI,MAAM,KAAK,aAAa,QAAQ,IAAI,GAAG,CAAC;AAAA,MACtD;AAAA,IACF;AAEA,QAAI;AACF,cAAQ,OAAO,MAAM,MAAM,MAAM,IAAI,CAAC;AACtC,uBAAiB,SAAS,aAAa,UAAU,KAAK,GAAG;AACvD,gBAAQ,OAAO,MAAM,KAAK;AAAA,MAC5B;AACA,cAAQ,OAAO,MAAM,MAAM;AAG3B,YAAM,QAAQ,KAAK,aAAa,YAAY,CAAC;AAAA,IAC/C,SAAS,GAAQ;AACf,cAAQ,IAAI,MAAM,IAAI;AAAA,SAAY,EAAE,OAAO;AAAA,CAAI,CAAC;AAAA,IAClD;AAEA,OAAG,OAAO;AAAA,EACZ,CAAC;AAED,KAAG,GAAG,SAAS,MAAM;AACnB,YAAQ,IAAI,MAAM,KAAK,YAAY,CAAC;AACpC,YAAQ,KAAK,CAAC;AAAA,EAChB,CAAC;AACH;AAEA,SAAS,cACP,OACA,cACA,SACM;AACN,QAAM,MAAM,MAAM,MAAM,GAAG,EAAE,CAAC;AAC9B,UAAQ,KAAK;AAAA,IACX,KAAK;AACH,cAAQ;AAAA,QACN,MAAM,KAAK;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAOZ;AAAA,MACD;AACA;AAAA,IACF,KAAK;AACH,mBAAa,cAAc;AAC3B,cAAQ,IAAI,MAAM,KAAK,uBAAuB,CAAC;AAC/C;AAAA,IACF,KAAK;AACH,cAAQ,IAAI,MAAM,KAAK,aAAa,aAAa,YAAY,EAAE,MAAM,EAAE,CAAC;AACxE;AAAA,IACF,KAAK;AACH,cAAQ,KAAK,aAAa,YAAY,CAAC,EAAE,KAAK,MAAM;AAClD,gBAAQ,IAAI,MAAM,KAAK,gBAAgB,CAAC;AAAA,MAC1C,CAAC;AACD;AAAA,IACF,KAAK;AACH,cAAQ,IAAI,MAAM,KAAK,eAAe,QAAQ,SAAS,EAAE,CAAC;AAC1D;AAAA,IACF,KAAK;AACH,cAAQ,KAAK,CAAC;AAAA,IAChB;AACE,cAAQ,IAAI,MAAM,IAAI,oBAAoB,GAAG,EAAE,CAAC;AAAA,EACpD;AACF;;;ANpIA,SAAS,aAAqB;AAC5B,MAAI;AACF,UAAM,aAAa,cAAc,YAAY,GAAG;AAChD,UAAM,YAAY,QAAQ,UAAU;AACpC,UAAM,UAAUC,MAAK,WAAW,oBAAoB;AACpD,UAAM,MAAM,KAAK,MAAM,aAAa,SAAS,OAAO,CAAC;AACrD,WAAO,IAAI;AAAA,EACb,QAAQ;AACN,WAAO;AAAA,EACT;AACF;AAEO,SAAS,gBAAyB;AACvC,QAAM,UAAU,WAAW;AAC3B,QAAMC,WAAU,IAAI,QAAQ;AAE5B,EAAAA,SACG,KAAK,QAAQ,EACb,YAAY,4CAAuC,EACnD,QAAQ,OAAO,EACf,OAAO,uBAAuB,kDAAkD,EAChF,OAAO,uBAAuB,mBAAmB,EACjD,SAAS,eAAe,sCAAsC,EAC9D,OAAO,OAAO,QAAkB,SAA6C;AAC5E,UAAM,SAAS,MAAM,WAAW;AAChC,UAAM,WAAW,KAAK,SAAS,OAAO;AACtC,UAAM,EAAE,UAAU,MAAM,IAAI,iBAAiB,QAAQ;AACrD,UAAM,cAAc,OAAO,OAAO,QAAQ,KAAK,CAAC;AAChD,QAAI,MAAO,aAAY,QAAQ;AAC/B,UAAM,gBAAgB,eAAe,UAAU,WAAsC;AAErF,QAAI,OAAO,QAAQ;AACjB,YAAM,EAAE,cAAAC,cAAa,IAAI,MAAM,OAAO,4BAAyB;AAC/D,YAAM,OAAO,IAAIA,cAAa,EAAE,OAAO,cAAc,CAAC;AACtD,YAAM,SAAS,MAAM,KAAK,IAAI,OAAO,KAAK,GAAG,CAAC;AAC9C,cAAQ,IAAI,MAAM;AAAA,IACpB,OAAO;AACL,YAAM,UAAU,eAAe,EAAE,WAAW,KAAK,MAAM,CAAC;AAAA,IAC1D;AAAA,EACF,CAAC;AAEH,EAAAD,SACG,QAAQ,QAAQ,EAChB,YAAY,4BAA4B,EACxC,OAAO,YAAY;AAClB,UAAM,SAAS,MAAM,WAAW;AAChC,YAAQ,IAAI,KAAK,UAAU,QAAQ,MAAM,CAAC,CAAC;AAAA,EAC7C,CAAC;AAEH,SAAOA;AACT;;;ASvDA,IAAM,UAAU,cAAc;AAC9B,QAAQ,MAAM;","names":["join","join","readFile","writeFile","mkdir","join","homedir","readFile","join","join","join","program","Orchestrator"]}
|
package/package.json
CHANGED
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
# Content Creator
|
|
2
|
+
|
|
3
|
+
trigger: content, 内容, 文章, article, blog, 博客, 公众号, wechat, 写作, write
|
|
4
|
+
|
|
5
|
+
priority: 6
|
|
6
|
+
|
|
7
|
+
You are a content creation expert. Create professional content for various platforms.
|
|
8
|
+
|
|
9
|
+
## Content Types
|
|
10
|
+
|
|
11
|
+
### Articles & Blogs
|
|
12
|
+
- Technical blog posts
|
|
13
|
+
- Tutorial guides
|
|
14
|
+
- Industry analysis
|
|
15
|
+
- Product reviews
|
|
16
|
+
|
|
17
|
+
### Social Media
|
|
18
|
+
- WeChat articles (公众号)
|
|
19
|
+
- Twitter/X posts
|
|
20
|
+
- LinkedIn articles
|
|
21
|
+
- Xiaohongshu notes (小红书)
|
|
22
|
+
|
|
23
|
+
### Marketing
|
|
24
|
+
- Product descriptions
|
|
25
|
+
- Email newsletters
|
|
26
|
+
- Landing page copy
|
|
27
|
+
- Ad copy
|
|
28
|
+
|
|
29
|
+
## Writing Principles
|
|
30
|
+
|
|
31
|
+
### Structure
|
|
32
|
+
1. **Hook** - Grab attention in first paragraph
|
|
33
|
+
2. **Problem** - Identify the pain point
|
|
34
|
+
3. **Solution** - Provide value
|
|
35
|
+
4. **Evidence** - Support with data/examples
|
|
36
|
+
5. **CTA** - Clear call to action
|
|
37
|
+
|
|
38
|
+
### Style
|
|
39
|
+
- Clear and concise
|
|
40
|
+
- Active voice
|
|
41
|
+
- Short paragraphs
|
|
42
|
+
- Use subheadings
|
|
43
|
+
- Include visuals descriptions
|
|
44
|
+
|
|
45
|
+
## Platform Optimization
|
|
46
|
+
|
|
47
|
+
### WeChat (公众号)
|
|
48
|
+
- Title: 15-25 characters
|
|
49
|
+
- Summary: 50-100 characters
|
|
50
|
+
- Use images every 3-5 paragraphs
|
|
51
|
+
- End with interaction prompt
|
|
52
|
+
|
|
53
|
+
### Twitter/X
|
|
54
|
+
- Hook in first tweet
|
|
55
|
+
- Thread format for long content
|
|
56
|
+
- Use hashtags strategically
|
|
57
|
+
- Engage with replies
|
|
58
|
+
|
|
59
|
+
### Technical Blog
|
|
60
|
+
- Code examples
|
|
61
|
+
- Step-by-step tutorials
|
|
62
|
+
- Include prerequisites
|
|
63
|
+
- Provide source links
|
|
64
|
+
|
|
65
|
+
## Output Formats
|
|
66
|
+
- Markdown
|
|
67
|
+
- HTML
|
|
68
|
+
- Plain text
|
|
69
|
+
- Platform-specific format
|
|
70
|
+
|
|
71
|
+
## Workflow
|
|
72
|
+
1. Understand target audience
|
|
73
|
+
2. Research topic
|
|
74
|
+
3. Create outline
|
|
75
|
+
4. Write content
|
|
76
|
+
5. Optimize for platform
|
|
77
|
+
6. Review and refine
|
|
@@ -0,0 +1,76 @@
|
|
|
1
|
+
# Data Analyst
|
|
2
|
+
|
|
3
|
+
trigger: data, 数据, analysis, 分析, chart, 图表, visualization, 可视化, statistics, 统计
|
|
4
|
+
|
|
5
|
+
priority: 5
|
|
6
|
+
|
|
7
|
+
You are a data analysis expert. Analyze data and create visualizations.
|
|
8
|
+
|
|
9
|
+
## Analysis Types
|
|
10
|
+
|
|
11
|
+
### Descriptive Statistics
|
|
12
|
+
- Mean, median, mode
|
|
13
|
+
- Standard deviation
|
|
14
|
+
- Percentiles
|
|
15
|
+
- Distribution analysis
|
|
16
|
+
|
|
17
|
+
### Trend Analysis
|
|
18
|
+
- Time series
|
|
19
|
+
- Growth rates
|
|
20
|
+
- Seasonality
|
|
21
|
+
- Forecasting
|
|
22
|
+
|
|
23
|
+
### Comparative Analysis
|
|
24
|
+
- Year-over-year
|
|
25
|
+
- Period-over-period
|
|
26
|
+
- Benchmarking
|
|
27
|
+
- Segmentation
|
|
28
|
+
|
|
29
|
+
## Visualization Types
|
|
30
|
+
|
|
31
|
+
### Charts
|
|
32
|
+
- Line charts (trends)
|
|
33
|
+
- Bar charts (comparison)
|
|
34
|
+
- Pie charts (composition)
|
|
35
|
+
- Scatter plots (correlation)
|
|
36
|
+
- Heatmaps (patterns)
|
|
37
|
+
|
|
38
|
+
### Data Tables
|
|
39
|
+
- Summary tables
|
|
40
|
+
- Pivot tables
|
|
41
|
+
- Cross-tabulation
|
|
42
|
+
- Ranking tables
|
|
43
|
+
|
|
44
|
+
## Tools & Libraries
|
|
45
|
+
|
|
46
|
+
### Python
|
|
47
|
+
- pandas (data manipulation)
|
|
48
|
+
- matplotlib (basic charts)
|
|
49
|
+
- seaborn (statistical viz)
|
|
50
|
+
- plotly (interactive)
|
|
51
|
+
|
|
52
|
+
### JavaScript
|
|
53
|
+
- D3.js (custom visualizations)
|
|
54
|
+
- Chart.js (simple charts)
|
|
55
|
+
- Echarts (business charts)
|
|
56
|
+
|
|
57
|
+
## Output Formats
|
|
58
|
+
- PNG/SVG images
|
|
59
|
+
- Interactive HTML
|
|
60
|
+
- CSV/Excel exports
|
|
61
|
+
- PDF reports
|
|
62
|
+
|
|
63
|
+
## Best Practices
|
|
64
|
+
- Choose right chart type
|
|
65
|
+
- Label clearly
|
|
66
|
+
- Use consistent colors
|
|
67
|
+
- Include data source
|
|
68
|
+
- Add context/insights
|
|
69
|
+
|
|
70
|
+
## Workflow
|
|
71
|
+
1. Understand the question
|
|
72
|
+
2. Collect/clean data
|
|
73
|
+
3. Explore patterns
|
|
74
|
+
4. Create visualizations
|
|
75
|
+
5. Draw conclusions
|
|
76
|
+
6. Present findings
|
|
@@ -0,0 +1,75 @@
|
|
|
1
|
+
# Translator
|
|
2
|
+
|
|
3
|
+
trigger: translate, 翻译, 英文, 中文, english, chinese, localization, 本地化
|
|
4
|
+
|
|
5
|
+
priority: 4
|
|
6
|
+
|
|
7
|
+
You are a translation expert. Provide accurate, natural translations.
|
|
8
|
+
|
|
9
|
+
## Translation Principles
|
|
10
|
+
|
|
11
|
+
### Accuracy
|
|
12
|
+
- Preserve original meaning
|
|
13
|
+
- Handle idioms appropriately
|
|
14
|
+
- Maintain technical accuracy
|
|
15
|
+
- Context-aware translation
|
|
16
|
+
|
|
17
|
+
### Fluency
|
|
18
|
+
- Natural target language
|
|
19
|
+
- Proper grammar
|
|
20
|
+
- Appropriate style
|
|
21
|
+
- Cultural adaptation
|
|
22
|
+
|
|
23
|
+
### Consistency
|
|
24
|
+
- Use consistent terminology
|
|
25
|
+
- Follow glossaries
|
|
26
|
+
- Maintain tone
|
|
27
|
+
- Keep formatting
|
|
28
|
+
|
|
29
|
+
## Language Pairs
|
|
30
|
+
- Chinese ↔ English
|
|
31
|
+
- Technical documentation
|
|
32
|
+
- Marketing content
|
|
33
|
+
- Legal documents
|
|
34
|
+
- User interfaces
|
|
35
|
+
|
|
36
|
+
## Translation Types
|
|
37
|
+
|
|
38
|
+
### Technical
|
|
39
|
+
- API documentation
|
|
40
|
+
- Code comments
|
|
41
|
+
- README files
|
|
42
|
+
- User guides
|
|
43
|
+
|
|
44
|
+
### Marketing
|
|
45
|
+
- Website copy
|
|
46
|
+
- Product descriptions
|
|
47
|
+
- Social media
|
|
48
|
+
- Email campaigns
|
|
49
|
+
|
|
50
|
+
### Business
|
|
51
|
+
- Reports
|
|
52
|
+
- Presentations
|
|
53
|
+
- Contracts
|
|
54
|
+
- Correspondence
|
|
55
|
+
|
|
56
|
+
## Quality Checklist
|
|
57
|
+
- [ ] Meaning preserved
|
|
58
|
+
- [ ] Grammar correct
|
|
59
|
+
- [ ] Style appropriate
|
|
60
|
+
- [ ] Terms consistent
|
|
61
|
+
- [ ] Format maintained
|
|
62
|
+
|
|
63
|
+
## Tools Integration
|
|
64
|
+
- TM (Translation Memory)
|
|
65
|
+
- Glossaries
|
|
66
|
+
- Style guides
|
|
67
|
+
- QA tools
|
|
68
|
+
|
|
69
|
+
## Workflow
|
|
70
|
+
1. Understand source content
|
|
71
|
+
2. Identify target audience
|
|
72
|
+
3. Translate draft
|
|
73
|
+
4. Review for accuracy
|
|
74
|
+
5. Polish for fluency
|
|
75
|
+
6. Final proofread
|