@saltcorn/agents 0.4.4 → 0.4.6

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/agent-view.js CHANGED
@@ -43,6 +43,7 @@ const {
43
43
  find_image_tool,
44
44
  is_debug_mode,
45
45
  get_initial_interactions,
46
+ get_skill_instances,
46
47
  } = require("./common");
47
48
  const MarkdownIt = require("markdown-it"),
48
49
  md = new MarkdownIt();
@@ -92,6 +93,7 @@ const configuration_workflow = (req) =>
92
93
  name: "stream",
93
94
  label: "Stream response",
94
95
  type: "Bool",
96
+ sublabel: "Requires dynamic update (Event settings)",
95
97
  },
96
98
  {
97
99
  name: "placeholder",
@@ -323,6 +325,14 @@ const run = async (
323
325
  }
324
326
  runInteractions = interactMarkups.join("");
325
327
  }
328
+ const skill_form_widgets = [];
329
+ for (const skill of get_skill_instances(action.configuration)) {
330
+ if (skill.formWidget)
331
+ skill_form_widgets.push(
332
+ await skill.formWidget({ user: req.user, klass: "skill-form-widget" })
333
+ );
334
+ }
335
+
326
336
  const debugMode = is_debug_mode(action.configuration, req.user);
327
337
  const input_form = form(
328
338
  {
@@ -337,10 +347,14 @@ const run = async (
337
347
  }),
338
348
  input({
339
349
  type: "hidden",
340
- class: "form-control ",
341
350
  name: "run_id",
342
351
  value: state.run_id ? +state.run_id : undefined,
343
352
  }),
353
+ input({
354
+ type: "hidden",
355
+ name: "page_load_tag",
356
+ value: "",
357
+ }),
344
358
  input({
345
359
  type: "hidden",
346
360
  class: "form-control ",
@@ -371,6 +385,7 @@ const run = async (
371
385
  onclick: "press_agent_debug_button()",
372
386
  class: "debugicon fas fa-bug",
373
387
  }),
388
+ skill_form_widgets,
374
389
  explainer && small({ class: "explainer" }, i(explainer))
375
390
  ),
376
391
  stream && div({ class: "next_response_scratch" })
@@ -457,6 +472,12 @@ const run = async (
457
472
  top: -1.8rem;
458
473
  left: 0.1rem;
459
474
  cursor: pointer;
475
+ }
476
+ .copilot-entry .skill-form-widget {
477
+ position: relative;
478
+ top: -2rem;
479
+ left: 0.4rem;
480
+ display: inline;
460
481
  }
461
482
  .session-open-sessions, .open-prev-runs {
462
483
  cursor: pointer;
@@ -484,15 +505,15 @@ const run = async (
484
505
  ),
485
506
  script(
486
507
  `
487
- function close_session_list() {
488
- $("div.prev-runs-list").hide().parents(".col-3").removeClass("col-3").addClass("was-col-3").parent().children(".col-9").removeClass("col-9").addClass("col-12")
489
- $("div.open-prev-runs").show()
490
- }
491
- function open_session_list() {
492
- $("div.prev-runs-list").show().parents(".was-col-3").removeClass(["was-col-3","col-0","d-none"]).addClass("col-3").parent().children(".col-12").removeClass("col-12").addClass("col-9")
493
- $("div.open-prev-runs").hide()
494
- }
495
- function processCopilotResponse(res) {
508
+ function close_session_list() {
509
+ $("div.prev-runs-list").hide().parents(".col-3").removeClass("col-3").addClass("was-col-3").parent().children(".col-9").removeClass("col-9").addClass("col-12")
510
+ $("div.open-prev-runs").show()
511
+ }
512
+ function open_session_list() {
513
+ $("div.prev-runs-list").show().parents(".was-col-3").removeClass(["was-col-3","col-0","d-none"]).addClass("col-3").parent().children(".col-12").removeClass("col-12").addClass("col-9")
514
+ $("div.open-prev-runs").hide()
515
+ }
516
+ function processCopilotResponse(res) {
496
517
  const hadFile = $("input#attach_agent_image").val();
497
518
  $("span.filename-label").text("");
498
519
  $("input#attach_agent_image").val(null);
@@ -566,6 +587,10 @@ const run = async (
566
587
  function spin_send_button() {
567
588
  $("#sendbuttonicon").attr("class","fas fa-spinner fa-spin");
568
589
  };`,
590
+ stream &&
591
+ domReady(
592
+ `$('form.agent-view input[name=page_load_tag]').val(window._sc_pageloadtag)`
593
+ ),
569
594
  initial_q && domReady("$('form.copilot').submit()")
570
595
  )
571
596
  )
@@ -692,13 +717,22 @@ const debug_info = async (table_id, viewname, config, body, { req, res }) => {
692
717
  if (table) triggering_row = await table.getRow({ [pk]: triggering_row_id });
693
718
  }
694
719
  const run = await WorkflowRun.findOne({ id: +run_id });
695
- const complArgs = await getCompletionArguments(
696
- action.configuration,
697
- req.user,
698
- triggering_row
699
- );
720
+ let sysPrompt = "";
721
+ if (
722
+ run.context.api_interactions?.[0].request?.messages?.[0]?.role === "system"
723
+ ) {
724
+ sysPrompt =
725
+ run.context.api_interactions?.[0].request?.messages?.[0].content;
726
+ } else {
727
+ const complArgs = await getCompletionArguments(
728
+ action.configuration,
729
+ req.user,
730
+ triggering_row
731
+ );
732
+ sysPrompt = complArgs.systemPrompt;
733
+ }
700
734
  const debug_html = div(
701
- div(h4("System prompt"), pre(complArgs.systemPrompt)),
735
+ div(h4("System prompt"), pre(sysPrompt)),
702
736
  div(
703
737
  h4("API interactions"),
704
738
  pre(JSON.stringify(run.context.api_interactions, null, 2))
package/common.js CHANGED
@@ -32,6 +32,7 @@ const get_skills = () => {
32
32
  require("./skills/PreloadData"),
33
33
  require("./skills/GenerateImage"),
34
34
  require("./skills/ModelContextProtocol"),
35
+ require("./skills/PromptPicker"),
35
36
  //require("./skills/AdaptiveFeedback"),
36
37
  ...exchange_skills,
37
38
  ];
@@ -90,7 +91,12 @@ const get_initial_interactions = async (config, user, triggering_row) => {
90
91
  return interacts;
91
92
  };
92
93
 
93
- const getCompletionArguments = async (config, user, triggering_row) => {
94
+ const getCompletionArguments = async (
95
+ config,
96
+ user,
97
+ triggering_row,
98
+ formbody
99
+ ) => {
94
100
  let tools = [];
95
101
 
96
102
  let sysPrompts = [
@@ -99,7 +105,11 @@ const getCompletionArguments = async (config, user, triggering_row) => {
99
105
 
100
106
  const skills = get_skill_instances(config);
101
107
  for (const skill of skills) {
102
- const sysPr = await skill.systemPrompt?.({ user, triggering_row });
108
+ const sysPr = await skill.systemPrompt?.({
109
+ ...(formbody || {}),
110
+ user,
111
+ triggering_row,
112
+ });
103
113
  if (sysPr) sysPrompts.push(sysPr);
104
114
  const skillTools = skill.provideTools?.();
105
115
  if (skillTools && Array.isArray(skillTools)) tools.push(...skillTools);
@@ -198,7 +208,8 @@ const process_interaction = async (
198
208
  const complArgs = await getCompletionArguments(
199
209
  config,
200
210
  req.user,
201
- triggering_row
211
+ triggering_row,
212
+ req.body
202
213
  );
203
214
  complArgs.chat = run.context.interactions.map(only_response_text_if_present);
204
215
  //complArgs.debugResult = true;
@@ -217,6 +228,7 @@ const process_interaction = async (
217
228
  eval_js: `$('form.agent-view div.next_response_scratch').append(${JSON.stringify(
218
229
  content
219
230
  )})`,
231
+ page_load_tag: req.body.page_load_tag,
220
232
  },
221
233
  [req.user.id]
222
234
  );
@@ -224,6 +236,8 @@ const process_interaction = async (
224
236
  }
225
237
  const answer = await sysState.functions.llm_generate.run("", complArgs);
226
238
 
239
+ //console.log({answer});
240
+
227
241
  if (debugMode)
228
242
  await addToContext(run, {
229
243
  api_interactions: [debugCollector],
@@ -306,6 +320,7 @@ const process_interaction = async (
306
320
  eval_js: `$('form.agent-view div.next_response_scratch').append(${JSON.stringify(
307
321
  content
308
322
  )})`,
323
+ page_load_tag: req.body.page_load_tag,
309
324
  },
310
325
  [req.user.id]
311
326
  );
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@saltcorn/agents",
3
- "version": "0.4.4",
3
+ "version": "0.4.6",
4
4
  "description": "AI agents for Saltcorn",
5
5
  "main": "index.js",
6
6
  "dependencies": {
@@ -69,7 +69,7 @@ class PreloadData {
69
69
  const table = Table.findOne(this.table_name);
70
70
  const q = eval_expression(
71
71
  this.preload_query,
72
- {},
72
+ triggering_row || {},
73
73
  user,
74
74
  "PreloadData query"
75
75
  );
@@ -0,0 +1,51 @@
1
+ const Workflow = require("@saltcorn/data/models/workflow");
2
+ const Form = require("@saltcorn/data/models/form");
3
+ const FieldRepeat = require("@saltcorn/data/models/fieldrepeat");
4
+ const { select, option } = require("@saltcorn/markup/tags");
5
+ const { eval_expression } = require("@saltcorn/data/models/expression");
6
+ const { validID } = require("@saltcorn/markup/layout_utils");
7
+
8
+ class PromptPicker {
9
+ static skill_name = "Prompt picker";
10
+ get skill_label() {
11
+ return `Prompt picker`;
12
+ }
13
+ constructor(cfg) {
14
+ Object.assign(this, cfg);
15
+ this.options = eval_expression(
16
+ this.options_obj,
17
+ {},
18
+ null,
19
+ "Prompt picker options"
20
+ );
21
+ this.formname = validID("pp" + Object.keys(this.options));
22
+ }
23
+ static async configFields() {
24
+ return [
25
+ { name: "placeholder", label: "Placeholder", type: "String" },
26
+ {
27
+ name: "options_obj",
28
+ label: "System prompt contents",
29
+ sublabel: `JavaScript object where the keys are the options and values are added to system prompt. Example:<br><code>{"Pirate":"Speak like a pirate", "Pop star":"Speak like a pop star"}</code>`,
30
+ type: "String",
31
+ fieldview: "textarea",
32
+ required: true,
33
+ },
34
+ ];
35
+ }
36
+ async formWidget({ user, klass }) {
37
+ return select(
38
+ {
39
+ class: ["form-select form-select-sm w-unset", klass],
40
+ name: this.formname,
41
+ },
42
+ this.placeholder && option({ disabled: true }, this.placeholder),
43
+ Object.keys(this.options).map((o) => option(o))
44
+ );
45
+ }
46
+ systemPrompt(body) {
47
+ if (body[this.formname]) return this.options[body[this.formname]];
48
+ }
49
+ }
50
+
51
+ module.exports = PromptPicker;