- Rename build* → create* workflow factories - Workflow factories accept adapters: Record<string, AgentFn> - Each role file exports createXxxRole(adapter, ...) factory - _shared/workspace-committer accepts adapter as first param - All adapter imports moved to index.ts (injection point) - solve-issue roles also updated Closes #15
37 lines
1.4 KiB
TypeScript
37 lines
1.4 KiB
TypeScript
import type { AgentFn, Role, StartStep } from "@uncaged/nerve-core";
|
|
import type { LlmExtractorConfig } from "@uncaged/nerve-workflow-utils";
|
|
import { createRole } from "@uncaged/nerve-workflow-utils";
|
|
import { z } from "zod";
|
|
|
|
export const plannerMetaSchema = z.object({
|
|
senseName: z.string().describe("kebab-case sense name from the plan"),
|
|
});
|
|
export type PlannerMeta = z.infer<typeof plannerMetaSchema>;
|
|
|
|
export function plannerPrompt({ threadId }: { threadId: string }): string {
|
|
return `You are planning a new Nerve sense.
|
|
|
|
Read the workflow thread for the user's request: \`nerve thread ${threadId}\`
|
|
Read the nerve-dev skill for sense conventions: \`cat node_modules/@uncaged/nerve-skills/nerve-dev/SKILL.md\`
|
|
Also look at existing senses in the \`senses/\` directory for patterns.
|
|
|
|
Pick a good kebab-case name for this sense. Produce a PLAN (not code) in markdown:
|
|
|
|
## Sense Design
|
|
### Name — kebab-case
|
|
### Fields — name, type (integer/real/text), description
|
|
### Compute Logic — step-by-step, specific Node.js APIs or shell commands
|
|
### Trigger Config — group, interval, throttle, timeout
|
|
|
|
Output ONLY the plan. Be precise and implementation-ready.`;
|
|
}
|
|
|
|
export function createPlannerRole(adapter: AgentFn, extract: LlmExtractorConfig): Role<PlannerMeta> {
|
|
return createRole(
|
|
adapter,
|
|
async (start: StartStep) => plannerPrompt({ threadId: start.meta.threadId }),
|
|
plannerMetaSchema,
|
|
extract,
|
|
);
|
|
}
|