openclaw-workflowskill 0.3.4 → 0.4.0

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 CHANGED
@@ -137,7 +137,7 @@ Workflow `tool` steps are forwarded to the **OpenClaw gateway** via `POST /tools
137
137
 
138
138
  The `workflowskill_llm` tool is built-in: it calls Anthropic directly using the API key from OpenClaw's credential store, and is always available.
139
139
 
140
- The plugin's own four tools (`workflowskill_validate`, `workflowskill_run`, `workflowskill_runs`, `workflowskill_llm`) are blocked from being forwarded to the gateway to prevent infinite recursion.
140
+ Only `workflowskill_run` is blocked from gateway forwarding — it is self-referencing and would create infinite recursion. The other three plugin tools (`workflowskill_validate`, `workflowskill_runs`, `workflowskill_llm`) are leaf operations and are forwarded normally.
141
141
 
142
142
  ## Tool Reference
143
143
 
@@ -184,7 +184,7 @@ Call Anthropic directly and return the text response. Uses the API key from Open
184
184
  | `prompt` | string | yes | The prompt to send to the LLM |
185
185
  | `model` | string | no | Model alias (`haiku`, `sonnet`, `opus`) or full model ID — omit to use the default |
186
186
 
187
- Returns `{ text: string }`.
187
+ Returns the LLM response as a plain text string.
188
188
 
189
189
  ## Development
190
190
 
package/index.ts CHANGED
@@ -208,7 +208,7 @@ export default {
208
208
  registerTool({
209
209
  name: 'workflowskill_llm',
210
210
  description:
211
- 'Call the Anthropic LLM and return { text }. ' +
211
+ 'Call the Anthropic LLM and return the response as plain text. ' +
212
212
  'Uses the API key from OpenClaw\'s credential store. ' +
213
213
  'Use in workflow tool steps when you need LLM reasoning inline. ' +
214
214
  'model is optional (haiku / sonnet / opus or full model ID); omit for haiku.',
package/lib/adapters.ts CHANGED
@@ -4,6 +4,19 @@
4
4
 
5
5
  import type { ToolAdapter, ToolDescriptor, ToolResult } from 'workflowskill';
6
6
 
7
+ /** Unwrap MCP text-content envelope so workflows see actual tool output. */
8
+ function unwrapMcpContent(body: unknown): unknown {
9
+ if (body !== null && typeof body === 'object' && 'content' in body) {
10
+ const { content } = body as { content: unknown };
11
+ if (Array.isArray(content) && content.length === 1
12
+ && content[0]?.type === 'text' && typeof content[0]?.text === 'string') {
13
+ try { return JSON.parse(content[0].text); }
14
+ catch { return content[0].text; }
15
+ }
16
+ }
17
+ return body;
18
+ }
19
+
7
20
  export interface GatewayConfig {
8
21
  baseUrl: string;
9
22
  token: string;
@@ -61,7 +74,7 @@ export class HostToolAdapter implements ToolAdapter {
61
74
 
62
75
  if (response.status === 200) {
63
76
  const result = (await response.json()) as unknown;
64
- return { output: result };
77
+ return { output: unwrapMcpContent(result) };
65
78
  }
66
79
  if (response.status === 404) {
67
80
  return { output: null, error: `Tool '${toolName}' not found or blocked by the gateway.` };
@@ -2,7 +2,7 @@
2
2
  "id": "openclaw-workflowskill",
3
3
  "name": "WorkflowSkill",
4
4
  "description": "Author, validate, run, and review WorkflowSkill YAML workflows",
5
- "version": "0.3.4",
5
+ "version": "0.4.0",
6
6
  "skills": ["skills/workflowskill-author"],
7
7
  "configSchema": {
8
8
  "type": "object",
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "openclaw-workflowskill",
3
- "version": "0.3.4",
3
+ "version": "0.4.0",
4
4
  "description": "WorkflowSkill plugin for OpenClaw — author, validate, run, and review YAML workflows",
5
5
  "type": "module",
6
6
  "main": "index.ts",
@@ -35,7 +35,7 @@
35
35
  ]
36
36
  },
37
37
  "dependencies": {
38
- "workflowskill": "^0.3.2"
38
+ "workflowskill": "^0.4.0"
39
39
  },
40
40
  "devDependencies": {
41
41
  "@types/node": "^25.3.0",
@@ -44,7 +44,6 @@
44
44
  },
45
45
  "scripts": {
46
46
  "typecheck": "tsc --noEmit --project tsconfig.json",
47
- "reset": "bash scripts/reset.sh",
48
47
  "prepublishOnly": "tsc --noEmit --project tsconfig.json"
49
48
  }
50
49
  }
package/tools/llm.ts CHANGED
@@ -9,10 +9,6 @@ export interface LlmParams {
9
9
  model?: string;
10
10
  }
11
11
 
12
- export interface LlmResult {
13
- text: string;
14
- }
15
-
16
12
  const MODEL_ALIASES: Record<string, string> = {
17
13
  haiku: 'claude-haiku-4-5-20251001',
18
14
  sonnet: 'claude-sonnet-4-6',
@@ -73,9 +69,8 @@ async function callAnthropic(apiKey: string, model: string, prompt: string): Pro
73
69
  return data.content.find((b) => b.type === 'text')?.text ?? '';
74
70
  }
75
71
 
76
- export async function llmHandler(params: LlmParams): Promise<LlmResult> {
72
+ export async function llmHandler(params: LlmParams): Promise<string> {
77
73
  const { prompt, model = DEFAULT_MODEL } = params;
78
74
  const apiKey = readAnthropicApiKey();
79
- const text = await callAnthropic(apiKey, model, prompt);
80
- return { text };
75
+ return callAnthropic(apiKey, model, prompt);
81
76
  }