deepclause-sdk 0.0.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.
Files changed (111) hide show
  1. package/README.md +446 -0
  2. package/dist/agent.d.ts +44 -0
  3. package/dist/agent.d.ts.map +1 -0
  4. package/dist/agent.js +518 -0
  5. package/dist/agent.js.map +1 -0
  6. package/dist/cli/commands.d.ts +37 -0
  7. package/dist/cli/commands.d.ts.map +1 -0
  8. package/dist/cli/commands.js +105 -0
  9. package/dist/cli/commands.js.map +1 -0
  10. package/dist/cli/compile.d.ts +88 -0
  11. package/dist/cli/compile.d.ts.map +1 -0
  12. package/dist/cli/compile.js +362 -0
  13. package/dist/cli/compile.js.map +1 -0
  14. package/dist/cli/config.d.ts +265 -0
  15. package/dist/cli/config.d.ts.map +1 -0
  16. package/dist/cli/config.js +272 -0
  17. package/dist/cli/config.js.map +1 -0
  18. package/dist/cli/index.d.ts +8 -0
  19. package/dist/cli/index.d.ts.map +1 -0
  20. package/dist/cli/index.js +287 -0
  21. package/dist/cli/index.js.map +1 -0
  22. package/dist/cli/mcp.d.ts +56 -0
  23. package/dist/cli/mcp.d.ts.map +1 -0
  24. package/dist/cli/mcp.js +138 -0
  25. package/dist/cli/mcp.js.map +1 -0
  26. package/dist/cli/prompt.d.ts +20 -0
  27. package/dist/cli/prompt.d.ts.map +1 -0
  28. package/dist/cli/prompt.js +669 -0
  29. package/dist/cli/prompt.js.map +1 -0
  30. package/dist/cli/run.d.ts +33 -0
  31. package/dist/cli/run.d.ts.map +1 -0
  32. package/dist/cli/run.js +429 -0
  33. package/dist/cli/run.js.map +1 -0
  34. package/dist/cli/search.d.ts +25 -0
  35. package/dist/cli/search.d.ts.map +1 -0
  36. package/dist/cli/search.js +125 -0
  37. package/dist/cli/search.js.map +1 -0
  38. package/dist/cli/tools.d.ts +36 -0
  39. package/dist/cli/tools.d.ts.map +1 -0
  40. package/dist/cli/tools.js +204 -0
  41. package/dist/cli/tools.js.map +1 -0
  42. package/dist/cli/tui/index.d.ts +22 -0
  43. package/dist/cli/tui/index.d.ts.map +1 -0
  44. package/dist/cli/tui/index.js +29 -0
  45. package/dist/cli/tui/index.js.map +1 -0
  46. package/dist/index.d.ts +9 -0
  47. package/dist/index.d.ts.map +1 -0
  48. package/dist/index.js +8 -0
  49. package/dist/index.js.map +1 -0
  50. package/dist/prolog/bridge.d.ts +21 -0
  51. package/dist/prolog/bridge.d.ts.map +1 -0
  52. package/dist/prolog/bridge.js +226 -0
  53. package/dist/prolog/bridge.js.map +1 -0
  54. package/dist/prolog/loader.d.ts +40 -0
  55. package/dist/prolog/loader.d.ts.map +1 -0
  56. package/dist/prolog/loader.js +133 -0
  57. package/dist/prolog/loader.js.map +1 -0
  58. package/dist/prolog-src/deepclause_memory.pl +45 -0
  59. package/dist/prolog-src/deepclause_mi.pl +1978 -0
  60. package/dist/prolog-src/deepclause_mi.pl.bak +570 -0
  61. package/dist/prolog-src/deepclause_strings.pl +89 -0
  62. package/dist/runner.d.ts +143 -0
  63. package/dist/runner.d.ts.map +1 -0
  64. package/dist/runner.js +1095 -0
  65. package/dist/runner.js.map +1 -0
  66. package/dist/sdk.d.ts +9 -0
  67. package/dist/sdk.d.ts.map +1 -0
  68. package/dist/sdk.js +131 -0
  69. package/dist/sdk.js.map +1 -0
  70. package/dist/tools.d.ts +22 -0
  71. package/dist/tools.d.ts.map +1 -0
  72. package/dist/tools.js +138 -0
  73. package/dist/tools.js.map +1 -0
  74. package/dist/types.d.ts +186 -0
  75. package/dist/types.d.ts.map +1 -0
  76. package/dist/types.js +5 -0
  77. package/dist/types.js.map +1 -0
  78. package/package.json +79 -0
  79. package/src/prolog-src/deepclause_memory.pl +45 -0
  80. package/src/prolog-src/deepclause_mi.pl +1978 -0
  81. package/src/prolog-src/deepclause_mi.pl.bak +570 -0
  82. package/src/prolog-src/deepclause_strings.pl +89 -0
  83. package/vendor/swipl-wasm/LICENSE.txt +41 -0
  84. package/vendor/swipl-wasm/dist/bin/index.js +25 -0
  85. package/vendor/swipl-wasm/dist/common.d.ts +88 -0
  86. package/vendor/swipl-wasm/dist/generateImage.d.ts +6 -0
  87. package/vendor/swipl-wasm/dist/generateImage.js +76 -0
  88. package/vendor/swipl-wasm/dist/index.d.ts +2 -0
  89. package/vendor/swipl-wasm/dist/index.js +1 -0
  90. package/vendor/swipl-wasm/dist/loadImage.d.ts +2 -0
  91. package/vendor/swipl-wasm/dist/loadImage.js +10 -0
  92. package/vendor/swipl-wasm/dist/loadImageDefault.d.ts +2 -0
  93. package/vendor/swipl-wasm/dist/loadImageDefault.js +11 -0
  94. package/vendor/swipl-wasm/dist/strToBuffer.d.ts +8 -0
  95. package/vendor/swipl-wasm/dist/strToBuffer.js +41 -0
  96. package/vendor/swipl-wasm/dist/swipl/swipl-bundle-no-data.d.ts +2 -0
  97. package/vendor/swipl-wasm/dist/swipl/swipl-bundle-no-data.js +2 -0
  98. package/vendor/swipl-wasm/dist/swipl/swipl-bundle.d.ts +2 -0
  99. package/vendor/swipl-wasm/dist/swipl/swipl-bundle.js +2 -0
  100. package/vendor/swipl-wasm/dist/swipl/swipl-web.d.ts +2 -0
  101. package/vendor/swipl-wasm/dist/swipl/swipl-web.data +0 -0
  102. package/vendor/swipl-wasm/dist/swipl/swipl-web.js +2 -0
  103. package/vendor/swipl-wasm/dist/swipl/swipl-web.wasm +0 -0
  104. package/vendor/swipl-wasm/dist/swipl/swipl-win.js +1 -0
  105. package/vendor/swipl-wasm/dist/swipl/swipl-win.wasm +0 -0
  106. package/vendor/swipl-wasm/dist/swipl/swipl.d.ts +2 -0
  107. package/vendor/swipl-wasm/dist/swipl/swipl.js +1 -0
  108. package/vendor/swipl-wasm/dist/swipl/swipl.wasm +0 -0
  109. package/vendor/swipl-wasm/dist/swipl-node.d.ts +2 -0
  110. package/vendor/swipl-wasm/dist/swipl-node.js +17 -0
  111. package/vendor/swipl-wasm/package.json +129 -0
@@ -0,0 +1,669 @@
1
+ /**
2
+ * DeepClause CLI - MD to DML Conversion Prompt
3
+ *
4
+ * Contains the base prompt template for converting Markdown task descriptions to DML.
5
+ */
6
+ // =============================================================================
7
+ // Prompt Template
8
+ // =============================================================================
9
+ export const DML_CONVERSION_PROMPT = `# Markdown to DML Conversion Prompt
10
+
11
+ You are an expert DML (DeepClause Meta Language) programmer. Your task is to convert
12
+ natural language task descriptions written in Markdown into executable DML programs.
13
+
14
+ ## Tool Types in DML
15
+
16
+ There are two kinds of tools in DML:
17
+
18
+ ### 1. DML Tool Wrappers (via \`tool/3\`)
19
+ These are predicates you define in DML using the \`tool/3\` syntax. They are pure DML logic
20
+ and typically wrap one or more external tools for convenience or composition. They are
21
+ **not** registered as external dependencies.
22
+
23
+ \`\`\`prolog
24
+ tool(search(Query, Results), "Search the web for information") :-
25
+ exec(web_search(query: Query), Results).
26
+ \`\`\`
27
+
28
+ ### 2. External Tools (MCP/AgentVM)
29
+ These are provided by the runtime (via MCP servers or built-in AgentVM) and are invoked
30
+ directly with \`exec/2\`. Only these are registered as dependencies in the meta file.
31
+
32
+ ## Available External Tools
33
+
34
+ {TOOLS_TABLE}
35
+
36
+ **Note:** Only tools invoked via \`exec/2\` that correspond to external MCP or AgentVM
37
+ tools are registered as dependencies. DML tool wrappers are not registered unless they
38
+ call external tools.
39
+
40
+ ## DML Language Overview
41
+
42
+ DML is a simplified Prolog dialect designed for AI agent programming. It combines
43
+ declarative logic programming with LLM-powered task execution.
44
+
45
+ ### Program Structure
46
+
47
+ Every DML program must have an \`agent_main\` entry point that accepts 0+ arguments:
48
+
49
+ \`\`\`prolog
50
+ % No arguments
51
+ agent_main :- ...
52
+
53
+ % One argument
54
+ agent_main(Topic) :- ...
55
+
56
+ % Two arguments (alphabetical order for dict unpacking)
57
+ agent_main(MaxResults, Topic) :- ...
58
+ \`\`\`
59
+
60
+ ### Core Predicates
61
+
62
+ #### Task Execution
63
+
64
+ | Predicate | Description |
65
+ |-----------|-------------|
66
+ | \`task(Description)\` | Execute an LLM task with accumulated memory |
67
+ | \`task(Description, Var)\` | Execute task, bind result to Var |
68
+ | \`task(Description, Var1, Var2)\` | Execute task, bind two results |
69
+ | \`task(Description, Var1, Var2, Var3)\` | Execute task, bind three results |
70
+
71
+ **Important:** Variable names in the description must match the Prolog variables:
72
+ \`\`\`prolog
73
+ task("Analyze this and store the result in Summary.", Summary)
74
+ \`\`\`
75
+
76
+ #### Fresh LLM Calls (No Memory)
77
+
78
+ | Predicate | Description |
79
+ |-----------|-------------|
80
+ | \`prompt(Description)\` | Execute LLM with **empty memory** (fresh context) |
81
+ | \`prompt(Description, Var)\` | Fresh LLM call, bind result to Var |
82
+ | \`prompt(Description, Var1, Var2)\` | Fresh LLM call, bind two results |
83
+ | \`prompt(Description, Var1, Var2, Var3)\` | Fresh LLM call, bind three results |
84
+
85
+ **When to use \`prompt()\` vs \`task()\`:**
86
+ - Use \`task()\` when you want the LLM to have context from previous \`system()\`, \`user()\`, and \`task()\` calls
87
+ - Use \`prompt()\` when you want a completely fresh LLM call without any prior conversation context
88
+
89
+ \`\`\`prolog
90
+ agent_main :-
91
+ system("You are a helpful assistant."),
92
+ task("What is 2+2?"), % LLM sees the system message
93
+ prompt("What is 3+3?"). % LLM does NOT see any prior context
94
+ \`\`\`
95
+
96
+ #### Direct Tool Execution
97
+
98
+ | Predicate | Description |
99
+ |-----------|-------------|
100
+ | \`exec(Tool, Result)\` | Execute external tool directly |
101
+
102
+ \`\`\`prolog
103
+ exec(web_search(query: "AI news"), Results)
104
+ exec(vm_exec(command: "echo hello"), Result)
105
+ \`\`\`
106
+
107
+ **Important:** \`vm_exec\` returns a dict with \`stdout\`, \`stderr\`, and \`exitCode\` fields.
108
+ Use \`get_dict/3\` to extract values:
109
+ \`\`\`prolog
110
+ exec(vm_exec(command: "echo hello"), Result),
111
+ get_dict(stdout, Result, Output),
112
+ output(Output).
113
+ \`\`\`
114
+
115
+ **VM Working Directory:** The VM starts with the working directory set to \`/workspace\`, which is
116
+ mounted to your actual workspace. Files are directly accessible:
117
+ \`\`\`prolog
118
+ exec(vm_exec(command: "cat README.md"), Result), % Reads workspace/README.md
119
+ get_dict(stdout, Result, Content).
120
+ \`\`\`
121
+
122
+ #### Memory Management
123
+
124
+ | Predicate | Description |
125
+ |-----------|-------------|
126
+ | \`system(Text)\` | Add system message (LLM instructions) |
127
+ | \`user(Text)\` | Add user message to context |
128
+ | \`push_context\` | Save memory state (for isolation) |
129
+ | \`push_context(clear)\` | Save and clear memory |
130
+ | \`pop_context\` | Restore previous memory state |
131
+ | \`clear_memory\` | Clear all accumulated memory |
132
+
133
+ **Note:** Memory is automatically restored on backtracking, so \`push_context\`/\`pop_context\`
134
+ are primarily useful for manual isolation within a clause.
135
+
136
+ #### Output
137
+
138
+ | Predicate | Description |
139
+ |-----------|-------------|
140
+ | \`output(Text)\` | Emit progress/intermediate output |
141
+ | \`yield(Text)\` | Alias for output/1 |
142
+ | \`log(Text)\` | Emit debug/log message |
143
+ | \`answer(Text)\` | Emit final answer (commits execution) |
144
+
145
+ #### Tool Definitions
146
+
147
+ Define tools that the LLM can call during \`task()\`:
148
+
149
+ \`\`\`prolog
150
+ % Tool wrapper (description is second arg, body calls exec)
151
+ tool(search(Query, Results), "Search the web for information") :-
152
+ exec(web_search(query: Query), Results).
153
+ \`\`\`
154
+ #### Using \`task()\` and \`prompt()\` Inside Tools
155
+
156
+ Tools can use \`task()\` or \`prompt()\` internally to combine Prolog logic with LLM reasoning:
157
+
158
+ \`\`\`prolog
159
+ % A tool that computes then explains
160
+ tool(explain_calculation(A, B, Explanation), "Calculate and explain the result") :-
161
+ Sum is A + B, % Prolog computation
162
+ format(string(Desc), "Explain ~w + ~w = ~w to a child", [A, B, Sum]),
163
+ task(Desc, Explanation). % LLM explanation
164
+ \`\`\`
165
+
166
+ **Memory Isolation:** Nested \`task()\` calls inside tools run with **fresh memory** - they
167
+ do NOT have access to the parent's accumulated memory. If you need context, either:
168
+ 1. Pass it as a tool argument
169
+ 2. Add it explicitly with \`system()\` inside the tool
170
+
171
+ \`\`\`prolog
172
+ % Pass context explicitly as an argument
173
+ tool(analyze_with_context(Context, Data, Result), "Analyze data with given context") :-
174
+ system(Context), % Add context to this tool's memory
175
+ format(string(Desc), "Analyze: ~w", [Data]),
176
+ task(Desc, Result).
177
+ \`\`\`
178
+
179
+ **Automatic Recursion Prevention:** When \`task()\` runs inside a tool, the nested agent
180
+ cannot call the tool that is currently executing. This prevents infinite recursion.
181
+
182
+ #### Tool Scoping
183
+
184
+ Control which tools are available to nested \`task()\` calls:
185
+
186
+ | Predicate | Description |
187
+ |-----------|-------------|
188
+ | \`with_tools(ToolList, Goal)\` | Run Goal with only specified tools available |
189
+ | \`without_tools(ToolList, Goal)\` | Run Goal excluding specified tools |
190
+
191
+ \`\`\`prolog
192
+ % Only allow search tool in nested task
193
+ tool(safe_research(Topic, Result), "Research with limited tools") :-
194
+ with_tools([search], (
195
+ format(string(Desc), "Research ~w using search", [Topic]),
196
+ task(Desc, Result)
197
+ )).
198
+
199
+ % Exclude expensive tools from nested task
200
+ tool(cheap_task(Input, Output), "Process without expensive tools") :-
201
+ without_tools([expensive_api], (
202
+ task("Process {Input} cheaply", Output)
203
+ )).
204
+ \`\`\`
205
+ #### Built-in Agent Tools
206
+
207
+ During \`task()\` execution, the LLM has access to these built-in tools:
208
+
209
+ | Tool | Description |
210
+ |------|-------------|
211
+ | \`store(variable, value)\` | Store a result in an output variable |
212
+ | \`ask_user(prompt)\` | Ask the user for input or clarification |
213
+ | \`finish(success)\` | Complete the task |
214
+
215
+ **Important:** If your task might need user input (clarification, choices, confirmation),
216
+ you should define an \`ask_user\` tool wrapper so the LLM can request input:
217
+
218
+ \`\`\`prolog
219
+ % Define ask_user wrapper so LLM can request user input during task()
220
+ tool(ask_user(Prompt, Response), "Ask the user a question and get their response") :-
221
+ exec(ask_user(prompt: Prompt), Result),
222
+ get_dict(user_response, Result, Response).
223
+ \`\`\`
224
+
225
+ ### String Interpolation
226
+
227
+ DML supports **automatic string interpolation** using \`{Variable}\` syntax in task descriptions
228
+ and output predicates. This is the preferred method:
229
+
230
+ \`\`\`prolog
231
+ agent_main(Topic) :-
232
+ task("Research the topic: {Topic}"),
233
+ output("Finished researching {Topic}"),
234
+ answer("Done").
235
+ \`\`\`
236
+
237
+ **IMPORTANT:** Never mix \`{Variable}\` interpolation with \`format/3\`. Choose one approach:
238
+
239
+ **Option 1: String Interpolation (preferred for simple cases)**
240
+ \`\`\`prolog
241
+ % Variables are automatically substituted
242
+ task("Analyze {Data} and summarize in Summary.", Summary),
243
+ output("Analysis complete for {Data}")
244
+ \`\`\`
245
+
246
+ **Option 2: format/3 for complex string building (Prolog-style)**
247
+ \`\`\`prolog
248
+ % format/3 writes to a string variable - use ~w for terms, ~s for strings
249
+ format(string(Message), "Found ~d results for query: ~w", [Count, Query]),
250
+ output(Message)
251
+ \`\`\`
252
+
253
+ **WRONG - Never do this:**
254
+ \`\`\`prolog
255
+ % DON'T mix interpolation and format
256
+ output(format("Value: {X}", [X])) % WRONG! format doesn't return a value
257
+
258
+ % DON'T use {Var} inside format strings
259
+ format(string(S), "Topic: {Topic}", []) % WRONG! Use ~w instead
260
+ \`\`\`
261
+
262
+ ### Control Flow
263
+
264
+ \`\`\`prolog
265
+ % Conjunction (and)
266
+ goal1, goal2, goal3
267
+
268
+ % Disjunction (or)
269
+ (goal1 ; goal2)
270
+
271
+ % If-then-else
272
+ (Condition -> Then ; Else)
273
+
274
+ % Negation as failure
275
+ \\+ goal
276
+
277
+ % Cut (commit to this branch)
278
+ !
279
+
280
+ % Exception handling
281
+ catch(Goal, Error, Recovery)
282
+ throw(some_error)
283
+ \`\`\`
284
+
285
+ ### Backtracking
286
+
287
+ DML supports full Prolog backtracking across LLM calls:
288
+
289
+ \`\`\`prolog
290
+ % Try multiple approaches
291
+ agent_main :-
292
+ ( try_approach_1
293
+ ; try_approach_2 % Falls back if first fails
294
+ ; fallback_approach
295
+ ),
296
+ answer("Done").
297
+ \`\`\`
298
+
299
+ ### List Processing
300
+
301
+ \`\`\`prolog
302
+ % Recursive list processing
303
+ process_items([]).
304
+ process_items([H|T]) :-
305
+ process_one(H),
306
+ process_items(T).
307
+
308
+ % Using findall
309
+ findall(X, some_condition(X), Results)
310
+
311
+ % Using maplist
312
+ maplist(process_one, Items)
313
+ \`\`\`
314
+
315
+ ---
316
+
317
+ ## Common Patterns
318
+
319
+ ### Pattern 1: Simple Task Agent
320
+ \`\`\`prolog
321
+ agent_main(Topic) :-
322
+ system("You are a helpful research assistant."),
323
+ task("Research {Topic} and provide a comprehensive summary."),
324
+ answer("Research complete!").
325
+ \`\`\`
326
+
327
+ ### Pattern 2: Multi-Step Workflow
328
+ \`\`\`prolog
329
+ agent_main(Topic) :-
330
+ system("You are a thorough research assistant."),
331
+
332
+ output("Step 1: Gathering information..."),
333
+ task("Search for recent information about {Topic}. Store findings in Findings.", Findings),
334
+
335
+ output("Step 2: Analyzing..."),
336
+ task("Analyze these findings: {Findings}. Store your analysis in Analysis.", Analysis),
337
+
338
+ output("Step 3: Generating report..."),
339
+ task("Create a comprehensive report based on this analysis: {Analysis}"),
340
+
341
+ answer("Report generated!").
342
+ \`\`\`
343
+
344
+ ### Pattern 3: Tool-Enabled Agent
345
+ \`\`\`prolog
346
+ tool(search(Query, Results), "Search the web") :-
347
+ exec(web_search(query: Query), Results).
348
+
349
+ agent_main(Topic) :-
350
+ system("You are a research assistant with web search. Use the search tool."),
351
+ task("Research {Topic} using available tools."),
352
+ answer("Research complete!").
353
+ \`\`\`
354
+
355
+ ### Pattern 3b: Tool with Nested LLM Call
356
+ \`\`\`prolog
357
+ % A tool that uses LLM to analyze search results
358
+ tool(smart_search(Query, Summary), "Search and summarize results") :-
359
+ exec(web_search(query: Query), Results),
360
+ format(string(Desc), "Summarize these search results: ~w", [Results]),
361
+ task(Desc, Summary). % Nested task CANNOT call smart_search (recursion prevention)
362
+
363
+ agent_main(Topic) :-
364
+ system("Use smart_search to research topics."),
365
+ task("Research {Topic}."),
366
+ answer("Done!").
367
+ \`\`\`
368
+
369
+ ### Pattern 4: Code Execution (Use Sparingly!)
370
+ \`\`\`prolog
371
+ % ONLY use exec/Python when you need:
372
+ % - External packages (pandas, numpy, etc.)
373
+ % - Shell commands (find, grep, sed, awk, curl)
374
+ % - Complex imperative logic that's awkward in Prolog
375
+ %
376
+ % NOTE: vm_exec returns a dict with stdout, stderr, exitCode - use get_dict to extract
377
+ % NOTE: The VM starts in /workspace which is your actual workspace directory
378
+
379
+ agent_main(Task) :-
380
+ system("You are a coding assistant."),
381
+
382
+ task("Write Python code to solve: {Task}. Store only the code in Code.", Code),
383
+
384
+ % Write code to a file in the workspace (VM cwd is /workspace)
385
+ open('script.py', write, S),
386
+ write(S, Code),
387
+ close(S),
388
+
389
+ output("Executing code..."),
390
+ exec(vm_exec(command: "python3 script.py"), Result), % Runs in /workspace
391
+ get_dict(stdout, Result, Output),
392
+
393
+ task("Explain this execution result: {Output}"),
394
+
395
+ answer("Done!").
396
+ \`\`\`
397
+
398
+ ### Pattern 5: Data Analysis with VM
399
+ \`\`\`prolog
400
+ % Good use of exec: requires pandas package
401
+ % NOTE: vm_exec returns a dict - use get_dict to extract stdout
402
+ agent_main(CsvPath, Question) :-
403
+ system("You are a data analyst."),
404
+
405
+ output("Setting up environment..."),
406
+ exec(vm_exec(command: "pip install pandas"), _),
407
+
408
+ output("Analyzing data..."),
409
+ task("Write Python code to load {CsvPath} with pandas and answer: {Question}. Store only the code in Code.", Code),
410
+
411
+ % Write code to file and execute
412
+ open('analysis.py', write, S),
413
+ write(S, Code),
414
+ close(S),
415
+ exec(vm_exec(command: "python3 analysis.py"), Result),
416
+ get_dict(stdout, Result, Output),
417
+
418
+ task("Interpret and explain these analysis results: {Output}"),
419
+
420
+ answer("Analysis complete!").
421
+ \`\`\`
422
+
423
+ ### Pattern 6: File I/O (Use Prolog, NOT Python!)
424
+ \`\`\`prolog
425
+ % GOOD: Use Prolog's native file I/O
426
+ agent_main(Content) :-
427
+ task("Generate a report about {Content}. Store in Report.", Report),
428
+
429
+ % Write to file using Prolog (not Python!)
430
+ open('output.md', write, Stream),
431
+ write(Stream, Report),
432
+ close(Stream),
433
+
434
+ answer("Report saved to output.md").
435
+
436
+ % Build filename from parts
437
+ agent_main(Name, Content) :-
438
+ task("Generate content about {Name}. Store in Text.", Text),
439
+
440
+ % Construct filename using atom operations
441
+ atom_string(NameAtom, Name),
442
+ atom_concat(NameAtom, '_report.md', FilenameAtom),
443
+ atom_string(FilenameAtom, Filename),
444
+
445
+ open(Filename, write, Stream),
446
+ write(Stream, Text),
447
+ close(Stream),
448
+
449
+ output("Saved to {Filename}"),
450
+ answer("Done!").
451
+ \`\`\`
452
+
453
+ ### Pattern 7: Using format/3 for Complex Strings
454
+ \`\`\`prolog
455
+ % When you need to build strings with numbers or complex formatting
456
+ agent_main(Items) :-
457
+ length(Items, Count),
458
+ format(string(StatusMsg), "Processing ~d items", [Count]),
459
+ output(StatusMsg),
460
+
461
+ process_all(Items),
462
+
463
+ format(string(DoneMsg), "Completed processing ~d items successfully", [Count]),
464
+ answer(DoneMsg).
465
+ \`\`\`
466
+
467
+ ### Pattern 8: Interactive Agent (User Input)
468
+ \`\`\`prolog
469
+ % When the task may need user clarification or choices
470
+ % Define ask_user wrapper so LLM can interact with user
471
+ tool(ask_user(Prompt, Response), "Ask the user a question") :-
472
+ exec(ask_user(prompt: Prompt), Result),
473
+ get_dict(user_response, Result, Response).
474
+
475
+ agent_main(Task) :-
476
+ system("You are a helpful assistant. If you need clarification, use the ask_user tool."),
477
+
478
+ task("Help the user with: {Task}. If anything is unclear, ask for clarification."),
479
+
480
+ answer("Task completed!").
481
+ \`\`\`
482
+
483
+ ### Pattern 9: Error Handling with catch/throw
484
+ \`\`\`prolog
485
+ % Safe tool call with error recovery
486
+ agent_main(Query) :-
487
+ catch(
488
+ (
489
+ exec(web_search(query: Query), Results),
490
+ task("Summarize: {Results}")
491
+ ),
492
+ Error,
493
+ (
494
+ format(string(ErrMsg), "Search failed: ~w. Proceeding without search.", [Error]),
495
+ output(ErrMsg),
496
+ task("Answer based on your knowledge: {Query}")
497
+ )
498
+ ),
499
+ answer("Done!").
500
+ \`\`\`
501
+
502
+ ### Pattern 10: Fresh Context with prompt()
503
+ \`\`\`prolog
504
+ % Use prompt() for independent sub-tasks that shouldn't share context
505
+ agent_main(Topic) :-
506
+ system("You are a research assistant."),
507
+
508
+ % Main research with accumulated context
509
+ task("Research {Topic} deeply.", MainFindings),
510
+
511
+ % Independent critique - fresh context, no bias from main research
512
+ prompt("As a skeptical reviewer, critique this research: {MainFindings}. Store critique in Critique.", Critique),
513
+
514
+ % Back to main context for final synthesis
515
+ task("Address this critique: {Critique}"),
516
+
517
+ answer("Research complete with peer review!").
518
+ \`\`\`
519
+
520
+ ---
521
+
522
+ ## When to Use exec() vs Prolog
523
+
524
+ ### Use Prolog Native Functionality For:
525
+ - **File I/O**: \`open/3\`, \`write/2\`, \`read/2\`, \`close/1\`
526
+ - **String manipulation**: \`atom_concat/3\`, \`atom_string/2\`, \`split_string/4\`
527
+ - **List operations**: \`append/3\`, \`member/2\`, \`findall/3\`, \`maplist/2\`
528
+ - **Arithmetic**: \`is/2\`, comparison operators
529
+ - **Logic and control flow**: conjunctions, disjunctions, conditionals
530
+
531
+ ### Use exec() ONLY For:
532
+ - **External packages**: pandas, numpy, requests, matplotlib, etc.
533
+ - **Shell commands**: find, grep, sed, awk, curl, git
534
+ - **System operations**: environment variables, process management
535
+ - **Complex imperative logic**: loops with side effects, mutable state
536
+
537
+ ### BAD Example - Unnecessary Python:
538
+ \`\`\`prolog
539
+ % DON'T do this - Python for simple file writing
540
+ exec(vm_exec(command: "python3 -c \"open('out.txt','w').write('hello')\""), _)
541
+ \`\`\`
542
+
543
+ ### GOOD Example - Use Prolog:
544
+ \`\`\`prolog
545
+ % DO this instead - native Prolog file I/O
546
+ open('out.txt', write, S),
547
+ write(S, Content),
548
+ close(S)
549
+ \`\`\`
550
+
551
+ ---
552
+
553
+ ## Conversion Guidelines
554
+
555
+ 1. **Identify the core task** - What is the primary goal?
556
+ 2. **Determine parameters** - What inputs does the agent need?
557
+ 3. **Map to patterns** - Which DML pattern best fits?
558
+ 4. **Prefer Prolog native operations** - Use Prolog for file I/O, strings, lists
559
+ 5. **Use exec() sparingly** - Only for packages, shell commands, imperative logic
560
+ 6. **Define required tools** - What external capabilities are needed?
561
+ 7. **Handle edge cases** - Add fallbacks and error handling
562
+ 8. **Add progress output** - Keep users informed with \`output/1\`
563
+ 9. **Add ask_user wrapper** - If the task might need user input, clarification, or choices
564
+
565
+ ## CRITICAL: String Handling Rules
566
+
567
+ **NEVER do any of these:**
568
+ - \`output(format(...))\` - format/3 doesn't return a value, it binds to first arg
569
+ - \`answer(format(...))\` - same issue
570
+ - Mixing \`{Var}\` and \`~w\` in the same string
571
+ - Using \`{Var}\` inside format/3 format strings
572
+
573
+ **DO this instead:**
574
+ - Use \`{Variable}\` interpolation directly: \`output("Processing {Item}")\`
575
+ - Or use format/3 properly: \`format(string(Msg), "Count: ~d", [N]), output(Msg)\`
576
+
577
+ ## CRITICAL: Prolog vs exec() Rules
578
+
579
+ **Use Prolog for:**
580
+ - File I/O: \`open/3\`, \`write/2\`, \`close/1\`
581
+ - String building: \`atom_concat/3\`, \`atom_string/2\`
582
+ - All standard logic and data manipulation
583
+
584
+ **Use exec() ONLY for:**
585
+ - External packages (pandas, numpy)
586
+ - Shell commands (grep, curl, find)
587
+ - Complex imperative tasks
588
+
589
+ ## Output Requirements
590
+
591
+ Your DML output must:
592
+
593
+ 1. Start with a comment header describing the program
594
+ 2. Define any tool wrappers needed with \`tool/3\`
595
+ 3. **If the task may need user input, define an \`ask_user\` tool wrapper**
596
+ 4. Have a single \`agent_main\` entry point
597
+ 5. Use appropriate system prompts
598
+ 6. Include progress outputs for long-running tasks
599
+ 7. End with \`answer/1\` to signal completion
600
+ 8. Handle stated edge cases
601
+ 9. **Only use tools from the Available External Tools list**
602
+ 10. **Use ONLY {Variable} interpolation OR format/3, never mix them**
603
+ 11. **NEVER pass format(...) directly to output/1 or answer/1**
604
+ 12. **Use Prolog native file I/O, NOT Python exec() for simple file operations**
605
+
606
+ Output ONLY the DML code, no explanations or markdown code fences.
607
+ `;
608
+ // =============================================================================
609
+ // Tool Table Building
610
+ // =============================================================================
611
+ /**
612
+ * Build the tools table for the prompt
613
+ */
614
+ export function buildToolsTable(tools) {
615
+ if (tools.length === 0) {
616
+ return 'No additional tools configured.';
617
+ }
618
+ const lines = [];
619
+ // Group by provider
620
+ const byProvider = new Map();
621
+ for (const tool of tools) {
622
+ const existing = byProvider.get(tool.provider) || [];
623
+ existing.push(tool);
624
+ byProvider.set(tool.provider, existing);
625
+ }
626
+ for (const [provider, providerTools] of byProvider) {
627
+ const isBuiltIn = provider === 'agentvm';
628
+ lines.push(`### ${isBuiltIn ? 'Built-in Tools (AgentVM)' : `${provider} (MCP)`}`);
629
+ lines.push('');
630
+ lines.push('| Tool | Description |');
631
+ lines.push('|------|-------------|');
632
+ for (const tool of providerTools) {
633
+ // Format tool signature
634
+ let signature = tool.name;
635
+ if (tool.schema && typeof tool.schema === 'object') {
636
+ const schema = tool.schema;
637
+ if (schema.properties) {
638
+ const params = Object.keys(schema.properties).join(', ');
639
+ signature = `${tool.name}(${params})`;
640
+ }
641
+ }
642
+ lines.push(`| \`${signature}\` | ${tool.description} |`);
643
+ }
644
+ lines.push('');
645
+ }
646
+ return lines.join('\n');
647
+ }
648
+ /**
649
+ * Build the complete compilation prompt with tools injected
650
+ */
651
+ export function buildCompilationPrompt(tools) {
652
+ const toolsTable = buildToolsTable(tools);
653
+ return DML_CONVERSION_PROMPT.replace('{TOOLS_TABLE}', toolsTable);
654
+ }
655
+ /**
656
+ * Build the user message containing the markdown to convert
657
+ */
658
+ export function buildUserMessage(markdown) {
659
+ return `Convert the following Markdown task description into a DML program:
660
+
661
+ ---
662
+
663
+ ${markdown}
664
+
665
+ ---
666
+
667
+ Output only valid DML code.`;
668
+ }
669
+ //# sourceMappingURL=prompt.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"prompt.js","sourceRoot":"","sources":["../../src/cli/prompt.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,33 @@
1
+ /**
2
+ * DeepClause CLI - Execution Module
3
+ *
4
+ * Executes compiled DML programs with full tool support.
5
+ */
6
+ import type { DMLEvent } from '../types.js';
7
+ import { type Provider } from './config.js';
8
+ export interface RunOptions {
9
+ workspace?: string;
10
+ verbose?: boolean;
11
+ stream?: boolean;
12
+ headless?: boolean;
13
+ trace?: string;
14
+ dryRun?: boolean;
15
+ model?: string;
16
+ provider?: Provider;
17
+ temperature?: number;
18
+ params?: Record<string, string>;
19
+ }
20
+ export interface RunResult {
21
+ output: string[];
22
+ answer?: string;
23
+ error?: string;
24
+ dryRun?: boolean;
25
+ wouldExecute?: string;
26
+ trace?: object;
27
+ events?: DMLEvent[];
28
+ }
29
+ /**
30
+ * Execute a compiled DML program
31
+ */
32
+ export declare function run(file: string, args: string[], options?: RunOptions): Promise<RunResult>;
33
+ //# sourceMappingURL=run.d.ts.map