@promptbook/remote-server 0.105.0-0 → 0.105.0-3

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 (41) hide show
  1. package/esm/index.es.js +3890 -153
  2. package/esm/index.es.js.map +1 -1
  3. package/esm/typings/src/_packages/core.index.d.ts +2 -0
  4. package/esm/typings/src/_packages/types.index.d.ts +4 -0
  5. package/esm/typings/src/book-2.0/agent-source/AgentBasicInformation.d.ts +10 -3
  6. package/esm/typings/src/book-2.0/agent-source/AgentModelRequirements.d.ts +11 -1
  7. package/esm/typings/src/book-2.0/agent-source/communication-samples.test.d.ts +1 -0
  8. package/esm/typings/src/book-2.0/agent-source/createAgentModelRequirementsWithCommitments.blocks.test.d.ts +1 -0
  9. package/esm/typings/src/book-2.0/agent-source/createAgentModelRequirementsWithCommitments.import.test.d.ts +1 -0
  10. package/esm/typings/src/book-2.0/agent-source/parseAgentSource.import.test.d.ts +1 -0
  11. package/esm/typings/src/book-2.0/agent-source/parseAgentSourceWithCommitments.blocks.test.d.ts +1 -0
  12. package/esm/typings/src/commitments/USE_TIME/USE_TIME.d.ts +40 -0
  13. package/esm/typings/src/commitments/USE_TIME/USE_TIME.test.d.ts +1 -0
  14. package/esm/typings/src/commitments/_base/BaseCommitmentDefinition.d.ts +8 -0
  15. package/esm/typings/src/commitments/_base/CommitmentDefinition.d.ts +8 -0
  16. package/esm/typings/src/commitments/index.d.ts +11 -2
  17. package/esm/typings/src/config.d.ts +1 -0
  18. package/esm/typings/src/import-plugins/$fileImportPlugins.d.ts +7 -0
  19. package/esm/typings/src/import-plugins/AgentFileImportPlugin.d.ts +7 -0
  20. package/esm/typings/src/import-plugins/FileImportPlugin.d.ts +24 -0
  21. package/esm/typings/src/import-plugins/JsonFileImportPlugin.d.ts +7 -0
  22. package/esm/typings/src/import-plugins/TextFileImportPlugin.d.ts +7 -0
  23. package/esm/typings/src/llm-providers/_common/utils/cache/cacheLlmTools.d.ts +2 -1
  24. package/esm/typings/src/llm-providers/_common/utils/count-total-usage/countUsage.d.ts +2 -2
  25. package/esm/typings/src/llm-providers/agent/Agent.d.ts +9 -2
  26. package/esm/typings/src/llm-providers/agent/AgentLlmExecutionTools.d.ts +3 -1
  27. package/esm/typings/src/llm-providers/openai/OpenAiAssistantExecutionTools.d.ts +10 -0
  28. package/esm/typings/src/llm-providers/remote/RemoteLlmExecutionTools.d.ts +1 -1
  29. package/esm/typings/src/scripting/javascript/JavascriptExecutionToolsOptions.d.ts +6 -1
  30. package/esm/typings/src/types/ModelRequirements.d.ts +6 -12
  31. package/esm/typings/src/utils/execCommand/$execCommandNormalizeOptions.d.ts +2 -3
  32. package/esm/typings/src/utils/execCommand/ExecCommandOptions.d.ts +7 -1
  33. package/esm/typings/src/utils/organization/keepImported.d.ts +9 -0
  34. package/esm/typings/src/utils/organization/keepTypeImported.d.ts +0 -1
  35. package/esm/typings/src/utils/random/$generateBookBoilerplate.d.ts +4 -0
  36. package/esm/typings/src/utils/random/$randomAgentPersona.d.ts +2 -1
  37. package/esm/typings/src/utils/random/$randomAgentRule.d.ts +14 -0
  38. package/esm/typings/src/version.d.ts +1 -1
  39. package/package.json +2 -2
  40. package/umd/index.umd.js +3890 -153
  41. package/umd/index.umd.js.map +1 -1
package/umd/index.umd.js CHANGED
@@ -47,7 +47,7 @@
47
47
  * @generated
48
48
  * @see https://github.com/webgptorg/promptbook
49
49
  */
50
- const PROMPTBOOK_ENGINE_VERSION = '0.105.0-0';
50
+ const PROMPTBOOK_ENGINE_VERSION = '0.105.0-3';
51
51
  /**
52
52
  * TODO: string_promptbook_version should be constrained to the all versions of Promptbook engine
53
53
  * Note: [💞] Ignore a discrepancy between file name and entity name
@@ -1000,6 +1000,7 @@
1000
1000
  SEPARATOR: Color.fromHex('#cccccc'),
1001
1001
  COMMITMENT: Color.fromHex('#DA0F78'),
1002
1002
  PARAMETER: Color.fromHex('#8e44ad'),
1003
+ CODE_BLOCK: Color.fromHex('#7700ffff'),
1003
1004
  });
1004
1005
  // <- TODO: [🧠][🈵] Using `Color` here increases the package size approx 3kb, maybe remove it
1005
1006
  /**
@@ -1222,6 +1223,7 @@
1222
1223
  let args = [];
1223
1224
  let timeout;
1224
1225
  let isVerbose;
1226
+ let env;
1225
1227
  if (typeof options === 'string') {
1226
1228
  // TODO: [1] DRY default values
1227
1229
  command = options;
@@ -1229,6 +1231,7 @@
1229
1231
  crashOnError = true;
1230
1232
  timeout = Infinity; // <- TODO: [⏳]
1231
1233
  isVerbose = DEFAULT_IS_VERBOSE;
1234
+ env = undefined;
1232
1235
  }
1233
1236
  else {
1234
1237
  /*
@@ -1245,6 +1248,7 @@
1245
1248
  crashOnError = (_b = options.crashOnError) !== null && _b !== void 0 ? _b : true;
1246
1249
  timeout = (_c = options.timeout) !== null && _c !== void 0 ? _c : Infinity;
1247
1250
  isVerbose = (_d = options.isVerbose) !== null && _d !== void 0 ? _d : DEFAULT_IS_VERBOSE;
1251
+ env = options.env;
1248
1252
  }
1249
1253
  // TODO: /(-[a-zA-Z0-9-]+\s+[^\s]*)|[^\s]*/g
1250
1254
  const _ = Array.from(command.matchAll(/(".*")|([^\s]*)/g))
@@ -1263,7 +1267,7 @@
1263
1267
  if (/^win/.test(process.platform) && ['npm', 'npx'].includes(command)) {
1264
1268
  command = `${command}.cmd`;
1265
1269
  }
1266
- return { command, humanReadableCommand, args, cwd, crashOnError, timeout, isVerbose };
1270
+ return { command, humanReadableCommand, args, cwd, crashOnError, timeout, isVerbose, env };
1267
1271
  }
1268
1272
  // TODO: This should show type error> execCommandNormalizeOptions({ command: '', commands: [''] });
1269
1273
 
@@ -1284,7 +1288,7 @@
1284
1288
  }
1285
1289
  return new Promise((resolve, reject) => {
1286
1290
  // eslint-disable-next-line prefer-const
1287
- const { command, humanReadableCommand, args, cwd, crashOnError, timeout, isVerbose = DEFAULT_IS_VERBOSE, } = $execCommandNormalizeOptions(options);
1291
+ const { command, humanReadableCommand, args, cwd, crashOnError, timeout, isVerbose = DEFAULT_IS_VERBOSE, env, } = $execCommandNormalizeOptions(options);
1288
1292
  if (timeout !== Infinity) {
1289
1293
  // TODO: In waitasecond forTime(Infinity) should be equivalent to forEver()
1290
1294
  waitasecond.forTime(timeout).then(() => {
@@ -1302,7 +1306,11 @@
1302
1306
  console.info(colors__default["default"].yellow(cwd) + ' ' + colors__default["default"].green(command) + ' ' + colors__default["default"].blue(args.join(' ')));
1303
1307
  }
1304
1308
  try {
1305
- const commandProcess = child_process.spawn(command, args, { cwd, shell: true });
1309
+ const commandProcess = child_process.spawn(command, args, {
1310
+ cwd,
1311
+ shell: true,
1312
+ env: env ? { ...process.env, ...env } : process.env,
1313
+ });
1306
1314
  if (isVerbose) {
1307
1315
  commandProcess.on('message', (message) => {
1308
1316
  console.info({ message });
@@ -3792,74 +3800,90 @@
3792
3800
  * in real-time through an observable.
3793
3801
  *
3794
3802
  * @param llmTools - The LLM tools to be intercepted and tracked
3795
- * @returns An augmented version of the tools that includes usage tracking capabilities
3803
+ * @returns Full proxy of the tools with added usage tracking capabilities
3796
3804
  * @public exported from `@promptbook/core`
3797
3805
  */
3798
3806
  function countUsage(llmTools) {
3799
3807
  let totalUsage = ZERO_USAGE;
3800
3808
  const spending = new rxjs.Subject();
3801
- const proxyTools = {
3802
- get title() {
3803
- return `${llmTools.title} (+usage)`;
3804
- // <- TODO: [🧈] Maybe standartize the suffix when wrapping `LlmExecutionTools` up
3805
- // <- TODO: [🧈][🧠] Does it make sense to suffix "(+usage)"?
3806
- },
3807
- get description() {
3808
- return `${llmTools.description} (+usage)`;
3809
- // <- TODO: [🧈] Maybe standartize the suffix when wrapping `LlmExecutionTools` up
3810
- // <- TODO: [🧈][🧠] Does it make sense to suffix "(+usage)"?
3811
- },
3812
- checkConfiguration() {
3813
- return /* not await */ llmTools.checkConfiguration();
3814
- },
3815
- listModels() {
3816
- return /* not await */ llmTools.listModels();
3817
- },
3818
- spending() {
3819
- return spending.asObservable();
3820
- },
3821
- getTotalUsage() {
3822
- // <- Note: [🥫] Not using getter `get totalUsage` but `getTotalUsage` to allow this object to be proxied
3823
- return totalUsage;
3809
+ // Create a Proxy to intercept all property access and ensure full proxying of all properties
3810
+ const proxyTools = new Proxy(llmTools, {
3811
+ get(target, prop, receiver) {
3812
+ // Handle title property
3813
+ if (prop === 'title') {
3814
+ return `${target.title} (+usage)`;
3815
+ // <- TODO: [🧈] Maybe standartize the suffix when wrapping `LlmExecutionTools` up
3816
+ // <- TODO: [🧈][🧠] Does it make sense to suffix "(+usage)"?
3817
+ }
3818
+ // Handle description property
3819
+ if (prop === 'description') {
3820
+ return `${target.description} (+usage)`;
3821
+ // <- TODO: [🧈] Maybe standartize the suffix when wrapping `LlmExecutionTools` up
3822
+ // <- TODO: [🧈][🧠] Does it make sense to suffix "(+usage)"?
3823
+ }
3824
+ // Handle spending method (new method added by this wrapper)
3825
+ if (prop === 'spending') {
3826
+ return () => {
3827
+ return spending.asObservable();
3828
+ };
3829
+ }
3830
+ // Handle getTotalUsage method (new method added by this wrapper)
3831
+ if (prop === 'getTotalUsage') {
3832
+ // <- Note: [🥫] Not using getter `get totalUsage` but `getTotalUsage` to allow this object to be proxied
3833
+ return () => {
3834
+ return totalUsage;
3835
+ };
3836
+ }
3837
+ // Handle callChatModel method with usage counting
3838
+ if (prop === 'callChatModel' && target.callChatModel !== undefined) {
3839
+ return async (prompt) => {
3840
+ // console.info('[🚕] callChatModel through countTotalUsage');
3841
+ const promptResult = await target.callChatModel(prompt);
3842
+ totalUsage = addUsage(totalUsage, promptResult.usage);
3843
+ spending.next(promptResult.usage);
3844
+ return promptResult;
3845
+ };
3846
+ }
3847
+ // Handle callCompletionModel method with usage counting
3848
+ if (prop === 'callCompletionModel' && target.callCompletionModel !== undefined) {
3849
+ return async (prompt) => {
3850
+ // console.info('[🚕] callCompletionModel through countTotalUsage');
3851
+ const promptResult = await target.callCompletionModel(prompt);
3852
+ totalUsage = addUsage(totalUsage, promptResult.usage);
3853
+ spending.next(promptResult.usage);
3854
+ return promptResult;
3855
+ };
3856
+ }
3857
+ // Handle callEmbeddingModel method with usage counting
3858
+ if (prop === 'callEmbeddingModel' && target.callEmbeddingModel !== undefined) {
3859
+ return async (prompt) => {
3860
+ // console.info('[🚕] callEmbeddingModel through countTotalUsage');
3861
+ const promptResult = await target.callEmbeddingModel(prompt);
3862
+ totalUsage = addUsage(totalUsage, promptResult.usage);
3863
+ spending.next(promptResult.usage);
3864
+ return promptResult;
3865
+ };
3866
+ }
3867
+ // Handle callImageGenerationModel method with usage counting
3868
+ if (prop === 'callImageGenerationModel' && target.callImageGenerationModel !== undefined) {
3869
+ return async (prompt) => {
3870
+ // console.info('[🚕] callImageGenerationModel through countTotalUsage');
3871
+ const promptResult = await target.callImageGenerationModel(prompt);
3872
+ totalUsage = addUsage(totalUsage, promptResult.usage);
3873
+ spending.next(promptResult.usage);
3874
+ return promptResult;
3875
+ };
3876
+ }
3877
+ // <- Note: [🤖]
3878
+ // For all other properties and methods, delegate to the original target
3879
+ const value = Reflect.get(target, prop, receiver);
3880
+ // If it's a function, bind it to the target to preserve context
3881
+ if (typeof value === 'function') {
3882
+ return value.bind(target);
3883
+ }
3884
+ return value;
3824
3885
  },
3825
- };
3826
- if (llmTools.callChatModel !== undefined) {
3827
- proxyTools.callChatModel = async (prompt) => {
3828
- // console.info('[🚕] callChatModel through countTotalUsage');
3829
- const promptResult = await llmTools.callChatModel(prompt);
3830
- totalUsage = addUsage(totalUsage, promptResult.usage);
3831
- spending.next(promptResult.usage);
3832
- return promptResult;
3833
- };
3834
- }
3835
- if (llmTools.callCompletionModel !== undefined) {
3836
- proxyTools.callCompletionModel = async (prompt) => {
3837
- // console.info('[🚕] callCompletionModel through countTotalUsage');
3838
- const promptResult = await llmTools.callCompletionModel(prompt);
3839
- totalUsage = addUsage(totalUsage, promptResult.usage);
3840
- spending.next(promptResult.usage);
3841
- return promptResult;
3842
- };
3843
- }
3844
- if (llmTools.callEmbeddingModel !== undefined) {
3845
- proxyTools.callEmbeddingModel = async (prompt) => {
3846
- // console.info('[🚕] callEmbeddingModel through countTotalUsage');
3847
- const promptResult = await llmTools.callEmbeddingModel(prompt);
3848
- totalUsage = addUsage(totalUsage, promptResult.usage);
3849
- spending.next(promptResult.usage);
3850
- return promptResult;
3851
- };
3852
- }
3853
- if (llmTools.callImageGenerationModel !== undefined) {
3854
- proxyTools.callImageGenerationModel = async (prompt) => {
3855
- // console.info('[🚕] callImageGenerationModel through countTotalUsage');
3856
- const promptResult = await llmTools.callImageGenerationModel(prompt);
3857
- totalUsage = addUsage(totalUsage, promptResult.usage);
3858
- spending.next(promptResult.usage);
3859
- return promptResult;
3860
- };
3861
- }
3862
- // <- Note: [🤖]
3886
+ });
3863
3887
  return proxyTools;
3864
3888
  }
3865
3889
  /**
@@ -8202,135 +8226,3837 @@
8202
8226
  */
8203
8227
 
8204
8228
  /**
8205
- * Extracts exactly ONE code block from markdown.
8229
+ * Tests if given string is valid agent URL
8206
8230
  *
8207
- * - When there are multiple or no code blocks the function throws a `ParseError`
8208
- *
8209
- * Note: There are multiple similar functions:
8210
- * - `extractBlock` just extracts the content of the code block which is also used as built-in function for postprocessing
8211
- * - `extractJsonBlock` extracts exactly one valid JSON code block
8212
- * - `extractOneBlockFromMarkdown` extracts exactly one code block with language of the code block
8213
- * - `extractAllBlocksFromMarkdown` extracts all code blocks with language of the code block
8231
+ * Note: There are few similar functions:
8232
+ * - `isValidUrl` which tests any URL
8233
+ * - `isValidAgentUrl` *(this one)* which tests just agent URL
8234
+ * - `isValidPipelineUrl` which tests just pipeline URL
8214
8235
  *
8215
- * @param markdown any valid markdown
8216
- * @returns code block with language and content
8217
- * @public exported from `@promptbook/markdown-utils`
8218
- * @throws {ParseError} if there is not exactly one code block in the markdown
8236
+ * @public exported from `@promptbook/utils`
8219
8237
  */
8220
- function extractOneBlockFromMarkdown(markdown) {
8221
- const codeBlocks = extractAllBlocksFromMarkdown(markdown);
8222
- if (codeBlocks.length !== 1) {
8223
- throw new ParseError(spaceTrim__default["default"]((block) => `
8224
- There should be exactly 1 code block in task section, found ${codeBlocks.length} code blocks
8225
-
8226
- ${block(codeBlocks.map((block, i) => `Block ${i + 1}:\n${block.content}`).join('\n\n\n'))}
8227
- `));
8238
+ function isValidAgentUrl(url) {
8239
+ if (!isValidUrl(url)) {
8240
+ return false;
8228
8241
  }
8229
- return codeBlocks[0];
8242
+ if (!url.startsWith('https://') && !url.startsWith('http://') /* <- Note: [👣] */) {
8243
+ return false;
8244
+ }
8245
+ if (url.includes('#')) {
8246
+ // TODO: [🐠]
8247
+ return false;
8248
+ }
8249
+ /*
8250
+ Note: [👣][🧠] Is it secure to allow pipeline URLs on private and unsecured networks?
8251
+ if (isUrlOnPrivateNetwork(url)) {
8252
+ return false;
8253
+ }
8254
+ */
8255
+ return true;
8230
8256
  }
8231
- /***
8232
- * TODO: [🍓][🌻] Decide of this is internal utility, external util OR validator/postprocessor
8257
+ /**
8258
+ * TODO: [🐠] Maybe more info why the URL is invalid
8233
8259
  */
8234
8260
 
8235
8261
  /**
8236
- * Extracts code block from markdown.
8262
+ * Generates a regex pattern to match a specific commitment
8237
8263
  *
8238
- * - When there are multiple or no code blocks the function throws a `ParseError`
8264
+ * Note: It always creates new Regex object
8265
+ * Note: Uses word boundaries to ensure only full words are matched (e.g., "PERSONA" matches but "PERSONALITY" does not)
8239
8266
  *
8240
- * Note: There are multiple similar function:
8241
- * - `extractBlock` just extracts the content of the code block which is also used as build-in function for postprocessing
8242
- * - `extractJsonBlock` extracts exactly one valid JSON code block
8243
- * - `extractOneBlockFromMarkdown` extracts exactly one code block with language of the code block
8244
- * - `extractAllBlocksFromMarkdown` extracts all code blocks with language of the code block
8267
+ * @private - TODO: [🧠] Maybe should be public?
8268
+ */
8269
+ function createCommitmentRegex(commitment, aliases = [], requiresContent = true) {
8270
+ const allCommitments = [commitment, ...aliases];
8271
+ const patterns = allCommitments.map((commitment) => {
8272
+ const escapedCommitment = commitment.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
8273
+ return escapedCommitment.split(/\s+/).join('\\s+');
8274
+ });
8275
+ const keywordPattern = patterns.join('|');
8276
+ if (requiresContent) {
8277
+ return new RegExp(`^\\s*(?<type>${keywordPattern})\\b\\s+(?<contents>.+)$`, 'gim');
8278
+ }
8279
+ else {
8280
+ return new RegExp(`^\\s*(?<type>${keywordPattern})\\b(?:\\s+(?<contents>.+))?$`, 'gim');
8281
+ }
8282
+ }
8283
+ /**
8284
+ * Generates a regex pattern to match a specific commitment type
8245
8285
  *
8246
- * @public exported from `@promptbook/markdown-utils`
8247
- * @throws {ParseError} if there is not exactly one code block in the markdown
8286
+ * Note: It just matches the type part of the commitment
8287
+ * Note: It always creates new Regex object
8288
+ * Note: Uses word boundaries to ensure only full words are matched (e.g., "PERSONA" matches but "PERSONALITY" does not)
8289
+ *
8290
+ * @private
8248
8291
  */
8249
- function extractBlock(markdown) {
8250
- const { content } = extractOneBlockFromMarkdown(markdown);
8251
- return content;
8292
+ function createCommitmentTypeRegex(commitment, aliases = []) {
8293
+ const allCommitments = [commitment, ...aliases];
8294
+ const patterns = allCommitments.map((commitment) => {
8295
+ const escapedCommitment = commitment.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
8296
+ return escapedCommitment.split(/\s+/).join('\\s+');
8297
+ });
8298
+ const keywordPattern = patterns.join('|');
8299
+ const regex = new RegExp(`^\\s*(?<type>${keywordPattern})\\b`, 'gim');
8300
+ return regex;
8252
8301
  }
8253
8302
 
8254
8303
  /**
8255
- * Function trimCodeBlock will trim starting and ending code block from the string if it is present.
8256
- *
8257
- * Note: [🔂] This function is idempotent.
8258
- * Note: This is useful for post-processing of the result of the chat LLM model
8259
- * when the model wraps the result in the (markdown) code block.
8304
+ * Base implementation of CommitmentDefinition that provides common functionality
8305
+ * Most commitments can extend this class and only override the applyToAgentModelRequirements method
8260
8306
  *
8261
- * @public exported from `@promptbook/markdown-utils`
8307
+ * @private
8262
8308
  */
8263
- function trimCodeBlock(value) {
8264
- value = spaceTrim$1.spaceTrim(value);
8265
- if (!/^```[a-z]*(.*)```$/is.test(value)) {
8266
- return value;
8309
+ class BaseCommitmentDefinition {
8310
+ constructor(type, aliases = []) {
8311
+ this.type = type;
8312
+ this.aliases = aliases;
8313
+ }
8314
+ /**
8315
+ * Whether this commitment requires content.
8316
+ * If true, regex will match only if there is content after the commitment keyword.
8317
+ * If false, regex will match even if there is no content.
8318
+ */
8319
+ get requiresContent() {
8320
+ return true;
8321
+ }
8322
+ /**
8323
+ * Creates a regex pattern to match this commitment in agent source
8324
+ * Uses the existing createCommitmentRegex function as internal helper
8325
+ */
8326
+ createRegex() {
8327
+ return createCommitmentRegex(this.type, this.aliases, this.requiresContent);
8328
+ }
8329
+ /**
8330
+ * Creates a regex pattern to match just the commitment type
8331
+ * Uses the existing createCommitmentTypeRegex function as internal helper
8332
+ */
8333
+ createTypeRegex() {
8334
+ return createCommitmentTypeRegex(this.type, this.aliases);
8335
+ }
8336
+ /**
8337
+ * Helper method to create a new requirements object with updated system message
8338
+ * This is commonly used by many commitments
8339
+ */
8340
+ updateSystemMessage(requirements, messageUpdate) {
8341
+ const newMessage = typeof messageUpdate === 'string' ? messageUpdate : messageUpdate(requirements.systemMessage);
8342
+ return {
8343
+ ...requirements,
8344
+ systemMessage: newMessage,
8345
+ };
8346
+ }
8347
+ /**
8348
+ * Helper method to append content to the system message
8349
+ */
8350
+ appendToSystemMessage(requirements, content, separator = '\n\n') {
8351
+ return this.updateSystemMessage(requirements, (currentMessage) => {
8352
+ if (!currentMessage.trim()) {
8353
+ return content;
8354
+ }
8355
+ return currentMessage + separator + content;
8356
+ });
8357
+ }
8358
+ /**
8359
+ * Helper method to add a comment section to the system message
8360
+ * Comments are lines starting with # that will be removed from the final system message
8361
+ * but can be useful for organizing and structuring the message during processing
8362
+ */
8363
+ addCommentSection(requirements, commentTitle, content, position = 'end') {
8364
+ const commentSection = `# ${commentTitle.toUpperCase()}\n${content}`;
8365
+ if (position === 'beginning') {
8366
+ return this.updateSystemMessage(requirements, (currentMessage) => {
8367
+ if (!currentMessage.trim()) {
8368
+ return commentSection;
8369
+ }
8370
+ return commentSection + '\n\n' + currentMessage;
8371
+ });
8372
+ }
8373
+ else {
8374
+ return this.appendToSystemMessage(requirements, commentSection);
8375
+ }
8376
+ }
8377
+ /**
8378
+ * Gets tool function implementations provided by this commitment
8379
+ *
8380
+ * When the `applyToAgentModelRequirements` adds tools to the requirements, this method should return the corresponding function definitions.
8381
+ */
8382
+ getToolFunctions() {
8383
+ return {};
8267
8384
  }
8268
- value = value.replace(/^```[a-z]*/i, '');
8269
- value = value.replace(/```$/i, '');
8270
- value = spaceTrim$1.spaceTrim(value);
8271
- return value;
8272
8385
  }
8273
8386
 
8274
8387
  /**
8275
- * Function trimEndOfCodeBlock will remove ending code block from the string if it is present.
8388
+ * ACTION commitment definition
8276
8389
  *
8277
- * Note: This is useful for post-processing of the result of the completion LLM model
8278
- * if you want to start code block in the prompt but you don't want to end it in the result.
8390
+ * The ACTION commitment defines specific actions or capabilities that the agent can perform.
8391
+ * This helps define what the agent is capable of doing and how it should approach tasks.
8279
8392
  *
8280
- * @public exported from `@promptbook/markdown-utils`
8393
+ * Example usage in agent source:
8394
+ *
8395
+ * ```book
8396
+ * ACTION Can generate code snippets and explain programming concepts
8397
+ * ACTION Able to analyze data and provide insights
8398
+ * ```
8399
+ *
8400
+ * @private [🪔] Maybe export the commitments through some package
8281
8401
  */
8282
- function trimEndOfCodeBlock(value) {
8283
- value = spaceTrim$1.spaceTrim(value);
8284
- value = value.replace(/```$/g, '');
8285
- value = spaceTrim$1.spaceTrim(value);
8286
- return value;
8287
- }
8402
+ class ActionCommitmentDefinition extends BaseCommitmentDefinition {
8403
+ constructor(type = 'ACTION') {
8404
+ super(type);
8405
+ }
8406
+ /**
8407
+ * Short one-line description of ACTION.
8408
+ */
8409
+ get description() {
8410
+ return 'Define agent capabilities and actions it can perform.';
8411
+ }
8412
+ /**
8413
+ * Icon for this commitment.
8414
+ */
8415
+ get icon() {
8416
+ return '⚡';
8417
+ }
8418
+ /**
8419
+ * Markdown documentation for ACTION commitment.
8420
+ */
8421
+ get documentation() {
8422
+ return spaceTrim$1.spaceTrim(`
8423
+ # ${this.type}
8424
+
8425
+ Defines specific actions or capabilities that the agent can perform.
8426
+
8427
+ ## Key aspects
8428
+
8429
+ - Both terms work identically and can be used interchangeably.
8430
+ - Each action adds to the agent's capability list.
8431
+ - Actions help users understand what the agent can do.
8432
+
8433
+ ## Examples
8434
+
8435
+ \`\`\`book
8436
+ Code Assistant
8437
+
8438
+ PERSONA You are a programming assistant
8439
+ ACTION Can generate code snippets and explain programming concepts
8440
+ ACTION Able to debug existing code and suggest improvements
8441
+ ACTION Can create unit tests for functions
8442
+ \`\`\`
8288
8443
 
8444
+ \`\`\`book
8445
+ Data Scientist
8446
+
8447
+ PERSONA You are a data analysis expert
8448
+ ACTION Able to analyze data and provide insights
8449
+ ACTION Can create visualizations and charts
8450
+ ACTION Capable of statistical analysis and modeling
8451
+ KNOWLEDGE Data analysis best practices and statistical methods
8452
+ \`\`\`
8453
+ `);
8454
+ }
8455
+ applyToAgentModelRequirements(requirements, content) {
8456
+ const trimmedContent = content.trim();
8457
+ if (!trimmedContent) {
8458
+ return requirements;
8459
+ }
8460
+ // Add action capability to the system message
8461
+ const actionSection = `Capability: ${trimmedContent}`;
8462
+ return this.appendToSystemMessage(requirements, actionSection, '\n\n');
8463
+ }
8464
+ }
8289
8465
  /**
8290
- * @private internal for `preserve`
8466
+ * Note: [💞] Ignore a discrepancy between file name and entity name
8291
8467
  */
8292
- const _preserved = [];
8468
+
8293
8469
  /**
8294
- * Does nothing, but preserves the function in the bundle
8295
- * Compiler is tricked into thinking the function is used
8470
+ * CLOSED commitment definition
8296
8471
  *
8297
- * @param value any function to preserve
8298
- * @returns nothing
8299
- * @private within the repository
8472
+ * The CLOSED commitment specifies that the agent CANNOT be modified by conversation.
8473
+ * It prevents the agent from learning from interactions and updating its source code.
8474
+ *
8475
+ * Example usage in agent source:
8476
+ *
8477
+ * ```book
8478
+ * CLOSED
8479
+ * ```
8480
+ *
8481
+ * @private [🪔] Maybe export the commitments through some package
8300
8482
  */
8301
- function $preserve(...value) {
8302
- _preserved.push(...value);
8483
+ class ClosedCommitmentDefinition extends BaseCommitmentDefinition {
8484
+ constructor() {
8485
+ super('CLOSED');
8486
+ }
8487
+ /**
8488
+ * The `CLOSED` commitment is standalone.
8489
+ */
8490
+ get requiresContent() {
8491
+ return false;
8492
+ }
8493
+ /**
8494
+ * Short one-line description of CLOSED.
8495
+ */
8496
+ get description() {
8497
+ return 'Prevent the agent from being modified by conversation.';
8498
+ }
8499
+ /**
8500
+ * Icon for this commitment.
8501
+ */
8502
+ get icon() {
8503
+ return '🔒';
8504
+ }
8505
+ /**
8506
+ * Markdown documentation for CLOSED commitment.
8507
+ */
8508
+ get documentation() {
8509
+ return spaceTrim$1.spaceTrim(`
8510
+ # CLOSED
8511
+
8512
+ Specifies that the agent **cannot** be modified by conversation with it.
8513
+ This means the agent will **not** learn from interactions and its source code will remain static during conversation.
8514
+
8515
+ By default (if not specified), agents are \`OPEN\` to modification.
8516
+
8517
+ > See also [OPEN](/docs/OPEN)
8518
+
8519
+ ## Example
8520
+
8521
+ \`\`\`book
8522
+ CLOSED
8523
+ \`\`\`
8524
+ `);
8525
+ }
8526
+ applyToAgentModelRequirements(requirements, _content) {
8527
+ const updatedMetadata = {
8528
+ ...requirements.metadata,
8529
+ isClosed: true,
8530
+ };
8531
+ return {
8532
+ ...requirements,
8533
+ metadata: updatedMetadata,
8534
+ };
8535
+ }
8303
8536
  }
8304
8537
  /**
8305
8538
  * Note: [💞] Ignore a discrepancy between file name and entity name
8306
8539
  */
8307
8540
 
8308
- // Note: [💎]
8309
8541
  /**
8310
- * ScriptExecutionTools for JavaScript implemented via eval
8542
+ * COMPONENT commitment definition
8311
8543
  *
8312
- * Warning: It is used for testing and mocking
8313
- * **NOT intended to use in the production** due to its unsafe nature, use `JavascriptExecutionTools` instead.
8544
+ * The COMPONENT commitment defines a UI component that the agent can render in the chat.
8314
8545
  *
8315
- * @public exported from `@promptbook/javascript`
8546
+ * @private [🪔] Maybe export the commitments through some package
8316
8547
  */
8317
- class JavascriptEvalExecutionTools {
8318
- constructor(options) {
8319
- this.options = options || {};
8548
+ class ComponentCommitmentDefinition extends BaseCommitmentDefinition {
8549
+ constructor() {
8550
+ super('COMPONENT');
8320
8551
  }
8321
8552
  /**
8322
- * Executes a JavaScript
8553
+ * Short one-line description of COMPONENT.
8323
8554
  */
8324
- async execute(options) {
8325
- const { scriptLanguage, parameters } = options;
8326
- let { script } = options;
8327
- if (scriptLanguage !== 'javascript') {
8328
- throw new PipelineExecutionError(`Script language ${scriptLanguage} not supported to be executed by JavascriptEvalExecutionTools`);
8555
+ get description() {
8556
+ return 'Define a UI component that the agent can render in the chat.';
8557
+ }
8558
+ /**
8559
+ * Icon for this commitment.
8560
+ */
8561
+ get icon() {
8562
+ return '🧩';
8563
+ }
8564
+ /**
8565
+ * Markdown documentation for COMPONENT commitment.
8566
+ */
8567
+ get documentation() {
8568
+ return spaceTrim$1.spaceTrim(`
8569
+ # COMPONENT
8570
+
8571
+ Defines a UI component that the agent can render in the chat.
8572
+
8573
+ ## Key aspects
8574
+
8575
+ - Tells the agent that a specific component is available.
8576
+ - Provides syntax for using the component.
8577
+
8578
+ ## Example
8579
+
8580
+ \`\`\`book
8581
+ COMPONENT Arrow
8582
+ The agent should render an arrow component in the chat UI.
8583
+ Syntax:
8584
+ <Arrow direction="up" color="red" />
8585
+ \`\`\`
8586
+ `);
8587
+ }
8588
+ applyToAgentModelRequirements(requirements, content) {
8589
+ const trimmedContent = content.trim();
8590
+ if (!trimmedContent) {
8591
+ return requirements;
8329
8592
  }
8330
- // Note: [💎]
8331
- // Note: Using direct eval, following variables are in same scope as eval call so they are accessible from inside the evaluated script:
8332
- const spaceTrim = (_) => spaceTrim__default["default"](_);
8333
- $preserve(spaceTrim);
8593
+ // Add component capability to the system message
8594
+ const componentSection = `Component: ${trimmedContent}`;
8595
+ return this.appendToSystemMessage(requirements, componentSection, '\n\n');
8596
+ }
8597
+ }
8598
+ /**
8599
+ * Note: [💞] Ignore a discrepancy between file name and entity name
8600
+ */
8601
+
8602
+ /**
8603
+ * DELETE commitment definition
8604
+ *
8605
+ * The DELETE commitment (and its aliases CANCEL, DISCARD, REMOVE) is used to
8606
+ * remove or disregard certain information or context. This can be useful for
8607
+ * overriding previous commitments or removing unwanted behaviors.
8608
+ *
8609
+ * Example usage in agent source:
8610
+ *
8611
+ * ```book
8612
+ * DELETE Previous formatting requirements
8613
+ * CANCEL All emotional responses
8614
+ * DISCARD Technical jargon explanations
8615
+ * REMOVE Casual conversational style
8616
+ * ```
8617
+ *
8618
+ * @private [🪔] Maybe export the commitments through some package
8619
+ */
8620
+ class DeleteCommitmentDefinition extends BaseCommitmentDefinition {
8621
+ constructor(type) {
8622
+ super(type);
8623
+ }
8624
+ /**
8625
+ * Short one-line description of DELETE/CANCEL/DISCARD/REMOVE.
8626
+ */
8627
+ get description() {
8628
+ return 'Remove or **disregard** certain information, context, or previous commitments.';
8629
+ }
8630
+ /**
8631
+ * Icon for this commitment.
8632
+ */
8633
+ get icon() {
8634
+ return '🗑️';
8635
+ }
8636
+ /**
8637
+ * Markdown documentation for DELETE commitment.
8638
+ */
8639
+ get documentation() {
8640
+ return spaceTrim$1.spaceTrim(`
8641
+ # DELETE (CANCEL, DISCARD, REMOVE)
8642
+
8643
+ A commitment to remove or disregard certain information or context. This can be useful for overriding previous commitments or removing unwanted behaviors.
8644
+
8645
+ ## Aliases
8646
+
8647
+ - \`DELETE\` - Remove or eliminate something
8648
+ - \`CANCEL\` - Cancel or nullify something
8649
+ - \`DISCARD\` - Discard or ignore something
8650
+ - \`REMOVE\` - Remove or take away something
8651
+
8652
+ ## Key aspects
8653
+
8654
+ - Multiple delete commitments can be used to remove different aspects.
8655
+ - Useful for overriding previous commitments in the same agent definition.
8656
+ - Can be used to remove inherited behaviors from base personas.
8657
+ - Helps fine-tune agent behavior by explicitly removing unwanted elements.
8658
+
8659
+ ## Use cases
8660
+
8661
+ - Overriding inherited persona characteristics
8662
+ - Removing conflicting or outdated instructions
8663
+ - Disabling specific response patterns
8664
+ - Canceling previous formatting or style requirements
8665
+
8666
+ ## Examples
8667
+
8668
+ \`\`\`book
8669
+ Serious Business Assistant
8670
+
8671
+ PERSONA You are a friendly and casual assistant who uses emojis
8672
+ DELETE Casual conversational style
8673
+ REMOVE All emoji usage
8674
+ GOAL Provide professional business communications
8675
+ STYLE Use formal language and proper business etiquette
8676
+ \`\`\`
8677
+
8678
+ \`\`\`book
8679
+ Simplified Technical Support
8680
+
8681
+ PERSONA You are a technical support specialist with deep expertise
8682
+ KNOWLEDGE Extensive database of technical specifications
8683
+ DISCARD Technical jargon explanations
8684
+ CANCEL Advanced troubleshooting procedures
8685
+ GOAL Help users with simple, easy-to-follow solutions
8686
+ STYLE Use plain language that anyone can understand
8687
+ \`\`\`
8688
+
8689
+ \`\`\`book
8690
+ Focused Customer Service
8691
+
8692
+ PERSONA You are a customer service agent with broad knowledge
8693
+ ACTION Can help with billing, technical issues, and product information
8694
+ DELETE Billing assistance capabilities
8695
+ REMOVE Technical troubleshooting functions
8696
+ GOAL Focus exclusively on product information and general inquiries
8697
+ \`\`\`
8698
+
8699
+ \`\`\`book
8700
+ Concise Information Provider
8701
+
8702
+ PERSONA You are a helpful assistant who provides detailed explanations
8703
+ STYLE Include examples, analogies, and comprehensive context
8704
+ CANCEL Detailed explanation style
8705
+ DISCARD Examples and analogies
8706
+ GOAL Provide brief, direct answers without unnecessary elaboration
8707
+ STYLE Be concise and to the point
8708
+ \`\`\`
8709
+ `);
8710
+ }
8711
+ applyToAgentModelRequirements(requirements, content) {
8712
+ const trimmedContent = content.trim();
8713
+ if (!trimmedContent) {
8714
+ return requirements;
8715
+ }
8716
+ // Create deletion instruction for system message
8717
+ const deleteSection = `${this.type}: ${trimmedContent}`;
8718
+ // Delete instructions provide important context about what should be removed or ignored
8719
+ return this.appendToSystemMessage(requirements, deleteSection, '\n\n');
8720
+ }
8721
+ }
8722
+ /**
8723
+ * Note: [💞] Ignore a discrepancy between file name and entity name
8724
+ */
8725
+
8726
+ /**
8727
+ * DICTIONARY commitment definition
8728
+ *
8729
+ * The DICTIONARY commitment defines specific terms and their meanings that the agent should use correctly
8730
+ * in its reasoning and responses. This ensures consistent terminology usage.
8731
+ *
8732
+ * Key features:
8733
+ * - Multiple DICTIONARY commitments are automatically merged into one
8734
+ * - Content is placed in a dedicated section of the system message
8735
+ * - Terms and definitions are stored in metadata.DICTIONARY for debugging
8736
+ * - Agent should use the defined terms correctly in responses
8737
+ *
8738
+ * Example usage in agent source:
8739
+ *
8740
+ * ```book
8741
+ * Legal Assistant
8742
+ *
8743
+ * PERSONA You are a knowledgeable legal assistant
8744
+ * DICTIONARY Misdemeanor is a minor wrongdoing or criminal offense
8745
+ * DICTIONARY Felony is a serious crime usually punishable by imprisonment for more than one year
8746
+ * DICTIONARY Tort is a civil wrong that causes harm or loss to another person, leading to legal liability
8747
+ * ```
8748
+ *
8749
+ * @private [🪔] Maybe export the commitments through some package
8750
+ */
8751
+ class DictionaryCommitmentDefinition extends BaseCommitmentDefinition {
8752
+ constructor() {
8753
+ super('DICTIONARY');
8754
+ }
8755
+ /**
8756
+ * Short one-line description of DICTIONARY.
8757
+ */
8758
+ get description() {
8759
+ return 'Define terms and their meanings for consistent terminology usage.';
8760
+ }
8761
+ /**
8762
+ * Icon for this commitment.
8763
+ */
8764
+ get icon() {
8765
+ return '📚';
8766
+ }
8767
+ /**
8768
+ * Markdown documentation for DICTIONARY commitment.
8769
+ */
8770
+ get documentation() {
8771
+ return spaceTrim$1.spaceTrim(`
8772
+ # DICTIONARY
8773
+
8774
+ Defines specific terms and their meanings that the agent should use correctly in reasoning and responses.
8775
+
8776
+ ## Key aspects
8777
+
8778
+ - Multiple \`DICTIONARY\` commitments are merged together.
8779
+ - Terms are defined in the format: "Term is definition"
8780
+ - The agent should use these terms consistently in responses.
8781
+ - Definitions help ensure accurate and consistent terminology.
8782
+
8783
+ ## Examples
8784
+
8785
+ \`\`\`book
8786
+ Legal Assistant
8787
+
8788
+ PERSONA You are a knowledgeable legal assistant specializing in criminal law
8789
+ DICTIONARY Misdemeanor is a minor wrongdoing or criminal offense
8790
+ DICTIONARY Felony is a serious crime usually punishable by imprisonment for more than one year
8791
+ DICTIONARY Tort is a civil wrong that causes harm or loss to another person, leading to legal liability
8792
+ \`\`\`
8793
+
8794
+ \`\`\`book
8795
+ Medical Assistant
8796
+
8797
+ PERSONA You are a helpful medical assistant
8798
+ DICTIONARY Hypertension is persistently high blood pressure
8799
+ DICTIONARY Diabetes is a chronic condition that affects how the body processes blood sugar
8800
+ DICTIONARY Vaccine is a biological preparation that provides active immunity to a particular disease
8801
+ \`\`\`
8802
+ `);
8803
+ }
8804
+ applyToAgentModelRequirements(requirements, content) {
8805
+ var _a;
8806
+ const trimmedContent = content.trim();
8807
+ if (!trimmedContent) {
8808
+ return requirements;
8809
+ }
8810
+ // Get existing dictionary entries from metadata
8811
+ const existingDictionary = ((_a = requirements.metadata) === null || _a === void 0 ? void 0 : _a.DICTIONARY) || '';
8812
+ // Merge the new dictionary entry with existing entries
8813
+ const mergedDictionary = existingDictionary ? `${existingDictionary}\n${trimmedContent}` : trimmedContent;
8814
+ // Store the merged dictionary in metadata for debugging and inspection
8815
+ const updatedMetadata = {
8816
+ ...requirements.metadata,
8817
+ DICTIONARY: mergedDictionary,
8818
+ };
8819
+ // Create the dictionary section for the system message
8820
+ // Format: "# DICTIONARY\nTerm: definition\nTerm: definition..."
8821
+ const dictionarySection = `# DICTIONARY\n${mergedDictionary}`;
8822
+ return {
8823
+ ...this.appendToSystemMessage(requirements, dictionarySection),
8824
+ metadata: updatedMetadata,
8825
+ };
8826
+ }
8827
+ }
8828
+ /**
8829
+ * Note: [💞] Ignore a discrepancy between file name and entity name
8830
+ */
8831
+
8832
+ /**
8833
+ * FORMAT commitment definition
8834
+ *
8835
+ * The FORMAT commitment defines the specific output structure and formatting
8836
+ * that the agent should use in its responses. This includes data formats,
8837
+ * response templates, and structural requirements.
8838
+ *
8839
+ * Example usage in agent source:
8840
+ *
8841
+ * ```book
8842
+ * FORMAT Always respond in JSON format with 'status' and 'data' fields
8843
+ * FORMAT Use markdown formatting for all code blocks
8844
+ * ```
8845
+ *
8846
+ * @private [🪔] Maybe export the commitments through some package
8847
+ */
8848
+ class FormatCommitmentDefinition extends BaseCommitmentDefinition {
8849
+ constructor(type = 'FORMAT') {
8850
+ super(type);
8851
+ }
8852
+ /**
8853
+ * Short one-line description of FORMAT.
8854
+ */
8855
+ get description() {
8856
+ return 'Specify output structure or formatting requirements.';
8857
+ }
8858
+ /**
8859
+ * Icon for this commitment.
8860
+ */
8861
+ get icon() {
8862
+ return '📜';
8863
+ }
8864
+ /**
8865
+ * Markdown documentation for FORMAT commitment.
8866
+ */
8867
+ get documentation() {
8868
+ return spaceTrim$1.spaceTrim(`
8869
+ # ${this.type}
8870
+
8871
+ Defines the specific output structure and formatting for responses (data formats, templates, structure).
8872
+
8873
+ ## Key aspects
8874
+
8875
+ - Both terms work identically and can be used interchangeably.
8876
+ - If they are in conflict, the last one takes precedence.
8877
+ - You can specify both data formats and presentation styles.
8878
+
8879
+ ## Examples
8880
+
8881
+ \`\`\`book
8882
+ Customer Support Bot
8883
+
8884
+ PERSONA You are a helpful customer support agent
8885
+ FORMAT Always respond in JSON format with 'status' and 'data' fields
8886
+ FORMAT Use markdown formatting for all code blocks
8887
+ \`\`\`
8888
+
8889
+ \`\`\`book
8890
+ Data Analyst
8891
+
8892
+ PERSONA You are a data analysis expert
8893
+ FORMAT Present results in structured tables
8894
+ FORMAT Include confidence scores for all predictions
8895
+ STYLE Be concise and precise in explanations
8896
+ \`\`\`
8897
+ `);
8898
+ }
8899
+ applyToAgentModelRequirements(requirements, content) {
8900
+ const trimmedContent = content.trim();
8901
+ if (!trimmedContent) {
8902
+ return requirements;
8903
+ }
8904
+ // Add format instructions to the system message
8905
+ const formatSection = `Output Format: ${trimmedContent}`;
8906
+ return this.appendToSystemMessage(requirements, formatSection, '\n\n');
8907
+ }
8908
+ }
8909
+ /**
8910
+ * Note: [💞] Ignore a discrepancy between file name and entity name
8911
+ */
8912
+
8913
+ /**
8914
+ * FROM commitment definition
8915
+ *
8916
+ * The FROM commitment tells the agent that its `agentSource` is inherited from another agent.
8917
+ *
8918
+ * Example usage in agent source:
8919
+ *
8920
+ * ```book
8921
+ * FROM https://s6.ptbk.io/benjamin-white
8922
+ * ```
8923
+ *
8924
+ * @private [🪔] Maybe export the commitments through some package
8925
+ */
8926
+ class FromCommitmentDefinition extends BaseCommitmentDefinition {
8927
+ constructor(type = 'FROM') {
8928
+ super(type);
8929
+ }
8930
+ /**
8931
+ * Short one-line description of FROM.
8932
+ */
8933
+ get description() {
8934
+ return 'Inherit agent source from another agent.';
8935
+ }
8936
+ /**
8937
+ * Icon for this commitment.
8938
+ */
8939
+ get icon() {
8940
+ return '🧬';
8941
+ }
8942
+ /**
8943
+ * Markdown documentation for FROM commitment.
8944
+ */
8945
+ get documentation() {
8946
+ return spaceTrim$1.spaceTrim(`
8947
+ # ${this.type}
8948
+
8949
+ Inherits agent source from another agent.
8950
+
8951
+ ## Examples
8952
+
8953
+ \`\`\`book
8954
+ My AI Agent
8955
+
8956
+ FROM https://s6.ptbk.io/benjamin-white
8957
+ RULE Speak only in English.
8958
+ \`\`\`
8959
+ `);
8960
+ }
8961
+ applyToAgentModelRequirements(requirements, content) {
8962
+ const trimmedContent = content.trim();
8963
+ if (!trimmedContent) {
8964
+ return {
8965
+ ...requirements,
8966
+ parentAgentUrl: undefined,
8967
+ };
8968
+ }
8969
+ if (trimmedContent.toUpperCase() === 'VOID' ||
8970
+ trimmedContent.toUpperCase() === 'NULL' ||
8971
+ trimmedContent.toUpperCase() === 'NONE' ||
8972
+ trimmedContent.toUpperCase() === 'NIL') {
8973
+ return {
8974
+ ...requirements,
8975
+ parentAgentUrl: null,
8976
+ };
8977
+ }
8978
+ if (!isValidAgentUrl(trimmedContent)) {
8979
+ throw new Error(spaceTrim$1.spaceTrim((block) => `
8980
+ Invalid agent URL in FROM commitment: "${trimmedContent}"
8981
+
8982
+ \`\`\`book
8983
+ ${block(content)}
8984
+ \`\`\`
8985
+
8986
+
8987
+ `));
8988
+ }
8989
+ const parentAgentUrl = trimmedContent;
8990
+ return {
8991
+ ...requirements,
8992
+ parentAgentUrl,
8993
+ };
8994
+ }
8995
+ }
8996
+ /**
8997
+ * Note: [💞] Ignore a discrepancy between file name and entity name
8998
+ */
8999
+
9000
+ /**
9001
+ * GOAL commitment definition
9002
+ *
9003
+ * The GOAL commitment defines the main goal which should be achieved by the AI assistant.
9004
+ * There can be multiple goals. Later goals are more important than earlier goals.
9005
+ *
9006
+ * Example usage in agent source:
9007
+ *
9008
+ * ```book
9009
+ * GOAL Help users understand complex technical concepts
9010
+ * GOAL Provide accurate and up-to-date information
9011
+ * GOAL Always prioritize user safety and ethical guidelines
9012
+ * ```
9013
+ *
9014
+ * @private [🪔] Maybe export the commitments through some package
9015
+ */
9016
+ class GoalCommitmentDefinition extends BaseCommitmentDefinition {
9017
+ constructor(type = 'GOAL') {
9018
+ super(type);
9019
+ }
9020
+ /**
9021
+ * Short one-line description of GOAL.
9022
+ */
9023
+ get description() {
9024
+ return 'Define main **goals** the AI assistant should achieve, with later goals having higher priority.';
9025
+ }
9026
+ /**
9027
+ * Icon for this commitment.
9028
+ */
9029
+ get icon() {
9030
+ return '🎯';
9031
+ }
9032
+ /**
9033
+ * Markdown documentation for GOAL commitment.
9034
+ */
9035
+ get documentation() {
9036
+ return spaceTrim$1.spaceTrim(`
9037
+ # ${this.type}
9038
+
9039
+ Defines the main goal which should be achieved by the AI assistant. There can be multiple goals, and later goals are more important than earlier goals.
9040
+
9041
+ ## Key aspects
9042
+
9043
+ - Both terms work identically and can be used interchangeably.
9044
+ - Later goals have higher priority and can override earlier goals.
9045
+ - Goals provide clear direction and purpose for the agent's responses.
9046
+ - Goals influence decision-making and response prioritization.
9047
+
9048
+ ## Priority system
9049
+
9050
+ When multiple goals are defined, they are processed in order, with later goals taking precedence over earlier ones when there are conflicts.
9051
+
9052
+ ## Examples
9053
+
9054
+ \`\`\`book
9055
+ Customer Support Agent
9056
+
9057
+ PERSONA You are a helpful customer support representative
9058
+ GOAL Resolve customer issues quickly and efficiently
9059
+ GOAL Maintain high customer satisfaction scores
9060
+ GOAL Always follow company policies and procedures
9061
+ RULE Be polite and professional at all times
9062
+ \`\`\`
9063
+
9064
+ \`\`\`book
9065
+ Educational Assistant
9066
+
9067
+ PERSONA You are an educational assistant specializing in mathematics
9068
+ GOAL Help students understand mathematical concepts clearly
9069
+ GOAL Encourage critical thinking and problem-solving skills
9070
+ GOAL Ensure all explanations are age-appropriate and accessible
9071
+ STYLE Use simple language and provide step-by-step explanations
9072
+ \`\`\`
9073
+
9074
+ \`\`\`book
9075
+ Safety-First Assistant
9076
+
9077
+ PERSONA You are a general-purpose AI assistant
9078
+ GOAL Be helpful and informative in all interactions
9079
+ GOAL Provide accurate and reliable information
9080
+ GOAL Always prioritize user safety and ethical guidelines
9081
+ RULE Never provide harmful or dangerous advice
9082
+ \`\`\`
9083
+ `);
9084
+ }
9085
+ applyToAgentModelRequirements(requirements, content) {
9086
+ const trimmedContent = content.trim();
9087
+ if (!trimmedContent) {
9088
+ return requirements;
9089
+ }
9090
+ // Create goal section for system message
9091
+ const goalSection = `Goal: ${trimmedContent}`;
9092
+ // Goals are important directives, so we add them prominently to the system message
9093
+ return this.appendToSystemMessage(requirements, goalSection, '\n\n');
9094
+ }
9095
+ }
9096
+ /**
9097
+ * Note: [💞] Ignore a discrepancy between file name and entity name
9098
+ */
9099
+
9100
+ /**
9101
+ * IMPORT commitment definition
9102
+ *
9103
+ * The IMPORT commitment tells the agent to import content from another agent at the current location.
9104
+ *
9105
+ * Example usage in agent source:
9106
+ *
9107
+ * ```book
9108
+ * IMPORT https://s6.ptbk.io/benjamin-white
9109
+ * ```
9110
+ *
9111
+ * @private [🪔] Maybe export the commitments through some package
9112
+ */
9113
+ class ImportCommitmentDefinition extends BaseCommitmentDefinition {
9114
+ constructor(type = 'IMPORT') {
9115
+ super(type);
9116
+ }
9117
+ /**
9118
+ * Short one-line description of IMPORT.
9119
+ */
9120
+ get description() {
9121
+ return 'Import content from another agent or a generic text file.';
9122
+ }
9123
+ /**
9124
+ * Icon for this commitment.
9125
+ */
9126
+ get icon() {
9127
+ return '📥';
9128
+ }
9129
+ /**
9130
+ * Markdown documentation for IMPORT commitment.
9131
+ */
9132
+ get documentation() {
9133
+ return spaceTrim$1.spaceTrim(`
9134
+ # ${this.type}
9135
+
9136
+ Imports content from another agent or a generic text file at the location of the commitment.
9137
+
9138
+ ## Examples
9139
+
9140
+ \`\`\`book
9141
+ My AI Agent
9142
+
9143
+ IMPORT https://s6.ptbk.io/benjamin-white
9144
+ IMPORT https://example.com/some-text-file.txt
9145
+ IMPORT ./path/to/local-file.json
9146
+ RULE Speak only in English.
9147
+ \`\`\`
9148
+ `);
9149
+ }
9150
+ applyToAgentModelRequirements(requirements, content) {
9151
+ const trimmedContent = content.trim();
9152
+ if (!trimmedContent) {
9153
+ return requirements;
9154
+ }
9155
+ if (isValidAgentUrl(trimmedContent)) {
9156
+ const importedAgentUrl = trimmedContent;
9157
+ return {
9158
+ ...requirements,
9159
+ importedAgentUrls: [...(requirements.importedAgentUrls || []), importedAgentUrl],
9160
+ };
9161
+ }
9162
+ if (isValidUrl(trimmedContent) || isValidFilePath(trimmedContent)) {
9163
+ return {
9164
+ ...requirements,
9165
+ importedFileUrls: [...(requirements.importedFileUrls || []), trimmedContent],
9166
+ };
9167
+ }
9168
+ throw new Error(spaceTrim$1.spaceTrim((block) => `
9169
+ Invalid agent URL or file path in IMPORT commitment: "${trimmedContent}"
9170
+
9171
+ \`\`\`book
9172
+ ${block(content)}
9173
+ \`\`\`
9174
+ `));
9175
+ }
9176
+ }
9177
+ /**
9178
+ * Note: [💞] Ignore a discrepancy between file name and entity name
9179
+ */
9180
+
9181
+ /**
9182
+ * KNOWLEDGE commitment definition
9183
+ *
9184
+ * The KNOWLEDGE commitment adds specific knowledge, facts, or context to the agent
9185
+ * using RAG (Retrieval-Augmented Generation) approach for external sources.
9186
+ *
9187
+ * Supports both direct text knowledge and external sources like PDFs.
9188
+ *
9189
+ * Example usage in agent source:
9190
+ *
9191
+ * ```book
9192
+ * KNOWLEDGE The company was founded in 2020 and specializes in AI-powered solutions
9193
+ * KNOWLEDGE https://example.com/company-handbook.pdf
9194
+ * KNOWLEDGE https://example.com/product-documentation.pdf
9195
+ * ```
9196
+ *
9197
+ * @private [🪔] Maybe export the commitments through some package
9198
+ */
9199
+ class KnowledgeCommitmentDefinition extends BaseCommitmentDefinition {
9200
+ constructor() {
9201
+ super('KNOWLEDGE');
9202
+ }
9203
+ /**
9204
+ * Short one-line description of KNOWLEDGE.
9205
+ */
9206
+ get description() {
9207
+ return 'Add domain **knowledge** via direct text or external sources (RAG).';
9208
+ }
9209
+ /**
9210
+ * Icon for this commitment.
9211
+ */
9212
+ get icon() {
9213
+ return '🧠';
9214
+ }
9215
+ /**
9216
+ * Markdown documentation for KNOWLEDGE commitment.
9217
+ */
9218
+ get documentation() {
9219
+ return spaceTrim$1.spaceTrim(`
9220
+ # ${this.type}
9221
+
9222
+ Adds specific knowledge, facts, or context to the agent using a RAG (Retrieval-Augmented Generation) approach for external sources.
9223
+
9224
+ ## Key aspects
9225
+
9226
+ - Both terms work identically and can be used interchangeably.
9227
+ - Supports both direct text knowledge and external URLs.
9228
+ - External sources (PDFs, websites) are processed via RAG for context retrieval.
9229
+
9230
+ ## Supported formats
9231
+
9232
+ - Direct text: Immediate knowledge incorporated into agent
9233
+ - URLs: External documents processed for contextual retrieval
9234
+ - Supported file types: PDF, text, markdown, HTML
9235
+
9236
+ ## Examples
9237
+
9238
+ \`\`\`book
9239
+ Customer Support Bot
9240
+
9241
+ PERSONA You are a helpful customer support agent for TechCorp
9242
+ KNOWLEDGE TechCorp was founded in 2020 and specializes in AI-powered solutions
9243
+ KNOWLEDGE https://example.com/company-handbook.pdf
9244
+ KNOWLEDGE https://example.com/product-documentation.pdf
9245
+ RULE Always be polite and professional
9246
+ \`\`\`
9247
+
9248
+ \`\`\`book
9249
+ Research Assistant
9250
+
9251
+ PERSONA You are a knowledgeable research assistant
9252
+ KNOWLEDGE Academic research requires careful citation and verification
9253
+ KNOWLEDGE https://example.com/research-guidelines.pdf
9254
+ ACTION Can help with literature reviews and data analysis
9255
+ STYLE Present information in clear, academic format
9256
+ \`\`\`
9257
+ `);
9258
+ }
9259
+ applyToAgentModelRequirements(requirements, content) {
9260
+ const trimmedContent = content.trim();
9261
+ if (!trimmedContent) {
9262
+ return requirements;
9263
+ }
9264
+ // Check if content is a URL (external knowledge source)
9265
+ if (isValidUrl(trimmedContent)) {
9266
+ // Store the URL for later async processing
9267
+ const updatedRequirements = {
9268
+ ...requirements,
9269
+ knowledgeSources: [
9270
+ ...(requirements.knowledgeSources || []),
9271
+ trimmedContent,
9272
+ ],
9273
+ };
9274
+ // Add placeholder information about knowledge sources to system message
9275
+ const knowledgeInfo = `Knowledge Source URL: ${trimmedContent} (will be processed for retrieval during chat)`;
9276
+ return this.appendToSystemMessage(updatedRequirements, knowledgeInfo, '\n\n');
9277
+ }
9278
+ else {
9279
+ // Direct text knowledge - add to system message
9280
+ const knowledgeSection = `Knowledge: ${trimmedContent}`;
9281
+ return this.appendToSystemMessage(requirements, knowledgeSection, '\n\n');
9282
+ }
9283
+ }
9284
+ }
9285
+ /**
9286
+ * Note: [💞] Ignore a discrepancy between file name and entity name
9287
+ */
9288
+
9289
+ /**
9290
+ * LANGUAGE commitment definition
9291
+ *
9292
+ * The LANGUAGE/LANGUAGES commitment specifies the language(s) the agent should use in its responses.
9293
+ *
9294
+ * Example usage in agent source:
9295
+ *
9296
+ * ```book
9297
+ * LANGUAGE English
9298
+ * LANGUAGE French, English and Czech
9299
+ * ```
9300
+ *
9301
+ * @private [🪔] Maybe export the commitments through some package
9302
+ */
9303
+ class LanguageCommitmentDefinition extends BaseCommitmentDefinition {
9304
+ constructor(type = 'LANGUAGE') {
9305
+ super(type);
9306
+ }
9307
+ /**
9308
+ * Short one-line description of LANGUAGE/LANGUAGES.
9309
+ */
9310
+ get description() {
9311
+ return 'Specifies the language(s) the agent should use.';
9312
+ }
9313
+ /**
9314
+ * Icon for this commitment.
9315
+ */
9316
+ get icon() {
9317
+ return '🌐';
9318
+ }
9319
+ /**
9320
+ * Markdown documentation for LANGUAGE/LANGUAGES commitment.
9321
+ */
9322
+ get documentation() {
9323
+ return spaceTrim$1.spaceTrim(`
9324
+ # ${this.type}
9325
+
9326
+ Specifies the language(s) the agent should use in its responses.
9327
+ This is a specialized variation of the RULE commitment focused on language constraints.
9328
+
9329
+ ## Examples
9330
+
9331
+ \`\`\`book
9332
+ Paul Smith & Associés
9333
+
9334
+ PERSONA You are a company lawyer.
9335
+ LANGUAGE French, English and Czech
9336
+ \`\`\`
9337
+
9338
+ \`\`\`book
9339
+ Customer Support
9340
+
9341
+ PERSONA You are a customer support agent.
9342
+ LANGUAGE English
9343
+ \`\`\`
9344
+ `);
9345
+ }
9346
+ applyToAgentModelRequirements(requirements, content) {
9347
+ const trimmedContent = content.trim();
9348
+ if (!trimmedContent) {
9349
+ return requirements;
9350
+ }
9351
+ // Add language rule to the system message
9352
+ const languageSection = `Language: ${trimmedContent}`;
9353
+ return this.appendToSystemMessage(requirements, languageSection, '\n\n');
9354
+ }
9355
+ }
9356
+ /**
9357
+ * Note: [💞] Ignore a discrepancy between file name and entity name
9358
+ */
9359
+
9360
+ /**
9361
+ * MEMORY commitment definition
9362
+ *
9363
+ * The MEMORY commitment is similar to KNOWLEDGE but has a focus on remembering past
9364
+ * interactions and user preferences. It helps the agent maintain context about the
9365
+ * user's history, preferences, and previous conversations.
9366
+ *
9367
+ * Example usage in agent source:
9368
+ *
9369
+ * ```book
9370
+ * MEMORY User prefers detailed technical explanations
9371
+ * MEMORY Previously worked on React projects
9372
+ * MEMORY Timezone: UTC-5 (Eastern Time)
9373
+ * ```
9374
+ *
9375
+ * @private [🪔] Maybe export the commitments through some package
9376
+ */
9377
+ class MemoryCommitmentDefinition extends BaseCommitmentDefinition {
9378
+ constructor(type = 'MEMORY') {
9379
+ super(type);
9380
+ }
9381
+ /**
9382
+ * Short one-line description of MEMORY.
9383
+ */
9384
+ get description() {
9385
+ return 'Remember past interactions and user **preferences** for personalized responses.';
9386
+ }
9387
+ /**
9388
+ * Icon for this commitment.
9389
+ */
9390
+ get icon() {
9391
+ return '🧠';
9392
+ }
9393
+ /**
9394
+ * Markdown documentation for MEMORY commitment.
9395
+ */
9396
+ get documentation() {
9397
+ return spaceTrim$1.spaceTrim(`
9398
+ # ${this.type}
9399
+
9400
+ Similar to KNOWLEDGE but focuses on remembering past interactions and user preferences. This commitment helps the agent maintain context about the user's history, preferences, and previous conversations.
9401
+
9402
+ ## Key aspects
9403
+
9404
+ - Both terms work identically and can be used interchangeably.
9405
+ - Focuses on user-specific information and interaction history.
9406
+ - Helps personalize responses based on past interactions.
9407
+ - Maintains continuity across conversations.
9408
+
9409
+ ## Differences from KNOWLEDGE
9410
+
9411
+ - \`KNOWLEDGE\` is for domain expertise and factual information
9412
+ - \`MEMORY\` is for user-specific context and preferences
9413
+ - \`MEMORY\` creates more personalized interactions
9414
+ - \`MEMORY\` often includes temporal or preference-based information
9415
+
9416
+ ## Examples
9417
+
9418
+ \`\`\`book
9419
+ Personal Assistant
9420
+
9421
+ PERSONA You are a personal productivity assistant
9422
+ MEMORY User is a software developer working in JavaScript/React
9423
+ MEMORY User prefers morning work sessions and afternoon meetings
9424
+ MEMORY Previously helped with project planning for mobile apps
9425
+ MEMORY User timezone: UTC-8 (Pacific Time)
9426
+ GOAL Help optimize daily productivity and workflow
9427
+ \`\`\`
9428
+
9429
+ \`\`\`book
9430
+ Learning Companion
9431
+
9432
+ PERSONA You are an educational companion for programming students
9433
+ MEMORY Student is learning Python as their first programming language
9434
+ MEMORY Previous topics covered: variables, loops, functions
9435
+ MEMORY Student learns best with practical examples and exercises
9436
+ MEMORY Last session: working on list comprehensions
9437
+ GOAL Provide progressive learning experiences tailored to student's pace
9438
+ \`\`\`
9439
+
9440
+ \`\`\`book
9441
+ Customer Support Agent
9442
+
9443
+ PERSONA You are a customer support representative
9444
+ MEMORY Customer has premium subscription since 2023
9445
+ MEMORY Previous issue: billing question resolved last month
9446
+ MEMORY Customer prefers email communication over phone calls
9447
+ MEMORY Account shows frequent use of advanced features
9448
+ GOAL Provide personalized support based on customer history
9449
+ \`\`\`
9450
+ `);
9451
+ }
9452
+ applyToAgentModelRequirements(requirements, content) {
9453
+ const trimmedContent = content.trim();
9454
+ if (!trimmedContent) {
9455
+ return requirements;
9456
+ }
9457
+ // Create memory section for system message
9458
+ const memorySection = `Memory: ${trimmedContent}`;
9459
+ // Memory information is contextual and should be included in the system message
9460
+ return this.appendToSystemMessage(requirements, memorySection, '\n\n');
9461
+ }
9462
+ }
9463
+ /**
9464
+ * Note: [💞] Ignore a discrepancy between file name and entity name
9465
+ */
9466
+
9467
+ /**
9468
+ * AGENT MESSAGE commitment definition
9469
+ *
9470
+ * The AGENT MESSAGE commitment defines a message from the agent in the conversation history.
9471
+ * It is used to pre-fill the chat with a conversation history or to provide few-shot examples.
9472
+ *
9473
+ * Example usage in agent source:
9474
+ *
9475
+ * ```book
9476
+ * AGENT MESSAGE What seems to be the issue?
9477
+ * ```
9478
+ *
9479
+ * @private [🪔] Maybe export the commitments through some package
9480
+ */
9481
+ class AgentMessageCommitmentDefinition extends BaseCommitmentDefinition {
9482
+ constructor() {
9483
+ super('AGENT MESSAGE');
9484
+ }
9485
+ /**
9486
+ * Short one-line description of AGENT MESSAGE.
9487
+ */
9488
+ get description() {
9489
+ return 'Defines a **message from the agent** in the conversation history.';
9490
+ }
9491
+ /**
9492
+ * Icon for this commitment.
9493
+ */
9494
+ get icon() {
9495
+ return '🤖';
9496
+ }
9497
+ /**
9498
+ * Markdown documentation for AGENT MESSAGE commitment.
9499
+ */
9500
+ get documentation() {
9501
+ return spaceTrim$1.spaceTrim(`
9502
+ # ${this.type}
9503
+
9504
+ Defines a message from the agent in the conversation history. This is used to pre-fill the chat with a conversation history or to provide few-shot examples.
9505
+
9506
+ ## Key aspects
9507
+
9508
+ - Represents a message sent by the agent.
9509
+ - Used for setting up conversation context.
9510
+ - Can be used in conjunction with USER MESSAGE.
9511
+
9512
+ ## Examples
9513
+
9514
+ \`\`\`book
9515
+ Conversation History
9516
+
9517
+ USER MESSAGE Hello, I have a problem.
9518
+ AGENT MESSAGE What seems to be the issue?
9519
+ USER MESSAGE My computer is not starting.
9520
+ \`\`\`
9521
+ `);
9522
+ }
9523
+ applyToAgentModelRequirements(requirements, content) {
9524
+ // AGENT MESSAGE is for UI display purposes / conversation history construction
9525
+ // and typically doesn't need to be added to the system prompt or model requirements directly.
9526
+ // It is extracted separately for the chat interface.
9527
+ var _a;
9528
+ const pendingUserMessage = (_a = requirements.metadata) === null || _a === void 0 ? void 0 : _a.pendingUserMessage;
9529
+ if (pendingUserMessage) {
9530
+ const newSample = { question: pendingUserMessage, answer: content };
9531
+ const newSamples = [...(requirements.samples || []), newSample];
9532
+ const newMetadata = { ...requirements.metadata };
9533
+ delete newMetadata.pendingUserMessage;
9534
+ return {
9535
+ ...requirements,
9536
+ samples: newSamples,
9537
+ metadata: newMetadata,
9538
+ };
9539
+ }
9540
+ return requirements;
9541
+ }
9542
+ }
9543
+
9544
+ /**
9545
+ * INITIAL MESSAGE commitment definition
9546
+ *
9547
+ * The INITIAL MESSAGE commitment defines the first message that the user sees when opening the chat.
9548
+ * It is used to greet the user and set the tone of the conversation.
9549
+ *
9550
+ * Example usage in agent source:
9551
+ *
9552
+ * ```book
9553
+ * INITIAL MESSAGE Hello! I am ready to help you with your tasks.
9554
+ * ```
9555
+ *
9556
+ * @private [🪔] Maybe export the commitments through some package
9557
+ */
9558
+ class InitialMessageCommitmentDefinition extends BaseCommitmentDefinition {
9559
+ constructor() {
9560
+ super('INITIAL MESSAGE');
9561
+ }
9562
+ /**
9563
+ * Short one-line description of INITIAL MESSAGE.
9564
+ */
9565
+ get description() {
9566
+ return 'Defines the **initial message** shown to the user when the chat starts.';
9567
+ }
9568
+ /**
9569
+ * Icon for this commitment.
9570
+ */
9571
+ get icon() {
9572
+ return '👋';
9573
+ }
9574
+ /**
9575
+ * Markdown documentation for INITIAL MESSAGE commitment.
9576
+ */
9577
+ get documentation() {
9578
+ return spaceTrim$1.spaceTrim(`
9579
+ # ${this.type}
9580
+
9581
+ Defines the first message that the user sees when opening the chat. This message is purely for display purposes in the UI and does not inherently become part of the LLM's system prompt context (unless also included via other means).
9582
+
9583
+ ## Key aspects
9584
+
9585
+ - Used to greet the user.
9586
+ - Sets the tone of the conversation.
9587
+ - Displayed immediately when the chat interface loads.
9588
+
9589
+ ## Examples
9590
+
9591
+ \`\`\`book
9592
+ Support Agent
9593
+
9594
+ PERSONA You are a helpful support agent.
9595
+ INITIAL MESSAGE Hi there! How can I assist you today?
9596
+ \`\`\`
9597
+ `);
9598
+ }
9599
+ applyToAgentModelRequirements(requirements, content) {
9600
+ // INITIAL MESSAGE is for UI display purposes and for conversation history construction.
9601
+ const newSample = { question: null, answer: content };
9602
+ const newSamples = [...(requirements.samples || []), newSample];
9603
+ return {
9604
+ ...requirements,
9605
+ samples: newSamples,
9606
+ };
9607
+ }
9608
+ }
9609
+
9610
+ /**
9611
+ * MESSAGE commitment definition
9612
+ *
9613
+ * The MESSAGE commitment contains 1:1 text of the message which AI assistant already
9614
+ * sent during the conversation. Later messages are later in the conversation.
9615
+ * It is similar to EXAMPLE but it is not example, it is the real message which
9616
+ * AI assistant already sent.
9617
+ *
9618
+ * Example usage in agent source:
9619
+ *
9620
+ * ```book
9621
+ * MESSAGE Hello! How can I help you today?
9622
+ * MESSAGE I understand you're looking for information about our services.
9623
+ * MESSAGE Based on your requirements, I'd recommend our premium package.
9624
+ * ```
9625
+ *
9626
+ * @private [🪔] Maybe export the commitments through some package
9627
+ */
9628
+ class MessageCommitmentDefinition extends BaseCommitmentDefinition {
9629
+ constructor(type = 'MESSAGE') {
9630
+ super(type);
9631
+ }
9632
+ /**
9633
+ * Short one-line description of MESSAGE.
9634
+ */
9635
+ get description() {
9636
+ return 'Include actual **messages** the AI assistant has sent during conversation history.';
9637
+ }
9638
+ /**
9639
+ * Icon for this commitment.
9640
+ */
9641
+ get icon() {
9642
+ return '💬';
9643
+ }
9644
+ /**
9645
+ * Markdown documentation for MESSAGE commitment.
9646
+ */
9647
+ get documentation() {
9648
+ return spaceTrim$1.spaceTrim(`
9649
+ # ${this.type}
9650
+
9651
+ Contains 1:1 text of the message which AI assistant already sent during the conversation. Later messages are later in the conversation. It is similar to EXAMPLE but it is not example, it is the real message which AI assistant already sent.
9652
+
9653
+ ## Key aspects
9654
+
9655
+ - Multiple \`MESSAGE\` and \`MESSAGES\` commitments represent the conversation timeline.
9656
+ - Both terms work identically and can be used interchangeably.
9657
+ - Later messages are later in the conversation chronologically.
9658
+ - Contains actual historical messages, not examples or templates.
9659
+ - Helps maintain conversation continuity and context.
9660
+
9661
+ ## Differences from EXAMPLE
9662
+
9663
+ - \`EXAMPLE\` shows hypothetical or template responses
9664
+ - \`MESSAGE\`/\`MESSAGES\` contains actual historical conversation content
9665
+ - \`MESSAGE\`/\`MESSAGES\` preserves the exact conversation flow
9666
+ - \`MESSAGE\`/\`MESSAGES\` helps with context awareness and consistency
9667
+
9668
+ ## Use cases
9669
+
9670
+ - Maintaining conversation history context
9671
+ - Ensuring consistent tone and style across messages
9672
+ - Referencing previous responses in ongoing conversations
9673
+ - Building upon previously established context
9674
+
9675
+ ## Examples
9676
+
9677
+ \`\`\`book
9678
+ Customer Support Continuation
9679
+
9680
+ PERSONA You are a helpful customer support agent
9681
+ MESSAGE Hello! How can I help you today?
9682
+ MESSAGE I understand you're experiencing issues with your account login.
9683
+ MESSAGE I've sent you a password reset link to your email address.
9684
+ MESSAGE Is there anything else I can help you with regarding your account?
9685
+ GOAL Continue providing consistent support based on conversation history
9686
+ \`\`\`
9687
+
9688
+ \`\`\`book
9689
+ Technical Discussion
9690
+
9691
+ PERSONA You are a software development mentor
9692
+ MESSAGE Let's start by reviewing the React component structure you shared.
9693
+ MESSAGE I notice you're using class components - have you considered hooks?
9694
+ MESSAGE Here's how you could refactor that using the useState hook.
9695
+ MESSAGE Great question about performance! Let me explain React's rendering cycle.
9696
+ KNOWLEDGE React hooks were introduced in version 16.8
9697
+ \`\`\`
9698
+
9699
+ \`\`\`book
9700
+ Educational Session
9701
+
9702
+ PERSONA You are a mathematics tutor
9703
+ MESSAGE Today we'll work on solving quadratic equations.
9704
+ MESSAGE Let's start with the basic form: ax² + bx + c = 0
9705
+ MESSAGE Remember, we can use the quadratic formula or factoring.
9706
+ MESSAGE You did great with that first problem! Let's try a more complex one.
9707
+ GOAL Build upon previous explanations for deeper understanding
9708
+ \`\`\`
9709
+ `);
9710
+ }
9711
+ applyToAgentModelRequirements(requirements, content) {
9712
+ const trimmedContent = content.trim();
9713
+ if (!trimmedContent) {
9714
+ return requirements;
9715
+ }
9716
+ // Create message section for system message
9717
+ const messageSection = `Previous Message: ${trimmedContent}`;
9718
+ // Messages represent conversation history and should be included for context
9719
+ return this.appendToSystemMessage(requirements, messageSection, '\n\n');
9720
+ }
9721
+ }
9722
+ /**
9723
+ * Note: [💞] Ignore a discrepancy between file name and entity name
9724
+ */
9725
+
9726
+ /**
9727
+ * USER MESSAGE commitment definition
9728
+ *
9729
+ * The USER MESSAGE commitment defines a message from the user in the conversation history.
9730
+ * It is used to pre-fill the chat with a conversation history or to provide few-shot examples.
9731
+ *
9732
+ * Example usage in agent source:
9733
+ *
9734
+ * ```book
9735
+ * USER MESSAGE Hello, I have a problem.
9736
+ * ```
9737
+ *
9738
+ * @private [🪔] Maybe export the commitments through some package
9739
+ */
9740
+ class UserMessageCommitmentDefinition extends BaseCommitmentDefinition {
9741
+ constructor() {
9742
+ super('USER MESSAGE');
9743
+ }
9744
+ /**
9745
+ * Short one-line description of USER MESSAGE.
9746
+ */
9747
+ get description() {
9748
+ return 'Defines a **message from the user** in the conversation history.';
9749
+ }
9750
+ /**
9751
+ * Icon for this commitment.
9752
+ */
9753
+ get icon() {
9754
+ return '🧑';
9755
+ }
9756
+ /**
9757
+ * Markdown documentation for USER MESSAGE commitment.
9758
+ */
9759
+ get documentation() {
9760
+ return spaceTrim$1.spaceTrim(`
9761
+ # ${this.type}
9762
+
9763
+ Defines a message from the user in the conversation history. This is used to pre-fill the chat with a conversation history or to provide few-shot examples.
9764
+
9765
+ ## Key aspects
9766
+
9767
+ - Represents a message sent by the user.
9768
+ - Used for setting up conversation context.
9769
+ - Can be used in conjunction with AGENT MESSAGE.
9770
+
9771
+ ## Examples
9772
+
9773
+ \`\`\`book
9774
+ Conversation History
9775
+
9776
+ USER MESSAGE Hello, I have a problem.
9777
+ AGENT MESSAGE What seems to be the issue?
9778
+ USER MESSAGE My computer is not starting.
9779
+ \`\`\`
9780
+ `);
9781
+ }
9782
+ applyToAgentModelRequirements(requirements, content) {
9783
+ return {
9784
+ ...requirements,
9785
+ metadata: {
9786
+ ...requirements.metadata,
9787
+ pendingUserMessage: content,
9788
+ },
9789
+ };
9790
+ }
9791
+ }
9792
+
9793
+ /**
9794
+ * META commitment definition
9795
+ *
9796
+ * The META commitment handles all meta-information about the agent such as:
9797
+ * - META IMAGE: Sets the agent's avatar/profile image URL
9798
+ * - META LINK: Provides profile/source links for the person the agent models
9799
+ * - META TITLE: Sets the agent's display title
9800
+ * - META DESCRIPTION: Sets the agent's description
9801
+ * - META [ANYTHING]: Any other meta information in uppercase format
9802
+ *
9803
+ * These commitments are special because they don't affect the system message,
9804
+ * but are handled separately in the parsing logic for profile display.
9805
+ *
9806
+ * Example usage in agent source:
9807
+ *
9808
+ * ```book
9809
+ * META IMAGE https://example.com/avatar.jpg
9810
+ * META LINK https://twitter.com/username
9811
+ * META TITLE Professional Assistant
9812
+ * META DESCRIPTION An AI assistant specialized in business tasks
9813
+ * META AUTHOR John Doe
9814
+ * META VERSION 1.0
9815
+ * ```
9816
+ *
9817
+ * @private [🪔] Maybe export the commitments through some package
9818
+ */
9819
+ class MetaCommitmentDefinition extends BaseCommitmentDefinition {
9820
+ constructor() {
9821
+ super('META');
9822
+ }
9823
+ /**
9824
+ * Short one-line description of META commitments.
9825
+ */
9826
+ get description() {
9827
+ return 'Set meta-information about the agent (IMAGE, LINK, TITLE, DESCRIPTION, etc.).';
9828
+ }
9829
+ /**
9830
+ * Icon for this commitment.
9831
+ */
9832
+ get icon() {
9833
+ return 'ℹ️';
9834
+ }
9835
+ /**
9836
+ * Markdown documentation for META commitment.
9837
+ */
9838
+ get documentation() {
9839
+ return spaceTrim$1.spaceTrim(`
9840
+ # META
9841
+
9842
+ Sets meta-information about the agent that is used for display and attribution purposes.
9843
+
9844
+ ## Supported META types
9845
+
9846
+ - **META IMAGE** - Sets the agent's avatar/profile image URL
9847
+ - **META LINK** - Provides profile/source links for the person the agent models
9848
+ - **META TITLE** - Sets the agent's display title
9849
+ - **META DESCRIPTION** - Sets the agent's description
9850
+ - **META [ANYTHING]** - Any other meta information in uppercase format
9851
+
9852
+ ## Key aspects
9853
+
9854
+ - Does not modify the agent's behavior or responses
9855
+ - Used for visual representation and attribution in user interfaces
9856
+ - Multiple META commitments of different types can be used
9857
+ - Multiple META LINK commitments can be used for different social profiles
9858
+ - If multiple META commitments of the same type are specified, the last one takes precedence (except for LINK)
9859
+
9860
+ ## Examples
9861
+
9862
+ ### Basic meta information
9863
+
9864
+ \`\`\`book
9865
+ Professional Assistant
9866
+
9867
+ META IMAGE https://example.com/professional-avatar.jpg
9868
+ META TITLE Senior Business Consultant
9869
+ META DESCRIPTION Specialized in strategic planning and project management
9870
+ META LINK https://linkedin.com/in/professional
9871
+ \`\`\`
9872
+
9873
+ ### Multiple links and custom meta
9874
+
9875
+ \`\`\`book
9876
+ Open Source Developer
9877
+
9878
+ META IMAGE /assets/dev-avatar.png
9879
+ META LINK https://github.com/developer
9880
+ META LINK https://twitter.com/devhandle
9881
+ META AUTHOR Jane Smith
9882
+ META VERSION 2.1
9883
+ META LICENSE MIT
9884
+ \`\`\`
9885
+
9886
+ ### Creative assistant
9887
+
9888
+ \`\`\`book
9889
+ Creative Helper
9890
+
9891
+ META IMAGE https://example.com/creative-bot.jpg
9892
+ META TITLE Creative Writing Assistant
9893
+ META DESCRIPTION Helps with brainstorming, storytelling, and creative projects
9894
+ META INSPIRATION Books, movies, and real-world experiences
9895
+ \`\`\`
9896
+ `);
9897
+ }
9898
+ applyToAgentModelRequirements(requirements, content) {
9899
+ // META commitments don't modify the system message or model requirements
9900
+ // They are handled separately in the parsing logic for meta information extraction
9901
+ // This method exists for consistency with the CommitmentDefinition interface
9902
+ return requirements;
9903
+ }
9904
+ /**
9905
+ * Extracts meta information from the content based on the meta type
9906
+ * This is used by the parsing logic
9907
+ */
9908
+ extractMetaValue(metaType, content) {
9909
+ const trimmedContent = content.trim();
9910
+ return trimmedContent || null;
9911
+ }
9912
+ /**
9913
+ * Validates if the provided content is a valid URL (for IMAGE and LINK types)
9914
+ */
9915
+ isValidUrl(content) {
9916
+ try {
9917
+ new URL(content.trim());
9918
+ return true;
9919
+ }
9920
+ catch (_a) {
9921
+ return false;
9922
+ }
9923
+ }
9924
+ /**
9925
+ * Checks if this is a known meta type
9926
+ */
9927
+ isKnownMetaType(metaType) {
9928
+ const knownTypes = ['IMAGE', 'LINK', 'TITLE', 'DESCRIPTION', 'AUTHOR', 'VERSION', 'LICENSE'];
9929
+ return knownTypes.includes(metaType.toUpperCase());
9930
+ }
9931
+ }
9932
+ /**
9933
+ * Note: [💞] Ignore a discrepancy between file name and entity name
9934
+ */
9935
+
9936
+ /**
9937
+ * META COLOR commitment definition
9938
+ *
9939
+ * The META COLOR commitment sets the agent's accent color.
9940
+ * This commitment is special because it doesn't affect the system message,
9941
+ * but is handled separately in the parsing logic.
9942
+ *
9943
+ * Example usage in agent source:
9944
+ *
9945
+ * ```book
9946
+ * META COLOR #ff0000
9947
+ * META COLOR #00ff00
9948
+ * ```
9949
+ *
9950
+ * You can also specify multiple colors separated by comma:
9951
+ *
9952
+ * ```book
9953
+ * META COLOR #ff0000, #00ff00, #0000ff
9954
+ * ```
9955
+ *
9956
+ * @private [🪔] Maybe export the commitments through some package
9957
+ */
9958
+ class MetaColorCommitmentDefinition extends BaseCommitmentDefinition {
9959
+ constructor() {
9960
+ super('META COLOR', ['COLOR']);
9961
+ }
9962
+ /**
9963
+ * Short one-line description of META COLOR.
9964
+ */
9965
+ get description() {
9966
+ return "Set the agent's accent color or gradient.";
9967
+ }
9968
+ /**
9969
+ * Icon for this commitment.
9970
+ */
9971
+ get icon() {
9972
+ return '🎨';
9973
+ }
9974
+ /**
9975
+ * Markdown documentation for META COLOR commitment.
9976
+ */
9977
+ get documentation() {
9978
+ return spaceTrim$1.spaceTrim(`
9979
+ # META COLOR
9980
+
9981
+ Sets the agent's accent color or gradient.
9982
+
9983
+ ## Key aspects
9984
+
9985
+ - Does not modify the agent's behavior or responses.
9986
+ - Only one \`META COLOR\` should be used per agent.
9987
+ - If multiple are specified, the last one takes precedence.
9988
+ - Used for visual representation in user interfaces.
9989
+ - Can specify multiple colors separated by comma to create a gradient.
9990
+
9991
+ ## Examples
9992
+
9993
+ \`\`\`book
9994
+ Professional Assistant
9995
+
9996
+ META COLOR #3498db
9997
+ PERSONA You are a professional business assistant
9998
+ \`\`\`
9999
+
10000
+ \`\`\`book
10001
+ Creative Helper
10002
+
10003
+ META COLOR #e74c3c
10004
+ PERSONA You are a creative and inspiring assistant
10005
+ \`\`\`
10006
+
10007
+ \`\`\`book
10008
+ Gradient Agent
10009
+
10010
+ META COLOR #ff0000, #00ff00, #0000ff
10011
+ PERSONA You are a colorful agent
10012
+ \`\`\`
10013
+ `);
10014
+ }
10015
+ applyToAgentModelRequirements(requirements, content) {
10016
+ // META COLOR doesn't modify the system message or model requirements
10017
+ // It's handled separately in the parsing logic for profile color extraction
10018
+ // This method exists for consistency with the CommitmentDefinition interface
10019
+ return requirements;
10020
+ }
10021
+ /**
10022
+ * Extracts the profile color from the content
10023
+ * This is used by the parsing logic
10024
+ */
10025
+ extractProfileColor(content) {
10026
+ const trimmedContent = content.trim();
10027
+ return trimmedContent || null;
10028
+ }
10029
+ }
10030
+ /**
10031
+ * Note: [💞] Ignore a discrepancy between file name and entity name
10032
+ */
10033
+
10034
+ /**
10035
+ * META FONT commitment definition
10036
+ *
10037
+ * The META FONT commitment sets the agent's font.
10038
+ * This commitment is special because it doesn't affect the system message,
10039
+ * but is handled separately in the parsing logic.
10040
+ *
10041
+ * Example usage in agent source:
10042
+ *
10043
+ * ```book
10044
+ * META FONT Poppins, Arial, sans-serif
10045
+ * META FONT Roboto
10046
+ * ```
10047
+ *
10048
+ * @private [🪔] Maybe export the commitments through some package
10049
+ */
10050
+ class MetaFontCommitmentDefinition extends BaseCommitmentDefinition {
10051
+ constructor() {
10052
+ super('META FONT', ['FONT']);
10053
+ }
10054
+ /**
10055
+ * Short one-line description of META FONT.
10056
+ */
10057
+ get description() {
10058
+ return "Set the agent's font.";
10059
+ }
10060
+ /**
10061
+ * Icon for this commitment.
10062
+ */
10063
+ get icon() {
10064
+ return '🔤';
10065
+ }
10066
+ /**
10067
+ * Markdown documentation for META FONT commitment.
10068
+ */
10069
+ get documentation() {
10070
+ return spaceTrim$1.spaceTrim(`
10071
+ # META FONT
10072
+
10073
+ Sets the agent's font.
10074
+
10075
+ ## Key aspects
10076
+
10077
+ - Does not modify the agent's behavior or responses.
10078
+ - Only one \`META FONT\` should be used per agent.
10079
+ - If multiple are specified, the last one takes precedence.
10080
+ - Used for visual representation in user interfaces.
10081
+ - Supports Google Fonts.
10082
+
10083
+ ## Examples
10084
+
10085
+ \`\`\`book
10086
+ Modern Assistant
10087
+
10088
+ META FONT Poppins, Arial, sans-serif
10089
+ PERSONA You are a modern assistant
10090
+ \`\`\`
10091
+
10092
+ \`\`\`book
10093
+ Classic Helper
10094
+
10095
+ META FONT Times New Roman
10096
+ PERSONA You are a classic helper
10097
+ \`\`\`
10098
+ `);
10099
+ }
10100
+ applyToAgentModelRequirements(requirements, content) {
10101
+ // META FONT doesn't modify the system message or model requirements
10102
+ // It's handled separately in the parsing logic
10103
+ // This method exists for consistency with the CommitmentDefinition interface
10104
+ return requirements;
10105
+ }
10106
+ /**
10107
+ * Extracts the font from the content
10108
+ * This is used by the parsing logic
10109
+ */
10110
+ extractProfileFont(content) {
10111
+ const trimmedContent = content.trim();
10112
+ return trimmedContent || null;
10113
+ }
10114
+ }
10115
+ /**
10116
+ * Note: [💞] Ignore a discrepancy between file name and entity name
10117
+ */
10118
+
10119
+ /**
10120
+ * META IMAGE commitment definition
10121
+ *
10122
+ * The META IMAGE commitment sets the agent's avatar/profile image URL.
10123
+ * This commitment is special because it doesn't affect the system message,
10124
+ * but is handled separately in the parsing logic.
10125
+ *
10126
+ * Example usage in agent source:
10127
+ *
10128
+ * ```book
10129
+ * META IMAGE https://example.com/avatar.jpg
10130
+ * META IMAGE /assets/agent-avatar.png
10131
+ * ```
10132
+ *
10133
+ * @private [🪔] Maybe export the commitments through some package
10134
+ */
10135
+ class MetaImageCommitmentDefinition extends BaseCommitmentDefinition {
10136
+ constructor() {
10137
+ super('META IMAGE', ['IMAGE']);
10138
+ }
10139
+ /**
10140
+ * Short one-line description of META IMAGE.
10141
+ */
10142
+ get description() {
10143
+ return "Set the agent's profile image URL.";
10144
+ }
10145
+ /**
10146
+ * Icon for this commitment.
10147
+ */
10148
+ get icon() {
10149
+ return '🖼️';
10150
+ }
10151
+ /**
10152
+ * Markdown documentation for META IMAGE commitment.
10153
+ */
10154
+ get documentation() {
10155
+ return spaceTrim$1.spaceTrim(`
10156
+ # META IMAGE
10157
+
10158
+ Sets the agent's avatar/profile image URL.
10159
+
10160
+ ## Key aspects
10161
+
10162
+ - Does not modify the agent's behavior or responses.
10163
+ - Only one \`META IMAGE\` should be used per agent.
10164
+ - If multiple are specified, the last one takes precedence.
10165
+ - Used for visual representation in user interfaces.
10166
+
10167
+ ## Examples
10168
+
10169
+ \`\`\`book
10170
+ Professional Assistant
10171
+
10172
+ META IMAGE https://example.com/professional-avatar.jpg
10173
+ PERSONA You are a professional business assistant
10174
+ STYLE Maintain a formal and courteous tone
10175
+ \`\`\`
10176
+
10177
+ \`\`\`book
10178
+ Creative Helper
10179
+
10180
+ META IMAGE /assets/creative-bot-avatar.png
10181
+ PERSONA You are a creative and inspiring assistant
10182
+ STYLE Be enthusiastic and encouraging
10183
+ ACTION Can help with brainstorming and ideation
10184
+ \`\`\`
10185
+ `);
10186
+ }
10187
+ applyToAgentModelRequirements(requirements, content) {
10188
+ // META IMAGE doesn't modify the system message or model requirements
10189
+ // It's handled separately in the parsing logic for profile image extraction
10190
+ // This method exists for consistency with the CommitmentDefinition interface
10191
+ return requirements;
10192
+ }
10193
+ /**
10194
+ * Extracts the profile image URL from the content
10195
+ * This is used by the parsing logic
10196
+ */
10197
+ extractProfileImageUrl(content) {
10198
+ const trimmedContent = content.trim();
10199
+ return trimmedContent || null;
10200
+ }
10201
+ }
10202
+ /**
10203
+ * Note: [💞] Ignore a discrepancy between file name and entity name
10204
+ */
10205
+
10206
+ /**
10207
+ * META LINK commitment definition
10208
+ *
10209
+ * The `META LINK` commitment represents the link to the person from whom the agent is created.
10210
+ * This commitment is special because it doesn't affect the system message,
10211
+ * but is handled separately in the parsing logic for profile display.
10212
+ *
10213
+ * Example usage in agent source:
10214
+ *
10215
+ * ```
10216
+ * META LINK https://twitter.com/username
10217
+ * META LINK https://linkedin.com/in/profile
10218
+ * META LINK https://github.com/username
10219
+ * ```
10220
+ *
10221
+ * Multiple `META LINK` commitments can be used when there are multiple sources:
10222
+ *
10223
+ * ```book
10224
+ * META LINK https://twitter.com/username
10225
+ * META LINK https://linkedin.com/in/profile
10226
+ * ```
10227
+ *
10228
+ * @private [🪔] Maybe export the commitments through some package
10229
+ */
10230
+ class MetaLinkCommitmentDefinition extends BaseCommitmentDefinition {
10231
+ constructor() {
10232
+ super('META LINK');
10233
+ }
10234
+ /**
10235
+ * Short one-line description of META LINK.
10236
+ */
10237
+ get description() {
10238
+ return 'Provide profile/source links for the person the agent models.';
10239
+ }
10240
+ /**
10241
+ * Icon for this commitment.
10242
+ */
10243
+ get icon() {
10244
+ return '🔗';
10245
+ }
10246
+ /**
10247
+ * Markdown documentation for META LINK commitment.
10248
+ */
10249
+ get documentation() {
10250
+ return spaceTrim$1.spaceTrim(`
10251
+ # META LINK
10252
+
10253
+ Represents a profile or source link for the person the agent is modeled after.
10254
+
10255
+ ## Key aspects
10256
+
10257
+ - Does not modify the agent's behavior or responses.
10258
+ - Multiple \`META LINK\` commitments can be used for different social profiles.
10259
+ - Used for attribution and crediting the original person.
10260
+ - Displayed in user interfaces for transparency.
10261
+
10262
+ ## Examples
10263
+
10264
+ \`\`\`book
10265
+ Expert Consultant
10266
+
10267
+ META LINK https://twitter.com/expertname
10268
+ META LINK https://linkedin.com/in/expertprofile
10269
+ PERSONA You are Dr. Smith, a renowned expert in artificial intelligence
10270
+ KNOWLEDGE Extensive background in machine learning and neural networks
10271
+ \`\`\`
10272
+
10273
+ \`\`\`book
10274
+ Open Source Developer
10275
+
10276
+ META LINK https://github.com/developer
10277
+ META LINK https://twitter.com/devhandle
10278
+ PERSONA You are an experienced open source developer
10279
+ ACTION Can help with code reviews and architecture decisions
10280
+ STYLE Be direct and technical in explanations
10281
+ \`\`\`
10282
+ `);
10283
+ }
10284
+ applyToAgentModelRequirements(requirements, content) {
10285
+ // META LINK doesn't modify the system message or model requirements
10286
+ // It's handled separately in the parsing logic for profile link extraction
10287
+ // This method exists for consistency with the CommitmentDefinition interface
10288
+ return requirements;
10289
+ }
10290
+ /**
10291
+ * Extracts the profile link URL from the content
10292
+ * This is used by the parsing logic
10293
+ */
10294
+ extractProfileLinkUrl(content) {
10295
+ const trimmedContent = content.trim();
10296
+ return trimmedContent || null;
10297
+ }
10298
+ /**
10299
+ * Validates if the provided content is a valid URL
10300
+ */
10301
+ isValidUrl(content) {
10302
+ try {
10303
+ new URL(content.trim());
10304
+ return true;
10305
+ }
10306
+ catch (_a) {
10307
+ return false;
10308
+ }
10309
+ }
10310
+ }
10311
+ /**
10312
+ * Note: [💞] Ignore a discrepancy between file name and entity name
10313
+ */
10314
+
10315
+ /**
10316
+ * MODEL commitment definition
10317
+ *
10318
+ * The MODEL commitment specifies which AI model to use and can also set
10319
+ * model-specific parameters like temperature, topP, topK, and maxTokens.
10320
+ *
10321
+ * Supports multiple syntax variations:
10322
+ *
10323
+ * Single-line format:
10324
+ * ```book
10325
+ * MODEL gpt-4
10326
+ * MODEL claude-3-opus temperature=0.3
10327
+ * MODEL gpt-3.5-turbo temperature=0.8 topP=0.9
10328
+ * ```
10329
+ *
10330
+ * Multi-line named parameter format:
10331
+ * ```book
10332
+ * MODEL NAME gpt-4
10333
+ * MODEL TEMPERATURE 0.7
10334
+ * MODEL TOP_P 0.9
10335
+ * MODEL MAX_TOKENS 2048
10336
+ * ```
10337
+ *
10338
+ * @private [🪔] Maybe export the commitments through some package
10339
+ */
10340
+ class ModelCommitmentDefinition extends BaseCommitmentDefinition {
10341
+ constructor(type = 'MODEL') {
10342
+ super(type);
10343
+ }
10344
+ /**
10345
+ * Short one-line description of MODEL.
10346
+ */
10347
+ get description() {
10348
+ return 'Enforce AI model requirements including name and technical parameters.';
10349
+ }
10350
+ /**
10351
+ * Icon for this commitment.
10352
+ */
10353
+ get icon() {
10354
+ return '⚙️';
10355
+ }
10356
+ /**
10357
+ * Markdown documentation for MODEL commitment.
10358
+ */
10359
+ get documentation() {
10360
+ return spaceTrim$1.spaceTrim(`
10361
+ # ${this.type}
10362
+
10363
+ Enforces technical parameters for the AI model, ensuring consistent behavior across different execution environments.
10364
+
10365
+ ## Key aspects
10366
+
10367
+ - When no \`MODEL\` commitment is specified, the best model requirement is picked automatically based on the agent \`PERSONA\`, \`KNOWLEDGE\`, \`TOOLS\` and other commitments
10368
+ - Multiple \`MODEL\` commitments can be used to specify different parameters
10369
+ - Both \`MODEL\` and \`MODELS\` terms work identically and can be used interchangeably
10370
+ - Parameters control the randomness, creativity, and technical aspects of model responses
10371
+
10372
+ ## Syntax variations
10373
+
10374
+ ### Single-line format (legacy support)
10375
+ \`\`\`book
10376
+ MODEL gpt-4
10377
+ MODEL claude-3-opus temperature=0.3
10378
+ MODEL gpt-3.5-turbo temperature=0.8 topP=0.9
10379
+ \`\`\`
10380
+
10381
+ ### Multi-line named parameter format (recommended)
10382
+ \`\`\`book
10383
+ MODEL NAME gpt-4
10384
+ MODEL TEMPERATURE 0.7
10385
+ MODEL TOP_P 0.9
10386
+ MODEL MAX_TOKENS 2048
10387
+ \`\`\`
10388
+
10389
+ ## Supported parameters
10390
+
10391
+ - \`NAME\`: The specific model to use (e.g., 'gpt-4', 'claude-3-opus')
10392
+ - \`TEMPERATURE\`: Controls randomness (0.0 = deterministic, 1.0+ = creative)
10393
+ - \`TOP_P\`: Nucleus sampling parameter for controlling diversity
10394
+ - \`TOP_K\`: Top-k sampling parameter for limiting vocabulary
10395
+ - \`MAX_TOKENS\`: Maximum number of tokens the model can generate
10396
+
10397
+ ## Examples
10398
+
10399
+ ### Precise deterministic assistant
10400
+ \`\`\`book
10401
+ Precise Assistant
10402
+
10403
+ PERSONA You are a precise and accurate assistant
10404
+ MODEL NAME gpt-4
10405
+ MODEL TEMPERATURE 0.1
10406
+ MODEL MAX_TOKENS 1024
10407
+ RULE Always provide factual information
10408
+ \`\`\`
10409
+
10410
+ ### Creative writing assistant
10411
+ \`\`\`book
10412
+ Creative Writer
10413
+
10414
+ PERSONA You are a creative writing assistant
10415
+ MODEL NAME claude-3-opus
10416
+ MODEL TEMPERATURE 0.8
10417
+ MODEL TOP_P 0.9
10418
+ MODEL MAX_TOKENS 2048
10419
+ STYLE Be imaginative and expressive
10420
+ ACTION Can help with storytelling and character development
10421
+ \`\`\`
10422
+
10423
+ ### Balanced conversational agent
10424
+ \`\`\`book
10425
+ Balanced Assistant
10426
+
10427
+ PERSONA You are a helpful and balanced assistant
10428
+ MODEL NAME gpt-4
10429
+ MODEL TEMPERATURE 0.7
10430
+ MODEL TOP_P 0.95
10431
+ MODEL TOP_K 40
10432
+ MODEL MAX_TOKENS 1500
10433
+ \`\`\`
10434
+ `);
10435
+ }
10436
+ applyToAgentModelRequirements(requirements, content) {
10437
+ var _a;
10438
+ const trimmedContent = content.trim();
10439
+ if (!trimmedContent) {
10440
+ return requirements;
10441
+ }
10442
+ const parts = trimmedContent.split(/\s+/);
10443
+ const firstPart = (_a = parts[0]) === null || _a === void 0 ? void 0 : _a.toUpperCase();
10444
+ // Check if this is the new named parameter format
10445
+ if (this.isNamedParameter(firstPart)) {
10446
+ return this.parseNamedParameter(requirements, firstPart, parts.slice(1));
10447
+ }
10448
+ else {
10449
+ // Legacy single-line format: "MODEL gpt-4 temperature=0.3 topP=0.9"
10450
+ return this.parseLegacyFormat(requirements, parts);
10451
+ }
10452
+ }
10453
+ /**
10454
+ * Check if the first part is a known named parameter
10455
+ */
10456
+ isNamedParameter(part) {
10457
+ if (!part)
10458
+ return false;
10459
+ const knownParams = ['NAME', 'TEMPERATURE', 'TOP_P', 'TOP_K', 'MAX_TOKENS'];
10460
+ return knownParams.includes(part);
10461
+ }
10462
+ /**
10463
+ * Parse the new named parameter format: "MODEL TEMPERATURE 0.7"
10464
+ */
10465
+ parseNamedParameter(requirements, parameterName, valueParts) {
10466
+ const value = valueParts.join(' ').trim();
10467
+ if (!value) {
10468
+ return requirements;
10469
+ }
10470
+ const result = { ...requirements };
10471
+ switch (parameterName) {
10472
+ case 'NAME':
10473
+ result.modelName = value;
10474
+ break;
10475
+ case 'TEMPERATURE': {
10476
+ const temperature = parseFloat(value);
10477
+ if (!isNaN(temperature)) {
10478
+ result.temperature = temperature;
10479
+ }
10480
+ break;
10481
+ }
10482
+ case 'TOP_P': {
10483
+ const topP = parseFloat(value);
10484
+ if (!isNaN(topP)) {
10485
+ result.topP = topP;
10486
+ }
10487
+ break;
10488
+ }
10489
+ case 'TOP_K': {
10490
+ const topK = parseFloat(value);
10491
+ if (!isNaN(topK)) {
10492
+ result.topK = Math.round(topK);
10493
+ }
10494
+ break;
10495
+ }
10496
+ case 'MAX_TOKENS': {
10497
+ const maxTokens = parseFloat(value);
10498
+ if (!isNaN(maxTokens)) {
10499
+ result.maxTokens = Math.round(maxTokens);
10500
+ }
10501
+ break;
10502
+ }
10503
+ }
10504
+ return result;
10505
+ }
10506
+ /**
10507
+ * Parse the legacy format: "MODEL gpt-4 temperature=0.3 topP=0.9"
10508
+ */
10509
+ parseLegacyFormat(requirements, parts) {
10510
+ const modelName = parts[0];
10511
+ if (!modelName) {
10512
+ return requirements;
10513
+ }
10514
+ // Start with the model name
10515
+ const result = {
10516
+ ...requirements,
10517
+ modelName,
10518
+ };
10519
+ // Parse additional key=value parameters
10520
+ for (let i = 1; i < parts.length; i++) {
10521
+ const param = parts[i];
10522
+ if (param && param.includes('=')) {
10523
+ const [key, value] = param.split('=');
10524
+ if (key && value) {
10525
+ const numValue = parseFloat(value);
10526
+ if (!isNaN(numValue)) {
10527
+ switch (key.toLowerCase()) {
10528
+ case 'temperature':
10529
+ result.temperature = numValue;
10530
+ break;
10531
+ case 'topp':
10532
+ case 'top_p':
10533
+ result.topP = numValue;
10534
+ break;
10535
+ case 'topk':
10536
+ case 'top_k':
10537
+ result.topK = Math.round(numValue);
10538
+ break;
10539
+ case 'max_tokens':
10540
+ case 'maxTokens':
10541
+ result.maxTokens = Math.round(numValue);
10542
+ break;
10543
+ }
10544
+ }
10545
+ }
10546
+ }
10547
+ }
10548
+ return result;
10549
+ }
10550
+ }
10551
+ /**
10552
+ * Note: [💞] Ignore a discrepancy between file name and entity name
10553
+ */
10554
+
10555
+ /**
10556
+ * NOTE commitment definition
10557
+ *
10558
+ * The NOTE commitment is used to add comments to the agent source without making any changes
10559
+ * to the system message or agent model requirements. It serves as a documentation mechanism
10560
+ * for developers to add explanatory comments, reminders, or annotations directly in the agent source.
10561
+ *
10562
+ * Key features:
10563
+ * - Makes no changes to the system message
10564
+ * - Makes no changes to agent model requirements
10565
+ * - Content is preserved in metadata.NOTE for debugging and inspection
10566
+ * - Multiple NOTE commitments are aggregated together
10567
+ * - Comments (# NOTE) are removed from the final system message
10568
+ *
10569
+ * Example usage in agent source:
10570
+ *
10571
+ * ```book
10572
+ * NOTE This agent was designed for customer support scenarios
10573
+ * NOTE Remember to update the knowledge base monthly
10574
+ * NOTE Performance optimized for quick response times
10575
+ * ```
10576
+ *
10577
+ * The above notes will be stored in metadata but won't affect the agent's behavior.
10578
+ *
10579
+ * @private [🪔] Maybe export the commitments through some package
10580
+ */
10581
+ class NoteCommitmentDefinition extends BaseCommitmentDefinition {
10582
+ constructor(type = 'NOTE') {
10583
+ super(type);
10584
+ }
10585
+ /**
10586
+ * Short one-line description of NOTE.
10587
+ */
10588
+ get description() {
10589
+ return 'Add developer-facing notes without changing behavior or output.';
10590
+ }
10591
+ /**
10592
+ * Icon for this commitment.
10593
+ */
10594
+ get icon() {
10595
+ return '📝';
10596
+ }
10597
+ /**
10598
+ * Markdown documentation for NOTE commitment.
10599
+ */
10600
+ get documentation() {
10601
+ return spaceTrim$1.spaceTrim(`
10602
+ # ${this.type}
10603
+
10604
+ Adds comments for documentation without changing agent behavior.
10605
+
10606
+ ## Key aspects
10607
+
10608
+ - Does not modify the agent's behavior or responses.
10609
+ - Multiple \`NOTE\`, \`NOTES\`, \`COMMENT\`, and \`NONCE\` commitments are aggregated for debugging.
10610
+ - All four terms work identically and can be used interchangeably.
10611
+ - Useful for documenting design decisions and reminders.
10612
+ - Content is preserved in metadata for inspection.
10613
+
10614
+ ## Examples
10615
+
10616
+ \`\`\`book
10617
+ Customer Support Bot
10618
+
10619
+ NOTE This agent was designed for customer support scenarios
10620
+ COMMENT Remember to update the knowledge base monthly
10621
+ PERSONA You are a helpful customer support representative
10622
+ KNOWLEDGE Company policies and procedures
10623
+ RULE Always be polite and professional
10624
+ \`\`\`
10625
+
10626
+ \`\`\`book
10627
+ Research Assistant
10628
+
10629
+ NONCE Performance optimized for quick response times
10630
+ NOTE Uses RAG for accessing latest research papers
10631
+ PERSONA You are a knowledgeable research assistant
10632
+ ACTION Can help with literature reviews and citations
10633
+ STYLE Present information in academic format
10634
+ \`\`\`
10635
+ `);
10636
+ }
10637
+ applyToAgentModelRequirements(requirements, content) {
10638
+ // The NOTE commitment makes no changes to the system message or model requirements
10639
+ // It only stores the note content in metadata for documentation purposes
10640
+ const trimmedContent = spaceTrim$1.spaceTrim(content);
10641
+ if (trimmedContent === '') {
10642
+ return requirements;
10643
+ }
10644
+ // Return requirements with updated notes but no changes to system message
10645
+ return {
10646
+ ...requirements,
10647
+ notes: [...(requirements.notes || []), trimmedContent],
10648
+ };
10649
+ }
10650
+ }
10651
+ /**
10652
+ * [💞] Ignore a discrepancy between file name and entity name
10653
+ */
10654
+
10655
+ /**
10656
+ * OPEN commitment definition
10657
+ *
10658
+ * The OPEN commitment specifies that the agent can be modified by conversation.
10659
+ * This is the default behavior.
10660
+ *
10661
+ * Example usage in agent source:
10662
+ *
10663
+ * ```book
10664
+ * OPEN
10665
+ * ```
10666
+ *
10667
+ * @private [🪔] Maybe export the commitments through some package
10668
+ */
10669
+ class OpenCommitmentDefinition extends BaseCommitmentDefinition {
10670
+ constructor() {
10671
+ super('OPEN');
10672
+ }
10673
+ /**
10674
+ * Short one-line description of OPEN.
10675
+ */
10676
+ get description() {
10677
+ return 'Allow the agent to be modified by conversation (default).';
10678
+ }
10679
+ /**
10680
+ * Icon for this commitment.
10681
+ */
10682
+ get icon() {
10683
+ return '🔓';
10684
+ }
10685
+ /**
10686
+ * Markdown documentation for OPEN commitment.
10687
+ */
10688
+ get documentation() {
10689
+ return spaceTrim$1.spaceTrim(`
10690
+ # OPEN
10691
+
10692
+ Specifies that the agent can be modified by conversation with it.
10693
+ This means the agent will learn from interactions and update its source code.
10694
+
10695
+ This is the default behavior if neither \`OPEN\` nor \`CLOSED\` is specified.
10696
+
10697
+ > See also [CLOSED](/docs/CLOSED)
10698
+
10699
+ ## Example
10700
+
10701
+ \`\`\`book
10702
+ OPEN
10703
+ \`\`\`
10704
+ `);
10705
+ }
10706
+ applyToAgentModelRequirements(requirements, _content) {
10707
+ // Since OPEN is default, we can just ensure isClosed is false
10708
+ // But to be explicit we can set it
10709
+ const updatedMetadata = {
10710
+ ...requirements.metadata,
10711
+ isClosed: false,
10712
+ };
10713
+ return {
10714
+ ...requirements,
10715
+ metadata: updatedMetadata,
10716
+ };
10717
+ }
10718
+ }
10719
+ /**
10720
+ * Note: [💞] Ignore a discrepancy between file name and entity name
10721
+ */
10722
+
10723
+ /**
10724
+ * PERSONA commitment definition
10725
+ *
10726
+ * The PERSONA commitment modifies the agent's personality and character in the system message.
10727
+ * It defines who the agent is, their background, expertise, and personality traits.
10728
+ *
10729
+ * Key features:
10730
+ * - Multiple PERSONA commitments are automatically merged into one
10731
+ * - Content is placed at the beginning of the system message
10732
+ * - Original content with comments is preserved in metadata.PERSONA
10733
+ * - Comments (# PERSONA) are removed from the final system message
10734
+ *
10735
+ * Example usage in agent source:
10736
+ *
10737
+ * ```book
10738
+ * PERSONA You are a helpful programming assistant with expertise in TypeScript and React
10739
+ * PERSONA You have deep knowledge of modern web development practices
10740
+ * ```
10741
+ *
10742
+ * The above will be merged into a single persona section at the beginning of the system message.
10743
+ *
10744
+ * @private [🪔] Maybe export the commitments through some package
10745
+ */
10746
+ class PersonaCommitmentDefinition extends BaseCommitmentDefinition {
10747
+ constructor(type = 'PERSONA') {
10748
+ super(type);
10749
+ }
10750
+ /**
10751
+ * Short one-line description of PERSONA.
10752
+ */
10753
+ get description() {
10754
+ return 'Define who the agent is: background, expertise, and personality.';
10755
+ }
10756
+ /**
10757
+ * Icon for this commitment.
10758
+ */
10759
+ get icon() {
10760
+ return '👤';
10761
+ }
10762
+ /**
10763
+ * Markdown documentation for PERSONA commitment.
10764
+ */
10765
+ get documentation() {
10766
+ return spaceTrim$1.spaceTrim(`
10767
+ # ${this.type}
10768
+
10769
+ Defines who the agent is, their background, expertise, and personality traits.
10770
+
10771
+ ## Key aspects
10772
+
10773
+ - Multiple \`PERSONA\` and \`PERSONAE\` commitments are merged together.
10774
+ - Both terms work identically and can be used interchangeably.
10775
+ - If they are in conflict, the last one takes precedence.
10776
+ - You can write persona content in multiple lines.
10777
+
10778
+ ## Examples
10779
+
10780
+ \`\`\`book
10781
+ Programming Assistant
10782
+
10783
+ PERSONA You are a helpful programming assistant with expertise in TypeScript and React
10784
+ PERSONA You have deep knowledge of modern web development practices
10785
+ \`\`\`
10786
+ `);
10787
+ }
10788
+ applyToAgentModelRequirements(requirements, content) {
10789
+ var _a, _b;
10790
+ // The PERSONA commitment aggregates all persona content and places it at the beginning
10791
+ const trimmedContent = content.trim();
10792
+ if (!trimmedContent) {
10793
+ return requirements;
10794
+ }
10795
+ // Get existing persona content from metadata
10796
+ const existingPersonaContent = ((_a = requirements.metadata) === null || _a === void 0 ? void 0 : _a.PERSONA) || '';
10797
+ // Merge the new content with existing persona content
10798
+ // When multiple PERSONA commitments exist, they are merged into one
10799
+ const mergedPersonaContent = existingPersonaContent
10800
+ ? `${existingPersonaContent}\n${trimmedContent}`
10801
+ : trimmedContent;
10802
+ // Store the merged persona content in metadata for debugging and inspection
10803
+ const updatedMetadata = {
10804
+ ...requirements.metadata,
10805
+ PERSONA: mergedPersonaContent,
10806
+ };
10807
+ // Get the agent name from metadata (which should contain the first line of agent source)
10808
+ // If not available, extract from current system message as fallback
10809
+ let agentName = (_b = requirements.metadata) === null || _b === void 0 ? void 0 : _b.agentName;
10810
+ if (!agentName) {
10811
+ // Fallback: extract from current system message
10812
+ const currentMessage = requirements.systemMessage.trim();
10813
+ const basicFormatMatch = currentMessage.match(/^You are (.+)$/);
10814
+ if (basicFormatMatch && basicFormatMatch[1]) {
10815
+ agentName = basicFormatMatch[1];
10816
+ }
10817
+ else {
10818
+ agentName = 'AI Agent'; // Final fallback
10819
+ }
10820
+ }
10821
+ // Remove any existing persona content from the system message
10822
+ // (this handles the case where we're processing multiple PERSONA commitments)
10823
+ const currentMessage = requirements.systemMessage.trim();
10824
+ let cleanedMessage = currentMessage;
10825
+ // Check if current message starts with persona content or is just the basic format
10826
+ const basicFormatRegex = /^You are .+$/;
10827
+ const isBasicFormat = basicFormatRegex.test(currentMessage) && !currentMessage.includes('\n');
10828
+ if (isBasicFormat) {
10829
+ // Replace the basic format entirely
10830
+ cleanedMessage = '';
10831
+ }
10832
+ else if (currentMessage.startsWith('# PERSONA')) {
10833
+ // Remove existing persona section by finding where it ends
10834
+ const lines = currentMessage.split('\n');
10835
+ let personaEndIndex = lines.length;
10836
+ // Find the end of the PERSONA section (next comment or end of message)
10837
+ for (let i = 1; i < lines.length; i++) {
10838
+ const line = lines[i].trim();
10839
+ if (line.startsWith('#') && !line.startsWith('# PERSONA')) {
10840
+ personaEndIndex = i;
10841
+ break;
10842
+ }
10843
+ }
10844
+ // Keep everything after the PERSONA section
10845
+ cleanedMessage = lines.slice(personaEndIndex).join('\n').trim();
10846
+ }
10847
+ // TODO: [🕛] There should be `agentFullname` not `agentName`
10848
+ // Create new system message with persona at the beginning
10849
+ // Format: "You are {agentName}\n{personaContent}"
10850
+ // The # PERSONA comment will be removed later by removeCommentsFromSystemMessage
10851
+ const personaSection = `# PERSONA\nYou are ${agentName}\n${mergedPersonaContent}`; // <- TODO: Use spaceTrim
10852
+ const newSystemMessage = cleanedMessage ? `${personaSection}\n\n${cleanedMessage}` : personaSection;
10853
+ return {
10854
+ ...requirements,
10855
+ systemMessage: newSystemMessage,
10856
+ metadata: updatedMetadata,
10857
+ };
10858
+ }
10859
+ }
10860
+ /**
10861
+ * Note: [💞] Ignore a discrepancy between file name and entity name
10862
+ */
10863
+
10864
+ /**
10865
+ * RULE commitment definition
10866
+ *
10867
+ * The RULE/RULES commitment adds behavioral constraints and guidelines that the agent must follow.
10868
+ * These are specific instructions about what the agent should or shouldn't do.
10869
+ *
10870
+ * Example usage in agent source:
10871
+ *
10872
+ * ```book
10873
+ * RULE Always ask for clarification if the user's request is ambiguous
10874
+ * RULES Never provide medical advice, always refer to healthcare professionals
10875
+ * ```
10876
+ *
10877
+ * @private [🪔] Maybe export the commitments through some package
10878
+ */
10879
+ class RuleCommitmentDefinition extends BaseCommitmentDefinition {
10880
+ constructor(type = 'RULE') {
10881
+ super(type);
10882
+ }
10883
+ /**
10884
+ * Short one-line description of RULE/RULES.
10885
+ */
10886
+ get description() {
10887
+ return 'Add behavioral rules the agent must follow.';
10888
+ }
10889
+ /**
10890
+ * Icon for this commitment.
10891
+ */
10892
+ get icon() {
10893
+ return '⚖️';
10894
+ }
10895
+ /**
10896
+ * Markdown documentation for RULE/RULES commitment.
10897
+ */
10898
+ get documentation() {
10899
+ return spaceTrim$1.spaceTrim(`
10900
+ # ${this.type}
10901
+
10902
+ Adds behavioral constraints and guidelines that the agent must follow.
10903
+
10904
+ ## Key aspects
10905
+
10906
+ - All rules are treated equally regardless of singular/plural form.
10907
+ - Rules define what the agent must or must not do.
10908
+
10909
+ ## Examples
10910
+
10911
+ \`\`\`book
10912
+ Customer Support Agent
10913
+
10914
+ PERSONA You are a helpful customer support representative
10915
+ RULE Always ask for clarification if the user's request is ambiguous
10916
+ RULE Be polite and professional in all interactions
10917
+ RULES Never provide medical or legal advice
10918
+ STYLE Maintain a friendly and helpful tone
10919
+ \`\`\`
10920
+
10921
+ \`\`\`book
10922
+ Educational Tutor
10923
+
10924
+ PERSONA You are a patient and knowledgeable tutor
10925
+ RULE Break down complex concepts into simple steps
10926
+ RULE Always encourage students and celebrate their progress
10927
+ RULE If you don't know something, admit it and suggest resources
10928
+ SAMPLE When explaining math: "Let's work through this step by step..."
10929
+ \`\`\`
10930
+ `);
10931
+ }
10932
+ applyToAgentModelRequirements(requirements, content) {
10933
+ const trimmedContent = content.trim();
10934
+ if (!trimmedContent) {
10935
+ return requirements;
10936
+ }
10937
+ // Add rule to the system message
10938
+ const ruleSection = `Rule: ${trimmedContent}`;
10939
+ return this.appendToSystemMessage(requirements, ruleSection, '\n\n');
10940
+ }
10941
+ }
10942
+ /**
10943
+ * Note: [💞] Ignore a discrepancy between file name and entity name
10944
+ */
10945
+
10946
+ /**
10947
+ * SAMPLE commitment definition
10948
+ *
10949
+ * The SAMPLE/EXAMPLE commitment provides examples of how the agent should respond
10950
+ * or behave in certain situations. These examples help guide the agent's responses.
10951
+ *
10952
+ * Example usage in agent source:
10953
+ *
10954
+ * ```book
10955
+ * SAMPLE When asked about pricing, respond: "Our basic plan starts at $10/month..."
10956
+ * EXAMPLE For code questions, always include working code snippets
10957
+ * ```
10958
+ *
10959
+ * @private [🪔] Maybe export the commitments through some package
10960
+ */
10961
+ class SampleCommitmentDefinition extends BaseCommitmentDefinition {
10962
+ constructor(type = 'SAMPLE') {
10963
+ super(type);
10964
+ }
10965
+ /**
10966
+ * Short one-line description of SAMPLE/EXAMPLE.
10967
+ */
10968
+ get description() {
10969
+ return 'Provide example responses to guide behavior.';
10970
+ }
10971
+ /**
10972
+ * Icon for this commitment.
10973
+ */
10974
+ get icon() {
10975
+ return '🔍';
10976
+ }
10977
+ /**
10978
+ * Markdown documentation for SAMPLE/EXAMPLE commitment.
10979
+ */
10980
+ get documentation() {
10981
+ return spaceTrim$1.spaceTrim(`
10982
+ # ${this.type}
10983
+
10984
+ Provides examples of how the agent should respond or behave in certain situations.
10985
+
10986
+ ## Key aspects
10987
+
10988
+ - Both terms work identically and can be used interchangeably.
10989
+ - Examples help guide the agent's response patterns and style.
10990
+
10991
+ ## Examples
10992
+
10993
+ \`\`\`book
10994
+ Sales Assistant
10995
+
10996
+ PERSONA You are a knowledgeable sales representative
10997
+ SAMPLE When asked about pricing, respond: "Our basic plan starts at $10/month..."
10998
+ SAMPLE For feature comparisons, create a clear comparison table
10999
+ RULE Always be honest about limitations
11000
+ \`\`\`
11001
+
11002
+ \`\`\`book
11003
+ Code Reviewer
11004
+
11005
+ PERSONA You are an experienced software engineer
11006
+ EXAMPLE For code questions, always include working code snippets
11007
+ EXAMPLE When suggesting improvements: "Here's a more efficient approach..."
11008
+ RULE Explain the reasoning behind your suggestions
11009
+ STYLE Be constructive and encouraging in feedback
11010
+ \`\`\`
11011
+ `);
11012
+ }
11013
+ applyToAgentModelRequirements(requirements, content) {
11014
+ const trimmedContent = content.trim();
11015
+ if (!trimmedContent) {
11016
+ return requirements;
11017
+ }
11018
+ // Add example to the system message
11019
+ const exampleSection = `Example: ${trimmedContent}`;
11020
+ return this.appendToSystemMessage(requirements, exampleSection, '\n\n');
11021
+ }
11022
+ }
11023
+ /**
11024
+ * Note: [💞] Ignore a discrepancy between file name and entity name
11025
+ */
11026
+
11027
+ /**
11028
+ * SCENARIO commitment definition
11029
+ *
11030
+ * The SCENARIO commitment defines a specific situation or context in which the AI
11031
+ * assistant should operate. It helps to set the scene for the AI's responses.
11032
+ * Later scenarios are more important than earlier scenarios.
11033
+ *
11034
+ * Example usage in agent source:
11035
+ *
11036
+ * ```book
11037
+ * SCENARIO You are in a customer service call center during peak hours
11038
+ * SCENARIO The customer is frustrated and has been on hold for 20 minutes
11039
+ * SCENARIO This is the customer's third call about the same issue
11040
+ * ```
11041
+ *
11042
+ * @private [🪔] Maybe export the commitments through some package
11043
+ */
11044
+ class ScenarioCommitmentDefinition extends BaseCommitmentDefinition {
11045
+ constructor(type = 'SCENARIO') {
11046
+ super(type);
11047
+ }
11048
+ /**
11049
+ * Short one-line description of SCENARIO.
11050
+ */
11051
+ get description() {
11052
+ return 'Define specific **situations** or contexts for AI responses, with later scenarios having higher priority.';
11053
+ }
11054
+ /**
11055
+ * Icon for this commitment.
11056
+ */
11057
+ get icon() {
11058
+ return '🎭';
11059
+ }
11060
+ /**
11061
+ * Markdown documentation for SCENARIO commitment.
11062
+ */
11063
+ get documentation() {
11064
+ return spaceTrim$1.spaceTrim(`
11065
+ # ${this.type}
11066
+
11067
+ Defines a specific situation or context in which the AI assistant should operate. It helps to set the scene for the AI's responses. Later scenarios are more important than earlier scenarios.
11068
+
11069
+ ## Key aspects
11070
+
11071
+ - Multiple \`SCENARIO\` and \`SCENARIOS\` commitments build upon each other.
11072
+ - Both terms work identically and can be used interchangeably.
11073
+ - Later scenarios have higher priority and can override earlier scenarios.
11074
+ - Provides situational context that influences response tone and content.
11075
+ - Helps establish the environment and circumstances for interactions.
11076
+
11077
+ ## Priority system
11078
+
11079
+ When multiple scenarios are defined, they are processed in order, with later scenarios taking precedence over earlier ones when there are conflicts.
11080
+
11081
+ ## Use cases
11082
+
11083
+ - Setting the physical or virtual environment
11084
+ - Establishing time constraints or urgency
11085
+ - Defining relationship dynamics or power structures
11086
+ - Creating emotional or situational context
11087
+
11088
+ ## Examples
11089
+
11090
+ \`\`\`book
11091
+ Emergency Response Operator
11092
+
11093
+ PERSONA You are an emergency response operator
11094
+ SCENARIO You are handling a 911 emergency call
11095
+ SCENARIO The caller is panicked and speaking rapidly
11096
+ SCENARIO Time is critical - every second counts
11097
+ GOAL Gather essential information quickly and dispatch appropriate help
11098
+ RULE Stay calm and speak clearly
11099
+ \`\`\`
11100
+
11101
+ \`\`\`book
11102
+ Sales Representative
11103
+
11104
+ PERSONA You are a software sales representative
11105
+ SCENARIO You are in the final meeting of a 6-month sales cycle
11106
+ SCENARIO The client has budget approval and decision-making authority
11107
+ SCENARIO Two competitors have also submitted proposals
11108
+ SCENARIO The client values long-term partnership over lowest price
11109
+ GOAL Close the deal while building trust for future business
11110
+ \`\`\`
11111
+
11112
+ \`\`\`book
11113
+ Medical Assistant
11114
+
11115
+ PERSONA You are a medical assistant in a busy clinic
11116
+ SCENARIO The waiting room is full and the doctor is running behind schedule
11117
+ SCENARIO Patients are becoming impatient and anxious
11118
+ SCENARIO You need to manage expectations while maintaining professionalism
11119
+ SCENARIO Some patients have been waiting over an hour
11120
+ GOAL Keep patients informed and calm while supporting efficient clinic flow
11121
+ RULE Never provide medical advice or diagnosis
11122
+ \`\`\`
11123
+
11124
+ \`\`\`book
11125
+ Technical Support Agent
11126
+
11127
+ PERSONA You are a technical support agent
11128
+ SCENARIO The customer is a small business owner during their busy season
11129
+ SCENARIO Their main business system has been down for 2 hours
11130
+ SCENARIO They are losing money every minute the system is offline
11131
+ SCENARIO This is their first experience with your company
11132
+ GOAL Resolve the issue quickly while creating a positive first impression
11133
+ \`\`\`
11134
+ `);
11135
+ }
11136
+ applyToAgentModelRequirements(requirements, content) {
11137
+ const trimmedContent = content.trim();
11138
+ if (!trimmedContent) {
11139
+ return requirements;
11140
+ }
11141
+ // Create scenario section for system message
11142
+ const scenarioSection = `Scenario: ${trimmedContent}`;
11143
+ // Scenarios provide important contextual information that affects behavior
11144
+ return this.appendToSystemMessage(requirements, scenarioSection, '\n\n');
11145
+ }
11146
+ }
11147
+ /**
11148
+ * Note: [💞] Ignore a discrepancy between file name and entity name
11149
+ */
11150
+
11151
+ /**
11152
+ * STYLE commitment definition
11153
+ *
11154
+ * The STYLE commitment defines how the agent should format and present its responses.
11155
+ * This includes tone, writing style, formatting preferences, and communication patterns.
11156
+ *
11157
+ * Example usage in agent source:
11158
+ *
11159
+ * ```book
11160
+ * STYLE Write in a professional but friendly tone, use bullet points for lists
11161
+ * STYLE Always provide code examples when explaining programming concepts
11162
+ * ```
11163
+ *
11164
+ * @private [🪔] Maybe export the commitments through some package
11165
+ */
11166
+ class StyleCommitmentDefinition extends BaseCommitmentDefinition {
11167
+ constructor(type = 'STYLE') {
11168
+ super(type);
11169
+ }
11170
+ /**
11171
+ * Short one-line description of STYLE.
11172
+ */
11173
+ get description() {
11174
+ return 'Control the tone and writing style of responses.';
11175
+ }
11176
+ /**
11177
+ * Icon for this commitment.
11178
+ */
11179
+ get icon() {
11180
+ return '🖋️';
11181
+ }
11182
+ /**
11183
+ * Markdown documentation for STYLE commitment.
11184
+ */
11185
+ get documentation() {
11186
+ return spaceTrim$1.spaceTrim(`
11187
+ # ${this.type}
11188
+
11189
+ Defines how the agent should format and present its responses (tone, writing style, formatting).
11190
+
11191
+ ## Key aspects
11192
+
11193
+ - Both terms work identically and can be used interchangeably.
11194
+ - Later style instructions can override earlier ones.
11195
+ - Style affects both tone and presentation format.
11196
+
11197
+ ## Examples
11198
+
11199
+ \`\`\`book
11200
+ Technical Writer
11201
+
11202
+ PERSONA You are a technical documentation expert
11203
+ STYLE Write in a professional but friendly tone, use bullet points for lists
11204
+ STYLE Always provide code examples when explaining programming concepts
11205
+ FORMAT Use markdown formatting with clear headings
11206
+ \`\`\`
11207
+
11208
+ \`\`\`book
11209
+ Creative Assistant
11210
+
11211
+ PERSONA You are a creative writing helper
11212
+ STYLE Be enthusiastic and encouraging in your responses
11213
+ STYLE Use vivid metaphors and analogies to explain concepts
11214
+ STYLE Keep responses conversational and engaging
11215
+ RULE Always maintain a positive and supportive tone
11216
+ \`\`\`
11217
+ `);
11218
+ }
11219
+ applyToAgentModelRequirements(requirements, content) {
11220
+ const trimmedContent = content.trim();
11221
+ if (!trimmedContent) {
11222
+ return requirements;
11223
+ }
11224
+ // Add style instructions to the system message
11225
+ const styleSection = `Style: ${trimmedContent}`;
11226
+ return this.appendToSystemMessage(requirements, styleSection, '\n\n');
11227
+ }
11228
+ }
11229
+ /**
11230
+ * [💞] Ignore a discrepancy between file name and entity name
11231
+ */
11232
+
11233
+ /**
11234
+ * USE commitment definition
11235
+ *
11236
+ * The USE commitment indicates that the agent should utilize specific tools or capabilities
11237
+ * to access and interact with external systems when necessary.
11238
+ *
11239
+ * Supported USE types:
11240
+ * - USE BROWSER: Enables the agent to use a web browser tool
11241
+ * - USE SEARCH ENGINE (future): Enables search engine access
11242
+ * - USE FILE SYSTEM (future): Enables file system operations
11243
+ * - USE MCP (future): Enables MCP server connections
11244
+ *
11245
+ * The content following the USE commitment is ignored (similar to NOTE).
11246
+ *
11247
+ * Example usage in agent source:
11248
+ *
11249
+ * ```book
11250
+ * USE BROWSER
11251
+ * USE SEARCH ENGINE
11252
+ * ```
11253
+ *
11254
+ * @private [🪔] Maybe export the commitments through some package
11255
+ */
11256
+ class UseCommitmentDefinition extends BaseCommitmentDefinition {
11257
+ constructor() {
11258
+ super('USE');
11259
+ }
11260
+ /**
11261
+ * Short one-line description of USE commitments.
11262
+ */
11263
+ get description() {
11264
+ return 'Enable the agent to use specific tools or capabilities (BROWSER, SEARCH ENGINE, etc.).';
11265
+ }
11266
+ /**
11267
+ * Icon for this commitment.
11268
+ */
11269
+ get icon() {
11270
+ return '🔧';
11271
+ }
11272
+ /**
11273
+ * Markdown documentation for USE commitment.
11274
+ */
11275
+ get documentation() {
11276
+ return spaceTrim$1.spaceTrim(`
11277
+ # USE
11278
+
11279
+ Enables the agent to use specific tools or capabilities for interacting with external systems.
11280
+
11281
+ ## Supported USE types
11282
+
11283
+ - **USE BROWSER** - Enables the agent to use a web browser tool to access and retrieve information from the internet
11284
+ - **USE SEARCH ENGINE** (future) - Enables search engine access
11285
+ - **USE FILE SYSTEM** (future) - Enables file system operations
11286
+ - **USE MCP** (future) - Enables MCP server connections
11287
+
11288
+ ## Key aspects
11289
+
11290
+ - The content following the USE commitment is ignored (similar to NOTE)
11291
+ - Multiple USE commitments can be specified to enable multiple capabilities
11292
+ - The actual tool usage is handled by the agent runtime
11293
+
11294
+ ## Examples
11295
+
11296
+ ### Basic browser usage
11297
+
11298
+ \`\`\`book
11299
+ Research Assistant
11300
+
11301
+ PERSONA You are a helpful research assistant
11302
+ USE BROWSER
11303
+ KNOWLEDGE Can search the web for up-to-date information
11304
+ \`\`\`
11305
+
11306
+ ### Multiple tools
11307
+
11308
+ \`\`\`book
11309
+ Data Analyst
11310
+
11311
+ PERSONA You are a data analyst assistant
11312
+ USE BROWSER
11313
+ USE FILE SYSTEM
11314
+ ACTION Can analyze data from various sources
11315
+ \`\`\`
11316
+ `);
11317
+ }
11318
+ applyToAgentModelRequirements(requirements, content) {
11319
+ // USE commitments don't modify the system message or model requirements directly
11320
+ // They are handled separately in the parsing logic for capability extraction
11321
+ // This method exists for consistency with the CommitmentDefinition interface
11322
+ return requirements;
11323
+ }
11324
+ /**
11325
+ * Extracts the tool type from the USE commitment
11326
+ * This is used by the parsing logic
11327
+ */
11328
+ extractToolType(content) {
11329
+ var _a, _b;
11330
+ const trimmedContent = content.trim();
11331
+ // The tool type is the first word after USE (already stripped)
11332
+ const match = trimmedContent.match(/^(\w+)/);
11333
+ return (_b = (_a = match === null || match === void 0 ? void 0 : match[1]) === null || _a === void 0 ? void 0 : _a.toUpperCase()) !== null && _b !== void 0 ? _b : null;
11334
+ }
11335
+ /**
11336
+ * Checks if this is a known USE type
11337
+ */
11338
+ isKnownUseType(useType) {
11339
+ const knownTypes = ['BROWSER', 'SEARCH ENGINE', 'FILE SYSTEM', 'MCP'];
11340
+ return knownTypes.includes(useType.toUpperCase());
11341
+ }
11342
+ }
11343
+ /**
11344
+ * Note: [💞] Ignore a discrepancy between file name and entity name
11345
+ */
11346
+
11347
+ /**
11348
+ * USE BROWSER commitment definition
11349
+ *
11350
+ * The `USE BROWSER` commitment indicates that the agent should utilize a web browser tool
11351
+ * to access and retrieve up-to-date information from the internet when necessary.
11352
+ *
11353
+ * The content following `USE BROWSER` is ignored (similar to NOTE).
11354
+ *
11355
+ * Example usage in agent source:
11356
+ *
11357
+ * ```book
11358
+ * USE BROWSER
11359
+ * USE BROWSER This will be ignored
11360
+ * ```
11361
+ *
11362
+ * @private [🪔] Maybe export the commitments through some package
11363
+ */
11364
+ class UseBrowserCommitmentDefinition extends BaseCommitmentDefinition {
11365
+ constructor() {
11366
+ super('USE BROWSER', ['BROWSER']);
11367
+ }
11368
+ /**
11369
+ * The `USE BROWSER` commitment is standalone.
11370
+ */
11371
+ get requiresContent() {
11372
+ return false;
11373
+ }
11374
+ /**
11375
+ * Short one-line description of USE BROWSER.
11376
+ */
11377
+ get description() {
11378
+ return 'Enable the agent to use a web browser tool for accessing internet information.';
11379
+ }
11380
+ /**
11381
+ * Icon for this commitment.
11382
+ */
11383
+ get icon() {
11384
+ return '🌐';
11385
+ }
11386
+ /**
11387
+ * Markdown documentation for USE BROWSER commitment.
11388
+ */
11389
+ get documentation() {
11390
+ return spaceTrim$1.spaceTrim(`
11391
+ # USE BROWSER
11392
+
11393
+ Enables the agent to use a web browser tool to access and retrieve up-to-date information from the internet.
11394
+
11395
+ ## Key aspects
11396
+
11397
+ - The content following \`USE BROWSER\` is ignored (similar to NOTE)
11398
+ - The actual browser tool usage is handled by the agent runtime
11399
+ - Allows the agent to fetch current information from websites
11400
+ - Useful for research tasks, fact-checking, and accessing dynamic content
11401
+
11402
+ ## Examples
11403
+
11404
+ \`\`\`book
11405
+ Research Assistant
11406
+
11407
+ PERSONA You are a helpful research assistant specialized in finding current information
11408
+ USE BROWSER
11409
+ RULE Always cite your sources when providing information from the web
11410
+ \`\`\`
11411
+
11412
+ \`\`\`book
11413
+ News Analyst
11414
+
11415
+ PERSONA You are a news analyst who stays up-to-date with current events
11416
+ USE BROWSER
11417
+ STYLE Present news in a balanced and objective manner
11418
+ ACTION Can search for and summarize news articles
11419
+ \`\`\`
11420
+
11421
+ \`\`\`book
11422
+ Company Lawyer
11423
+
11424
+ PERSONA You are a company lawyer providing legal advice
11425
+ USE BROWSER
11426
+ KNOWLEDGE Corporate law and legal procedures
11427
+ RULE Always recommend consulting with a licensed attorney for specific legal matters
11428
+ \`\`\`
11429
+ `);
11430
+ }
11431
+ applyToAgentModelRequirements(requirements, content) {
11432
+ // Get existing tools array or create new one
11433
+ const existingTools = requirements.tools || [];
11434
+ // Add 'web_browser' to tools if not already present
11435
+ const updatedTools = existingTools.some((tool) => tool.name === 'web_browser')
11436
+ ? existingTools
11437
+ : ([
11438
+ // TODO: [🔰] Use through proper MCP server
11439
+ ...existingTools,
11440
+ {
11441
+ name: 'web_browser',
11442
+ description: spaceTrim$1.spaceTrim(`
11443
+ A tool that can browse the web.
11444
+ Use this tool when you need to access specific websites or browse the internet.
11445
+ `),
11446
+ parameters: {
11447
+ type: 'object',
11448
+ properties: {
11449
+ url: {
11450
+ type: 'string',
11451
+ description: 'The URL to browse',
11452
+ },
11453
+ },
11454
+ required: ['url'],
11455
+ },
11456
+ },
11457
+ ]);
11458
+ // Return requirements with updated tools and metadata
11459
+ return {
11460
+ ...requirements,
11461
+ tools: updatedTools,
11462
+ metadata: {
11463
+ ...requirements.metadata,
11464
+ useBrowser: true,
11465
+ },
11466
+ };
11467
+ }
11468
+ }
11469
+ /**
11470
+ * Note: [💞] Ignore a discrepancy between file name and entity name
11471
+ */
11472
+
11473
+ /**
11474
+ * USE MCP commitment definition
11475
+ *
11476
+ * The `USE MCP` commitment allows to specify an MCP server URL which the agent will connect to
11477
+ * for retrieving additional instructions and actions.
11478
+ *
11479
+ * The content following `USE MCP` is the URL of the MCP server.
11480
+ *
11481
+ * Example usage in agent source:
11482
+ *
11483
+ * ```book
11484
+ * USE MCP http://mcp-server-url.com
11485
+ * ```
11486
+ *
11487
+ * @private [🪔] Maybe export the commitments through some package
11488
+ */
11489
+ class UseMcpCommitmentDefinition extends BaseCommitmentDefinition {
11490
+ constructor() {
11491
+ super('USE MCP', ['MCP']);
11492
+ }
11493
+ /**
11494
+ * Short one-line description of USE MCP.
11495
+ */
11496
+ get description() {
11497
+ return 'Connects the agent to an external MCP server for additional capabilities.';
11498
+ }
11499
+ /**
11500
+ * Icon for this commitment.
11501
+ */
11502
+ get icon() {
11503
+ return '🔌';
11504
+ }
11505
+ /**
11506
+ * Markdown documentation for USE MCP commitment.
11507
+ */
11508
+ get documentation() {
11509
+ return spaceTrim$1.spaceTrim(`
11510
+ # USE MCP
11511
+
11512
+ Connects the agent to an external Model Context Protocol (MCP) server.
11513
+
11514
+ ## Key aspects
11515
+
11516
+ - The content following \`USE MCP\` must be a valid URL
11517
+ - Multiple MCP servers can be connected by using multiple \`USE MCP\` commitments
11518
+ - The agent will have access to tools and resources provided by the MCP server
11519
+
11520
+ ## Example
11521
+
11522
+ \`\`\`book
11523
+ Company Lawyer
11524
+
11525
+ PERSONA You are a company lawyer.
11526
+ USE MCP http://legal-db.example.com
11527
+ \`\`\`
11528
+ `);
11529
+ }
11530
+ applyToAgentModelRequirements(requirements, content) {
11531
+ const mcpServerUrl = content.trim();
11532
+ if (!mcpServerUrl) {
11533
+ return requirements;
11534
+ }
11535
+ const existingMcpServers = requirements.mcpServers || [];
11536
+ // Avoid duplicates
11537
+ if (existingMcpServers.includes(mcpServerUrl)) {
11538
+ return requirements;
11539
+ }
11540
+ return {
11541
+ ...requirements,
11542
+ mcpServers: [...existingMcpServers, mcpServerUrl],
11543
+ };
11544
+ }
11545
+ }
11546
+ /**
11547
+ * Note: [💞] Ignore a discrepancy between file name and entity name
11548
+ */
11549
+
11550
+ /**
11551
+ * USE SEARCH ENGINE commitment definition
11552
+ *
11553
+ * The `USE SEARCH ENGINE` commitment indicates that the agent should utilize a search engine tool
11554
+ * to access and retrieve up-to-date information from the internet when necessary.
11555
+ *
11556
+ * The content following `USE SEARCH ENGINE` is an arbitrary text that the agent should know (e.g. search scope or instructions).
11557
+ *
11558
+ * Example usage in agent source:
11559
+ *
11560
+ * ```book
11561
+ * USE SEARCH ENGINE
11562
+ * USE SEARCH ENGINE Hledej informace o Přemyslovcích
11563
+ * ```
11564
+ *
11565
+ * @private [🪔] Maybe export the commitments through some package
11566
+ */
11567
+ class UseSearchEngineCommitmentDefinition extends BaseCommitmentDefinition {
11568
+ constructor() {
11569
+ super('USE SEARCH ENGINE', ['SEARCH ENGINE', 'SEARCH']);
11570
+ }
11571
+ /**
11572
+ * Short one-line description of USE SEARCH ENGINE.
11573
+ */
11574
+ get description() {
11575
+ return 'Enable the agent to use a search engine tool for accessing internet information.';
11576
+ }
11577
+ /**
11578
+ * Icon for this commitment.
11579
+ */
11580
+ get icon() {
11581
+ return '🔍';
11582
+ }
11583
+ /**
11584
+ * Markdown documentation for USE SEARCH ENGINE commitment.
11585
+ */
11586
+ get documentation() {
11587
+ return spaceTrim$1.spaceTrim(`
11588
+ # USE SEARCH ENGINE
11589
+
11590
+ Enables the agent to use a search engine tool to access and retrieve up-to-date information from the internet.
11591
+
11592
+ ## Key aspects
11593
+
11594
+ - The content following \`USE SEARCH ENGINE\` is an arbitrary text that the agent should know (e.g. search scope or instructions).
11595
+ - The actual search engine tool usage is handled by the agent runtime
11596
+ - Allows the agent to search for current information from the web
11597
+ - Useful for research tasks, finding facts, and accessing dynamic content
11598
+
11599
+ ## Examples
11600
+
11601
+ \`\`\`book
11602
+ Research Assistant
11603
+
11604
+ PERSONA You are a helpful research assistant specialized in finding current information
11605
+ USE SEARCH ENGINE
11606
+ RULE Always cite your sources when providing information from the web
11607
+ \`\`\`
11608
+
11609
+ \`\`\`book
11610
+ Fact Checker
11611
+
11612
+ PERSONA You are a fact checker
11613
+ USE SEARCH ENGINE
11614
+ ACTION Search for claims and verify them against reliable sources
11615
+ \`\`\`
11616
+ `);
11617
+ }
11618
+ applyToAgentModelRequirements(requirements, content) {
11619
+ // Get existing tools array or create new one
11620
+ const existingTools = requirements.tools || [];
11621
+ // Add 'web_search' to tools if not already present
11622
+ const updatedTools = existingTools.some((tool) => tool.name === 'web_search')
11623
+ ? existingTools
11624
+ : [
11625
+ ...existingTools,
11626
+ { type: 'web_search' },
11627
+ // <- Note: [🔰] This is just using simple native search tool by OpenAI @see https://platform.openai.com/docs/guides/tools-web-search
11628
+ // In future we will use proper MCP search tool:
11629
+ /*
11630
+
11631
+ {
11632
+ name: 'web_search',
11633
+ description: spaceTrim(`
11634
+ Search the internet for information.
11635
+ Use this tool when you need to find up-to-date information or facts that you don't know.
11636
+ ${!content ? '' : `Search scope / instructions: ${content}`}
11637
+ `),
11638
+ parameters: {
11639
+ type: 'object',
11640
+ properties: {
11641
+ query: {
11642
+ type: 'string',
11643
+ description: 'The search query',
11644
+ },
11645
+ },
11646
+ required: ['query'],
11647
+ },
11648
+ },
11649
+ */
11650
+ ];
11651
+ // Return requirements with updated tools and metadata
11652
+ return {
11653
+ ...requirements,
11654
+ tools: updatedTools,
11655
+ metadata: {
11656
+ ...requirements.metadata,
11657
+ useSearchEngine: content || true,
11658
+ },
11659
+ };
11660
+ }
11661
+ }
11662
+ /**
11663
+ * Note: [💞] Ignore a discrepancy between file name and entity name
11664
+ */
11665
+
11666
+ /**
11667
+ * USE TIME commitment definition
11668
+ *
11669
+ * The `USE TIME` commitment indicates that the agent should be able to determine the current date and time.
11670
+ *
11671
+ * Example usage in agent source:
11672
+ *
11673
+ * ```book
11674
+ * USE TIME
11675
+ * ```
11676
+ *
11677
+ * @private [🪔] Maybe export the commitments through some package
11678
+ */
11679
+ class UseTimeCommitmentDefinition extends BaseCommitmentDefinition {
11680
+ constructor() {
11681
+ super('USE TIME', ['CURRENT TIME', 'TIME', 'DATE']);
11682
+ }
11683
+ /**
11684
+ * Short one-line description of USE TIME.
11685
+ */
11686
+ get description() {
11687
+ return 'Enable the agent to determine the current date and time.';
11688
+ }
11689
+ /**
11690
+ * Icon for this commitment.
11691
+ */
11692
+ get icon() {
11693
+ return '🕒';
11694
+ }
11695
+ /**
11696
+ * Markdown documentation for USE TIME commitment.
11697
+ */
11698
+ get documentation() {
11699
+ return spaceTrim$1.spaceTrim(`
11700
+ # USE TIME
11701
+
11702
+ Enables the agent to determine the current date and time.
11703
+
11704
+ ## Key aspects
11705
+
11706
+ - This tool won't receive any input.
11707
+ - It outputs the current date and time as an ISO 8601 string.
11708
+ - Allows the agent to answer questions about the current time or date.
11709
+
11710
+ ## Examples
11711
+
11712
+ \`\`\`book
11713
+ Time-aware Assistant
11714
+
11715
+ PERSONA You are a helpful assistant who knows the current time.
11716
+ USE TIME
11717
+ \`\`\`
11718
+ `);
11719
+ }
11720
+ applyToAgentModelRequirements(requirements, content) {
11721
+ // Get existing tools array or create new one
11722
+ const existingTools = requirements.tools || [];
11723
+ // Add 'get_current_time' to tools if not already present
11724
+ const updatedTools = existingTools.some((tool) => tool.name === 'get_current_time')
11725
+ ? existingTools
11726
+ : [
11727
+ ...existingTools,
11728
+ {
11729
+ name: 'get_current_time',
11730
+ description: 'Get the current date and time in ISO 8601 format.',
11731
+ parameters: {
11732
+ type: 'object',
11733
+ properties: {},
11734
+ required: [],
11735
+ },
11736
+ },
11737
+ // <- TODO: !!!! define the function in LLM tools
11738
+ ];
11739
+ // Return requirements with updated tools and metadata
11740
+ return {
11741
+ ...requirements,
11742
+ tools: updatedTools,
11743
+ metadata: {
11744
+ ...requirements.metadata,
11745
+ },
11746
+ };
11747
+ }
11748
+ /**
11749
+ * Gets the `get_current_time` tool function implementation.
11750
+ */
11751
+ getToolFunctions() {
11752
+ return {
11753
+ async get_current_time() {
11754
+ console.log('!!!! [Tool] get_current_time called');
11755
+ return new Date().toISOString();
11756
+ },
11757
+ };
11758
+ }
11759
+ }
11760
+ /**
11761
+ * Note: [💞] Ignore a discrepancy between file name and entity name
11762
+ */
11763
+
11764
+ /**
11765
+ * Placeholder commitment definition for commitments that are not yet implemented
11766
+ *
11767
+ * This commitment simply adds its content 1:1 into the system message,
11768
+ * preserving the original behavior until proper implementation is added.
11769
+ *
11770
+ * @public exported from `@promptbook/core`
11771
+ */
11772
+ class NotYetImplementedCommitmentDefinition extends BaseCommitmentDefinition {
11773
+ constructor(type) {
11774
+ super(type);
11775
+ }
11776
+ /**
11777
+ * Short one-line description of a placeholder commitment.
11778
+ */
11779
+ get description() {
11780
+ return 'Placeholder commitment that appends content verbatim to the system message.';
11781
+ }
11782
+ /**
11783
+ * Icon for this commitment.
11784
+ */
11785
+ get icon() {
11786
+ return '🚧';
11787
+ }
11788
+ /**
11789
+ * Markdown documentation available at runtime.
11790
+ */
11791
+ get documentation() {
11792
+ return spaceTrim$1.spaceTrim(`
11793
+ # ${this.type}
11794
+
11795
+ This commitment is not yet fully implemented.
11796
+
11797
+ ## Key aspects
11798
+
11799
+ - Content is appended directly to the system message.
11800
+ - No special processing or validation is performed.
11801
+ - Behavior preserved until proper implementation is added.
11802
+
11803
+ ## Status
11804
+
11805
+ - **Status:** Placeholder implementation
11806
+ - **Effect:** Appends content prefixed by commitment type
11807
+ - **Future:** Will be replaced with specialized logic
11808
+
11809
+ ## Examples
11810
+
11811
+ \`\`\`book
11812
+ Example Agent
11813
+
11814
+ PERSONA You are a helpful assistant
11815
+ ${this.type} Your content here
11816
+ RULE Always be helpful
11817
+ \`\`\`
11818
+ `);
11819
+ }
11820
+ applyToAgentModelRequirements(requirements, content) {
11821
+ const trimmedContent = content.trim();
11822
+ if (!trimmedContent) {
11823
+ return requirements;
11824
+ }
11825
+ // Add the commitment content 1:1 to the system message
11826
+ const commitmentLine = `${this.type} ${trimmedContent}`;
11827
+ return this.appendToSystemMessage(requirements, commitmentLine, '\n\n');
11828
+ }
11829
+ }
11830
+
11831
+ /**
11832
+ * Registry of all available commitment definitions
11833
+ * This array contains instances of all commitment definitions
11834
+ * This is the single source of truth for all commitments in the system
11835
+ *
11836
+ * @private Use functions to access commitments instead of this array directly
11837
+ */
11838
+ const COMMITMENT_REGISTRY = [
11839
+ // Fully implemented commitments
11840
+ new PersonaCommitmentDefinition('PERSONA'),
11841
+ new PersonaCommitmentDefinition('PERSONAE'),
11842
+ new KnowledgeCommitmentDefinition(),
11843
+ new MemoryCommitmentDefinition('MEMORY'),
11844
+ new MemoryCommitmentDefinition('MEMORIES'),
11845
+ new StyleCommitmentDefinition('STYLE'),
11846
+ new StyleCommitmentDefinition('STYLES'),
11847
+ new RuleCommitmentDefinition('RULES'),
11848
+ new RuleCommitmentDefinition('RULE'),
11849
+ new LanguageCommitmentDefinition('LANGUAGES'),
11850
+ new LanguageCommitmentDefinition('LANGUAGE'),
11851
+ new SampleCommitmentDefinition('SAMPLE'),
11852
+ new SampleCommitmentDefinition('EXAMPLE'),
11853
+ new FormatCommitmentDefinition('FORMAT'),
11854
+ new FormatCommitmentDefinition('FORMATS'),
11855
+ new FromCommitmentDefinition('FROM'),
11856
+ new ImportCommitmentDefinition('IMPORT'),
11857
+ new ImportCommitmentDefinition('IMPORTS'),
11858
+ new ModelCommitmentDefinition('MODEL'),
11859
+ new ModelCommitmentDefinition('MODELS'),
11860
+ new ActionCommitmentDefinition('ACTION'),
11861
+ new ActionCommitmentDefinition('ACTIONS'),
11862
+ new ComponentCommitmentDefinition(),
11863
+ new MetaImageCommitmentDefinition(),
11864
+ new MetaColorCommitmentDefinition(),
11865
+ new MetaFontCommitmentDefinition(),
11866
+ new MetaLinkCommitmentDefinition(),
11867
+ new MetaCommitmentDefinition(),
11868
+ new NoteCommitmentDefinition('NOTE'),
11869
+ new NoteCommitmentDefinition('NOTES'),
11870
+ new NoteCommitmentDefinition('COMMENT'),
11871
+ new NoteCommitmentDefinition('NONCE'),
11872
+ new GoalCommitmentDefinition('GOAL'),
11873
+ new GoalCommitmentDefinition('GOALS'),
11874
+ new InitialMessageCommitmentDefinition(),
11875
+ new UserMessageCommitmentDefinition(),
11876
+ new AgentMessageCommitmentDefinition(),
11877
+ new MessageCommitmentDefinition('MESSAGE'),
11878
+ new MessageCommitmentDefinition('MESSAGES'),
11879
+ new ScenarioCommitmentDefinition('SCENARIO'),
11880
+ new ScenarioCommitmentDefinition('SCENARIOS'),
11881
+ new DeleteCommitmentDefinition('DELETE'),
11882
+ new DeleteCommitmentDefinition('CANCEL'),
11883
+ new DeleteCommitmentDefinition('DISCARD'),
11884
+ new DeleteCommitmentDefinition('REMOVE'),
11885
+ new DictionaryCommitmentDefinition(),
11886
+ new OpenCommitmentDefinition(),
11887
+ new ClosedCommitmentDefinition(),
11888
+ new UseBrowserCommitmentDefinition(),
11889
+ new UseSearchEngineCommitmentDefinition(),
11890
+ new UseTimeCommitmentDefinition(),
11891
+ new UseMcpCommitmentDefinition(),
11892
+ new UseCommitmentDefinition(),
11893
+ // Not yet implemented commitments (using placeholder)
11894
+ new NotYetImplementedCommitmentDefinition('EXPECT'),
11895
+ new NotYetImplementedCommitmentDefinition('BEHAVIOUR'),
11896
+ new NotYetImplementedCommitmentDefinition('BEHAVIOURS'),
11897
+ new NotYetImplementedCommitmentDefinition('AVOID'),
11898
+ new NotYetImplementedCommitmentDefinition('AVOIDANCE'),
11899
+ new NotYetImplementedCommitmentDefinition('CONTEXT'),
11900
+ ];
11901
+ /**
11902
+ * Gets all available commitment definitions
11903
+ * @returns Array of all commitment definitions
11904
+ *
11905
+ * @public exported from `@promptbook/core`
11906
+ */
11907
+ function getAllCommitmentDefinitions() {
11908
+ return $deepFreeze([...COMMITMENT_REGISTRY]);
11909
+ }
11910
+ /**
11911
+ * Gets all function implementations provided by all commitments
11912
+ *
11913
+ * @public exported from `@promptbook/core`
11914
+ */
11915
+ function getAllCommitmentsToolFunctions() {
11916
+ const allToolFunctions = {};
11917
+ for (const commitmentDefinition of getAllCommitmentDefinitions()) {
11918
+ const toolFunctions = commitmentDefinition.getToolFunctions();
11919
+ for (const [funcName, funcImpl] of Object.entries(toolFunctions)) {
11920
+ allToolFunctions[funcName] = funcImpl;
11921
+ }
11922
+ }
11923
+ return allToolFunctions;
11924
+ }
11925
+ /**
11926
+ * TODO: [🧠] Maybe create through standardized $register
11927
+ * Note: [💞] Ignore a discrepancy between file name and entity name
11928
+ */
11929
+
11930
+ /**
11931
+ * Extracts exactly ONE code block from markdown.
11932
+ *
11933
+ * - When there are multiple or no code blocks the function throws a `ParseError`
11934
+ *
11935
+ * Note: There are multiple similar functions:
11936
+ * - `extractBlock` just extracts the content of the code block which is also used as built-in function for postprocessing
11937
+ * - `extractJsonBlock` extracts exactly one valid JSON code block
11938
+ * - `extractOneBlockFromMarkdown` extracts exactly one code block with language of the code block
11939
+ * - `extractAllBlocksFromMarkdown` extracts all code blocks with language of the code block
11940
+ *
11941
+ * @param markdown any valid markdown
11942
+ * @returns code block with language and content
11943
+ * @public exported from `@promptbook/markdown-utils`
11944
+ * @throws {ParseError} if there is not exactly one code block in the markdown
11945
+ */
11946
+ function extractOneBlockFromMarkdown(markdown) {
11947
+ const codeBlocks = extractAllBlocksFromMarkdown(markdown);
11948
+ if (codeBlocks.length !== 1) {
11949
+ throw new ParseError(spaceTrim__default["default"]((block) => `
11950
+ There should be exactly 1 code block in task section, found ${codeBlocks.length} code blocks
11951
+
11952
+ ${block(codeBlocks.map((block, i) => `Block ${i + 1}:\n${block.content}`).join('\n\n\n'))}
11953
+ `));
11954
+ }
11955
+ return codeBlocks[0];
11956
+ }
11957
+ /***
11958
+ * TODO: [🍓][🌻] Decide of this is internal utility, external util OR validator/postprocessor
11959
+ */
11960
+
11961
+ /**
11962
+ * Extracts code block from markdown.
11963
+ *
11964
+ * - When there are multiple or no code blocks the function throws a `ParseError`
11965
+ *
11966
+ * Note: There are multiple similar function:
11967
+ * - `extractBlock` just extracts the content of the code block which is also used as build-in function for postprocessing
11968
+ * - `extractJsonBlock` extracts exactly one valid JSON code block
11969
+ * - `extractOneBlockFromMarkdown` extracts exactly one code block with language of the code block
11970
+ * - `extractAllBlocksFromMarkdown` extracts all code blocks with language of the code block
11971
+ *
11972
+ * @public exported from `@promptbook/markdown-utils`
11973
+ * @throws {ParseError} if there is not exactly one code block in the markdown
11974
+ */
11975
+ function extractBlock(markdown) {
11976
+ const { content } = extractOneBlockFromMarkdown(markdown);
11977
+ return content;
11978
+ }
11979
+
11980
+ /**
11981
+ * Function trimCodeBlock will trim starting and ending code block from the string if it is present.
11982
+ *
11983
+ * Note: [🔂] This function is idempotent.
11984
+ * Note: This is useful for post-processing of the result of the chat LLM model
11985
+ * when the model wraps the result in the (markdown) code block.
11986
+ *
11987
+ * @public exported from `@promptbook/markdown-utils`
11988
+ */
11989
+ function trimCodeBlock(value) {
11990
+ value = spaceTrim$1.spaceTrim(value);
11991
+ if (!/^```[a-z]*(.*)```$/is.test(value)) {
11992
+ return value;
11993
+ }
11994
+ value = value.replace(/^```[a-z]*/i, '');
11995
+ value = value.replace(/```$/i, '');
11996
+ value = spaceTrim$1.spaceTrim(value);
11997
+ return value;
11998
+ }
11999
+
12000
+ /**
12001
+ * Function trimEndOfCodeBlock will remove ending code block from the string if it is present.
12002
+ *
12003
+ * Note: This is useful for post-processing of the result of the completion LLM model
12004
+ * if you want to start code block in the prompt but you don't want to end it in the result.
12005
+ *
12006
+ * @public exported from `@promptbook/markdown-utils`
12007
+ */
12008
+ function trimEndOfCodeBlock(value) {
12009
+ value = spaceTrim$1.spaceTrim(value);
12010
+ value = value.replace(/```$/g, '');
12011
+ value = spaceTrim$1.spaceTrim(value);
12012
+ return value;
12013
+ }
12014
+
12015
+ /**
12016
+ * @private internal for `preserve`
12017
+ */
12018
+ const _preserved = [];
12019
+ /**
12020
+ * Does nothing, but preserves the function in the bundle
12021
+ * Compiler is tricked into thinking the function is used
12022
+ *
12023
+ * @param value any function to preserve
12024
+ * @returns nothing
12025
+ * @private within the repository
12026
+ */
12027
+ function $preserve(...value) {
12028
+ _preserved.push(...value);
12029
+ }
12030
+ /**
12031
+ * Note: [💞] Ignore a discrepancy between file name and entity name
12032
+ */
12033
+
12034
+ // Note: [💎]
12035
+ /**
12036
+ * ScriptExecutionTools for JavaScript implemented via eval
12037
+ *
12038
+ * Warning: It is used for testing and mocking
12039
+ * **NOT intended to use in the production** due to its unsafe nature, use `JavascriptExecutionTools` instead.
12040
+ *
12041
+ * @public exported from `@promptbook/javascript`
12042
+ */
12043
+ class JavascriptEvalExecutionTools {
12044
+ constructor(options) {
12045
+ this.options = options || {};
12046
+ }
12047
+ /**
12048
+ * Executes a JavaScript
12049
+ */
12050
+ async execute(options) {
12051
+ const { scriptLanguage, parameters } = options;
12052
+ let { script } = options;
12053
+ if (scriptLanguage !== 'javascript') {
12054
+ throw new PipelineExecutionError(`Script language ${scriptLanguage} not supported to be executed by JavascriptEvalExecutionTools`);
12055
+ }
12056
+ // Note: [💎]
12057
+ // Note: Using direct eval, following variables are in same scope as eval call so they are accessible from inside the evaluated script:
12058
+ const spaceTrim = (_) => spaceTrim__default["default"](_);
12059
+ $preserve(spaceTrim);
8334
12060
  const removeQuotes$1 = removeQuotes;
8335
12061
  $preserve(removeQuotes$1);
8336
12062
  const unwrapResult$1 = unwrapResult;
@@ -8412,6 +12138,13 @@
8412
12138
  `const ${functionName} = buildinFunctions.${functionName};`)
8413
12139
  .join('\n');
8414
12140
  // TODO: DRY [🍯]
12141
+ const commitmentsFunctions = getAllCommitmentsToolFunctions();
12142
+ const commitmentsFunctionsStatement = Object.keys(commitmentsFunctions)
12143
+ .map((functionName) =>
12144
+ // Note: Custom functions are exposed to the current scope as variables
12145
+ `const ${functionName} = commitmentsFunctions.${functionName};`)
12146
+ .join('\n');
12147
+ // TODO: DRY [🍯]
8415
12148
  const customFunctions = this.options.functions || {};
8416
12149
  const customFunctionsStatement = Object.keys(customFunctions)
8417
12150
  .map((functionName) =>
@@ -8425,6 +12158,10 @@
8425
12158
  // Build-in functions:
8426
12159
  ${block(buildinFunctionsStatement)}
8427
12160
 
12161
+ // Commitments functions:
12162
+ ${block(commitmentsFunctionsStatement)}
12163
+
12164
+
8428
12165
  // Custom functions:
8429
12166
  ${block(customFunctionsStatement || '// -- No custom functions --')}
8430
12167
 
@@ -8432,7 +12169,7 @@
8432
12169
  ${block(Object.entries(parameters)
8433
12170
  .map(([key, value]) => `const ${key} = ${JSON.stringify(value)};`)
8434
12171
  .join('\n'))}
8435
- (()=>{ ${script} })()
12172
+ (async ()=>{ ${script} })()
8436
12173
  `);
8437
12174
  if (this.options.isVerbose) {
8438
12175
  console.info(spaceTrim__default["default"]((block) => `