@promptbook/cli 0.61.0-16 → 0.61.0-18

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.
@@ -1,4 +1,5 @@
1
1
  import { createCollectionFromDirectory } from '../collection/constructors/createCollectionFromDirectory';
2
+ import { createLlmToolsFromEnv } from '../llm-providers/_common/createLlmToolsFromEnv';
2
3
  import { PROMPTBOOK_VERSION } from '../version';
3
4
  export { PROMPTBOOK_VERSION };
4
- export { createCollectionFromDirectory };
5
+ export { createCollectionFromDirectory, createLlmToolsFromEnv };
@@ -3,36 +3,36 @@ import type { Prompt } from '../types/Prompt';
3
3
  import type { string_pipeline_url } from '../types/typeAliases';
4
4
  import type { PipelineCollection } from './PipelineCollection';
5
5
  /**
6
- * Library of promptbooks that groups together promptbooks for an application.
7
- * This implementation is a very thin wrapper around the Array / Map of promptbooks.
6
+ * Library of pipelines that groups together pipelines for an application.
7
+ * This implementation is a very thin wrapper around the Array / Map of pipelines.
8
8
  *
9
9
  * @private use `createCollectionFromJson` instead
10
- * @see https://github.com/webgptorg/promptbook#promptbook-collection
10
+ * @see https://github.com/webgptorg/pipeline#pipeline-collection
11
11
  */
12
12
  export declare class SimplePipelineCollection implements PipelineCollection {
13
13
  private collection;
14
14
  /**
15
- * Constructs a pipeline collection from promptbooks
15
+ * Constructs a pipeline collection from pipelines
16
16
  *
17
- * @param promptbooks @@@
17
+ * @param pipelines @@@
18
18
  *
19
19
  * @private Use instead `createCollectionFromJson`
20
- * Note: During the construction logic of all promptbooks are validated
20
+ * Note: During the construction logic of all pipelines are validated
21
21
  * Note: It is not recommended to use this constructor directly, use `createCollectionFromJson` *(or other variant)* instead
22
22
  */
23
- constructor(...promptbooks: Array<PipelineJson>);
23
+ constructor(...pipelines: Array<PipelineJson>);
24
24
  /**
25
- * Gets all promptbooks in the collection
25
+ * Gets all pipelines in the collection
26
26
  */
27
27
  listPipelines(): Array<string_pipeline_url>;
28
28
  /**
29
- * Gets promptbook by its URL
29
+ * Gets pipeline by its URL
30
30
  *
31
31
  * Note: This is not a direct fetching from the URL, but a lookup in the collection
32
32
  */
33
33
  getPipelineByUrl(url: string_pipeline_url): PipelineJson;
34
34
  /**
35
- * Checks whether given prompt was defined in any promptbook in the collection
35
+ * Checks whether given prompt was defined in any pipeline in the collection
36
36
  */
37
37
  isResponsibleForPrompt(prompt: Prompt): boolean;
38
38
  }
@@ -6,7 +6,7 @@ import type { PipelineCollection } from '../PipelineCollection';
6
6
  */
7
7
  type CreatePipelineCollectionFromDirectoryOptions = PipelineStringToJsonOptions & {
8
8
  /**
9
- * If true, the directory is searched recursively for promptbooks
9
+ * If true, the directory is searched recursively for pipelines
10
10
  *
11
11
  * @default true
12
12
  */
@@ -24,25 +24,25 @@ type CreatePipelineCollectionFromDirectoryOptions = PipelineStringToJsonOptions
24
24
  */
25
25
  isLazyLoaded?: boolean;
26
26
  /**
27
- * If true, whole collection creation crashes on error in any promptbook
28
- * If true and isLazyLoaded is true, the error is thrown on first access to the promptbook
27
+ * If true, whole collection creation crashes on error in any pipeline
28
+ * If true and isLazyLoaded is true, the error is thrown on first access to the pipeline
29
29
  *
30
30
  * @default true
31
31
  */
32
32
  isCrashedOnError?: boolean;
33
33
  };
34
34
  /**
35
- * Constructs Promptbook from given directory
35
+ * Constructs Pipeline from given directory
36
36
  *
37
37
  * Note: Works only in Node.js environment because it reads the file system
38
38
  *
39
- * @param path - path to the directory with promptbooks
39
+ * @param path - path to the directory with pipelines
40
40
  * @param options - Misc options for the collection
41
41
  * @returns PipelineCollection
42
42
  */
43
43
  export declare function createCollectionFromDirectory(path: string_folder_path, options?: CreatePipelineCollectionFromDirectoryOptions): Promise<PipelineCollection>;
44
44
  export {};
45
45
  /**
46
- * TODO: !!!! [🧠] Library precompilation and do not mix markdown and json promptbooks
47
- * Note: [🟢] This code should never be published outside of `@promptbook/node`
46
+ * TODO: !!!! [🧠] Library precompilation and do not mix markdown and json pipelines
47
+ * Note: [🟢] This code should never be published outside of `@pipeline/node`
48
48
  */
@@ -4,6 +4,7 @@ import type { PipelineJson } from '../types/PipelineJson/PipelineJson';
4
4
  */
5
5
  export declare function isPipelinePrepared(pipeline: PipelineJson): boolean;
6
6
  /**
7
+ * TODO: [🐠] Maybe base this on `makeValidator`
7
8
  * TODO: [🔼] Export via core or utils
8
9
  * TODO: [🧊] Pipeline can be partially prepared, this should return true ONLY if fully prepared
9
10
  */
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@promptbook/cli",
3
- "version": "0.61.0-16",
3
+ "version": "0.61.0-18",
4
4
  "description": "Supercharge your use of large language models",
5
5
  "private": false,
6
6
  "sideEffects": false,
@@ -54,7 +54,7 @@
54
54
  }
55
55
  ],
56
56
  "peerDependencies": {
57
- "@promptbook/core": "0.61.0-16"
57
+ "@promptbook/core": "0.61.0-18"
58
58
  },
59
59
  "main": "./umd/index.umd.js",
60
60
  "module": "./esm/index.es.js",
package/umd/index.umd.js CHANGED
@@ -154,7 +154,7 @@
154
154
  /**
155
155
  * The version of the Promptbook library
156
156
  */
157
- var PROMPTBOOK_VERSION = '0.61.0-15';
157
+ var PROMPTBOOK_VERSION = '0.61.0-17';
158
158
  // TODO: !!!! List here all the versions and annotate + put into script
159
159
 
160
160
  /**
@@ -496,7 +496,7 @@
496
496
  });
497
497
  }
498
498
 
499
- var PipelineCollection = [{title:"Prepare Knowledge from Markdown",pipelineUrl:"https://promptbook.studio/promptbook/prepare-knowledge-from-markdown.ptbk.md",promptbookVersion:"0.61.0-15",parameters:[{name:"content",description:"Markdown document content",isInput:true,isOutput:false},{name:"knowledge",description:"The knowledge JSON object",isInput:false,isOutput:true}],promptTemplates:[{blockType:"PROMPT_TEMPLATE",name:"knowledge",title:"Knowledge",modelRequirements:{modelVariant:"CHAT",modelName:"claude-3-opus-20240229"},content:"You are experienced data researcher, extract the important knowledge from the document.\n\n# Rules\n\n- Make pieces of information concise, clear, and easy to understand\n- One piece of information should be approximately 1 paragraph\n- Divide the paragraphs by markdown horizontal lines ---\n- Omit irrelevant information\n- Group redundant information\n- Write just extracted information, nothing else\n\n# The document\n\nTake information from this document:\n\n> {content}",dependentParameterNames:["content"],resultingParameterName:"knowledge"}],knowledgeSources:[],knowledgePieces:[],personas:[],preparations:[{id:1,promptbookVersion:"0.61.0-15",modelUsage:{price:{value:0},input:{tokensCount:{value:0},charactersCount:{value:0},wordsCount:{value:0},sentencesCount:{value:0},linesCount:{value:0},paragraphsCount:{value:0},pagesCount:{value:0}},output:{tokensCount:{value:0},charactersCount:{value:0},wordsCount:{value:0},sentencesCount:{value:0},linesCount:{value:0},paragraphsCount:{value:0},pagesCount:{value:0}}}}],sourceFile:"./promptbook-collection/prepare-knowledge-from-markdown.ptbk.md"},{title:"Prepare Keywords",pipelineUrl:"https://promptbook.studio/promptbook/prepare-knowledge-keywords.ptbk.md",promptbookVersion:"0.61.0-15",parameters:[{name:"content",description:"The content",isInput:true,isOutput:false},{name:"keywords",description:"Keywords separated by comma",isInput:false,isOutput:true}],promptTemplates:[{blockType:"PROMPT_TEMPLATE",name:"knowledge",title:"Knowledge",modelRequirements:{modelVariant:"CHAT",modelName:"claude-3-opus-20240229"},content:"You are experienced data researcher, detect the important keywords in the document.\n\n# Rules\n\n- Write just keywords separated by comma\n\n# The document\n\nTake information from this document:\n\n> {content}",dependentParameterNames:["content"],resultingParameterName:"keywords"}],knowledgeSources:[],knowledgePieces:[],personas:[],preparations:[{id:1,promptbookVersion:"0.61.0-15",modelUsage:{price:{value:0},input:{tokensCount:{value:0},charactersCount:{value:0},wordsCount:{value:0},sentencesCount:{value:0},linesCount:{value:0},paragraphsCount:{value:0},pagesCount:{value:0}},output:{tokensCount:{value:0},charactersCount:{value:0},wordsCount:{value:0},sentencesCount:{value:0},linesCount:{value:0},paragraphsCount:{value:0},pagesCount:{value:0}}}}],sourceFile:"./promptbook-collection/prepare-knowledge-keywords.ptbk.md"},{title:"Prepare Title",pipelineUrl:"https://promptbook.studio/promptbook/prepare-knowledge-title.ptbk.md",promptbookVersion:"0.61.0-15",parameters:[{name:"content",description:"The content",isInput:true,isOutput:false},{name:"title",description:"The title of the document",isInput:false,isOutput:true}],promptTemplates:[{blockType:"PROMPT_TEMPLATE",name:"knowledge",title:"Knowledge",modelRequirements:{modelVariant:"CHAT",modelName:"claude-3-opus-20240229"},content:"You are experienced content creator, write best title for the document.\n\n# Rules\n\n- Write just title, nothing else\n- Title should be concise and clear\n- Write maximum 5 words for the title\n\n# The document\n\n> {content}",expectations:{words:{min:1,max:8}},dependentParameterNames:["content"],resultingParameterName:"title"}],knowledgeSources:[],knowledgePieces:[],personas:[],preparations:[{id:1,promptbookVersion:"0.61.0-15",modelUsage:{price:{value:0},input:{tokensCount:{value:0},charactersCount:{value:0},wordsCount:{value:0},sentencesCount:{value:0},linesCount:{value:0},paragraphsCount:{value:0},pagesCount:{value:0}},output:{tokensCount:{value:0},charactersCount:{value:0},wordsCount:{value:0},sentencesCount:{value:0},linesCount:{value:0},paragraphsCount:{value:0},pagesCount:{value:0}}}}],sourceFile:"./promptbook-collection/prepare-knowledge-title.ptbk.md"},{title:"Prepare Keywords",pipelineUrl:"https://promptbook.studio/promptbook/prepare-persona.ptbk.md",promptbookVersion:"0.61.0-15",parameters:[{name:"availableModelNames",description:"List of available model names separated by comma (,)",isInput:true,isOutput:false},{name:"personaDescription",description:"Description of the persona",isInput:true,isOutput:false},{name:"modelRequirements",description:"Specific requirements for the model",isInput:false,isOutput:true}],promptTemplates:[{blockType:"PROMPT_TEMPLATE",name:"make-model-requirements",title:"Make modelRequirements",modelRequirements:{modelVariant:"CHAT",modelName:"gpt-4-turbo"},content:"You are experienced AI engineer, you need to create virtual assistant.\nWrite\n\n## Sample\n\n```json\n{\n\"modelName\": \"gpt-4o\",\n\"systemMessage\": \"You are experienced AI engineer and helpfull assistant.\",\n\"temperature\": 0.7\n}\n```\n\n## Instructions\n\n### Option `modelName`\n\nPick from the following models:\n\n- {availableModelNames}\n\n### Option `systemMessage`\n\nThe system message is used to communicate instructions or provide context to the model at the beginning of a conversation. It is displayed in a different format compared to user messages, helping the model understand its role in the conversation. The system message typically guides the model's behavior, sets the tone, or specifies desired output from the model. By utilizing the system message effectively, users can steer the model towards generating more accurate and relevant responses.\n\nFor example:\n\n> You are an experienced AI engineer and helpful assistant.\n\n> You are a friendly and knowledgeable chatbot.\n\n### Option `temperature`\n\nThe sampling temperature, between 0 and 1. Higher values like 0.8 will make the output more random, while lower values like 0.2 will make it more focused and deterministic. If set to 0, the model will use log probability to automatically increase the temperature until certain thresholds are hit.\n\nYou can pick a value between 0 and 2. For example:\n\n- `0.1`: Low temperature, extremely conservative and deterministic\n- `0.5`: Medium temperature, balanced between conservative and creative\n- `1.0`: High temperature, creative and bit random\n- `1.5`: Very high temperature, extremely creative and often chaotic and unpredictable\n- `2.0`: Maximum temperature, completely random and unpredictable, for some extreme creative use cases\n\n# The assistant\n\nTake this description of the persona:\n\n> {personaDescription}",expectFormat:"JSON",dependentParameterNames:["availableModelNames","personaDescription"],resultingParameterName:"modelRequirements"}],knowledgeSources:[],knowledgePieces:[],personas:[],preparations:[{id:1,promptbookVersion:"0.61.0-15",modelUsage:{price:{value:0},input:{tokensCount:{value:0},charactersCount:{value:0},wordsCount:{value:0},sentencesCount:{value:0},linesCount:{value:0},paragraphsCount:{value:0},pagesCount:{value:0}},output:{tokensCount:{value:0},charactersCount:{value:0},wordsCount:{value:0},sentencesCount:{value:0},linesCount:{value:0},paragraphsCount:{value:0},pagesCount:{value:0}}}}],sourceFile:"./promptbook-collection/prepare-persona.ptbk.md"}];
499
+ var PipelineCollection = [{title:"Prepare Knowledge from Markdown",pipelineUrl:"https://promptbook.studio/promptbook/prepare-knowledge-from-markdown.ptbk.md",promptbookVersion:"0.61.0-17",parameters:[{name:"content",description:"Markdown document content",isInput:true,isOutput:false},{name:"knowledge",description:"The knowledge JSON object",isInput:false,isOutput:true}],promptTemplates:[{blockType:"PROMPT_TEMPLATE",name:"knowledge",title:"Knowledge",modelRequirements:{modelVariant:"CHAT",modelName:"claude-3-opus-20240229"},content:"You are experienced data researcher, extract the important knowledge from the document.\n\n# Rules\n\n- Make pieces of information concise, clear, and easy to understand\n- One piece of information should be approximately 1 paragraph\n- Divide the paragraphs by markdown horizontal lines ---\n- Omit irrelevant information\n- Group redundant information\n- Write just extracted information, nothing else\n\n# The document\n\nTake information from this document:\n\n> {content}",dependentParameterNames:["content"],resultingParameterName:"knowledge"}],knowledgeSources:[],knowledgePieces:[],personas:[],preparations:[{id:1,promptbookVersion:"0.61.0-17",modelUsage:{price:{value:0},input:{tokensCount:{value:0},charactersCount:{value:0},wordsCount:{value:0},sentencesCount:{value:0},linesCount:{value:0},paragraphsCount:{value:0},pagesCount:{value:0}},output:{tokensCount:{value:0},charactersCount:{value:0},wordsCount:{value:0},sentencesCount:{value:0},linesCount:{value:0},paragraphsCount:{value:0},pagesCount:{value:0}}}}],sourceFile:"./promptbook-collection/prepare-knowledge-from-markdown.ptbk.md"},{title:"Prepare Keywords",pipelineUrl:"https://promptbook.studio/promptbook/prepare-knowledge-keywords.ptbk.md",promptbookVersion:"0.61.0-17",parameters:[{name:"content",description:"The content",isInput:true,isOutput:false},{name:"keywords",description:"Keywords separated by comma",isInput:false,isOutput:true}],promptTemplates:[{blockType:"PROMPT_TEMPLATE",name:"knowledge",title:"Knowledge",modelRequirements:{modelVariant:"CHAT",modelName:"claude-3-opus-20240229"},content:"You are experienced data researcher, detect the important keywords in the document.\n\n# Rules\n\n- Write just keywords separated by comma\n\n# The document\n\nTake information from this document:\n\n> {content}",dependentParameterNames:["content"],resultingParameterName:"keywords"}],knowledgeSources:[],knowledgePieces:[],personas:[],preparations:[{id:1,promptbookVersion:"0.61.0-17",modelUsage:{price:{value:0},input:{tokensCount:{value:0},charactersCount:{value:0},wordsCount:{value:0},sentencesCount:{value:0},linesCount:{value:0},paragraphsCount:{value:0},pagesCount:{value:0}},output:{tokensCount:{value:0},charactersCount:{value:0},wordsCount:{value:0},sentencesCount:{value:0},linesCount:{value:0},paragraphsCount:{value:0},pagesCount:{value:0}}}}],sourceFile:"./promptbook-collection/prepare-knowledge-keywords.ptbk.md"},{title:"Prepare Title",pipelineUrl:"https://promptbook.studio/promptbook/prepare-knowledge-title.ptbk.md",promptbookVersion:"0.61.0-17",parameters:[{name:"content",description:"The content",isInput:true,isOutput:false},{name:"title",description:"The title of the document",isInput:false,isOutput:true}],promptTemplates:[{blockType:"PROMPT_TEMPLATE",name:"knowledge",title:"Knowledge",modelRequirements:{modelVariant:"CHAT",modelName:"claude-3-opus-20240229"},content:"You are experienced content creator, write best title for the document.\n\n# Rules\n\n- Write just title, nothing else\n- Title should be concise and clear\n- Write maximum 5 words for the title\n\n# The document\n\n> {content}",expectations:{words:{min:1,max:8}},dependentParameterNames:["content"],resultingParameterName:"title"}],knowledgeSources:[],knowledgePieces:[],personas:[],preparations:[{id:1,promptbookVersion:"0.61.0-17",modelUsage:{price:{value:0},input:{tokensCount:{value:0},charactersCount:{value:0},wordsCount:{value:0},sentencesCount:{value:0},linesCount:{value:0},paragraphsCount:{value:0},pagesCount:{value:0}},output:{tokensCount:{value:0},charactersCount:{value:0},wordsCount:{value:0},sentencesCount:{value:0},linesCount:{value:0},paragraphsCount:{value:0},pagesCount:{value:0}}}}],sourceFile:"./promptbook-collection/prepare-knowledge-title.ptbk.md"},{title:"Prepare Keywords",pipelineUrl:"https://promptbook.studio/promptbook/prepare-persona.ptbk.md",promptbookVersion:"0.61.0-17",parameters:[{name:"availableModelNames",description:"List of available model names separated by comma (,)",isInput:true,isOutput:false},{name:"personaDescription",description:"Description of the persona",isInput:true,isOutput:false},{name:"modelRequirements",description:"Specific requirements for the model",isInput:false,isOutput:true}],promptTemplates:[{blockType:"PROMPT_TEMPLATE",name:"make-model-requirements",title:"Make modelRequirements",modelRequirements:{modelVariant:"CHAT",modelName:"gpt-4-turbo"},content:"You are experienced AI engineer, you need to create virtual assistant.\nWrite\n\n## Sample\n\n```json\n{\n\"modelName\": \"gpt-4o\",\n\"systemMessage\": \"You are experienced AI engineer and helpfull assistant.\",\n\"temperature\": 0.7\n}\n```\n\n## Instructions\n\n### Option `modelName`\n\nPick from the following models:\n\n- {availableModelNames}\n\n### Option `systemMessage`\n\nThe system message is used to communicate instructions or provide context to the model at the beginning of a conversation. It is displayed in a different format compared to user messages, helping the model understand its role in the conversation. The system message typically guides the model's behavior, sets the tone, or specifies desired output from the model. By utilizing the system message effectively, users can steer the model towards generating more accurate and relevant responses.\n\nFor example:\n\n> You are an experienced AI engineer and helpful assistant.\n\n> You are a friendly and knowledgeable chatbot.\n\n### Option `temperature`\n\nThe sampling temperature, between 0 and 1. Higher values like 0.8 will make the output more random, while lower values like 0.2 will make it more focused and deterministic. If set to 0, the model will use log probability to automatically increase the temperature until certain thresholds are hit.\n\nYou can pick a value between 0 and 2. For example:\n\n- `0.1`: Low temperature, extremely conservative and deterministic\n- `0.5`: Medium temperature, balanced between conservative and creative\n- `1.0`: High temperature, creative and bit random\n- `1.5`: Very high temperature, extremely creative and often chaotic and unpredictable\n- `2.0`: Maximum temperature, completely random and unpredictable, for some extreme creative use cases\n\n# The assistant\n\nTake this description of the persona:\n\n> {personaDescription}",expectFormat:"JSON",dependentParameterNames:["availableModelNames","personaDescription"],resultingParameterName:"modelRequirements"}],knowledgeSources:[],knowledgePieces:[],personas:[],preparations:[{id:1,promptbookVersion:"0.61.0-17",modelUsage:{price:{value:0},input:{tokensCount:{value:0},charactersCount:{value:0},wordsCount:{value:0},sentencesCount:{value:0},linesCount:{value:0},paragraphsCount:{value:0},pagesCount:{value:0}},output:{tokensCount:{value:0},charactersCount:{value:0},wordsCount:{value:0},sentencesCount:{value:0},linesCount:{value:0},paragraphsCount:{value:0},pagesCount:{value:0}}}}],sourceFile:"./promptbook-collection/prepare-persona.ptbk.md"}];
500
500
 
501
501
  /**
502
502
  * Prettify the html code
@@ -1105,11 +1105,11 @@
1105
1105
  throw new PipelineLogicError(spaceTrim.spaceTrim(function (block) { return "\n\n Can not resolve some parameters:\n Either you are using a parameter that is not defined, or there are some circular dependencies.\n\n Can not resolve:\n ".concat(block(unresovedTemplates
1106
1106
  .map(function (_a) {
1107
1107
  var resultingParameterName = _a.resultingParameterName, dependentParameterNames = _a.dependentParameterNames;
1108
- return "- {".concat(resultingParameterName, "} depends on ").concat(dependentParameterNames
1108
+ return "- Parameter {".concat(resultingParameterName, "} which depends on ").concat(dependentParameterNames
1109
1109
  .map(function (dependentParameterName) { return "{".concat(dependentParameterName, "}"); })
1110
- .join(', '));
1110
+ .join(' and '));
1111
1111
  })
1112
- .join('\n')), "\n\n Resolved:\n ").concat(block(resovedParameters.map(function (name) { return "- {".concat(name, "}"); }).join('\n')), "\n "); }));
1112
+ .join('\n')), "\n\n Resolved:\n ").concat(block(resovedParameters.map(function (name) { return "- Parameter {".concat(name, "}"); }).join('\n')), "\n "); }));
1113
1113
  }
1114
1114
  resovedParameters = __spreadArray(__spreadArray([], __read(resovedParameters), false), __read(currentlyResovedTemplates.map(function (_a) {
1115
1115
  var resultingParameterName = _a.resultingParameterName;
@@ -1172,79 +1172,94 @@
1172
1172
  }(Error));
1173
1173
 
1174
1174
  /**
1175
- * Library of promptbooks that groups together promptbooks for an application.
1176
- * This implementation is a very thin wrapper around the Array / Map of promptbooks.
1175
+ * Unprepare just strips the preparation data of the pipeline
1176
+ */
1177
+ function unpreparePipeline(pipeline) {
1178
+ var personas = pipeline.personas, knowledgeSources = pipeline.knowledgeSources;
1179
+ personas = personas.map(function (persona) { return (__assign(__assign({}, persona), { modelRequirements: undefined, preparationIds: undefined })); });
1180
+ knowledgeSources = knowledgeSources.map(function (knowledgeSource) { return (__assign(__assign({}, knowledgeSource), { preparationIds: undefined })); });
1181
+ return __assign(__assign({}, pipeline), { knowledgeSources: knowledgeSources, knowledgePieces: [], personas: personas, preparations: [] });
1182
+ }
1183
+ /**
1184
+ * TODO: [🔼] !!! Export via `@promptbook/core`
1185
+ * TODO: Write tests for `preparePipeline`
1186
+ */
1187
+
1188
+ /**
1189
+ * Library of pipelines that groups together pipelines for an application.
1190
+ * This implementation is a very thin wrapper around the Array / Map of pipelines.
1177
1191
  *
1178
1192
  * @private use `createCollectionFromJson` instead
1179
- * @see https://github.com/webgptorg/promptbook#promptbook-collection
1193
+ * @see https://github.com/webgptorg/pipeline#pipeline-collection
1180
1194
  */
1181
1195
  var SimplePipelineCollection = /** @class */ (function () {
1182
1196
  /**
1183
- * Constructs a pipeline collection from promptbooks
1197
+ * Constructs a pipeline collection from pipelines
1184
1198
  *
1185
- * @param promptbooks @@@
1199
+ * @param pipelines @@@
1186
1200
  *
1187
1201
  * @private Use instead `createCollectionFromJson`
1188
- * Note: During the construction logic of all promptbooks are validated
1202
+ * Note: During the construction logic of all pipelines are validated
1189
1203
  * Note: It is not recommended to use this constructor directly, use `createCollectionFromJson` *(or other variant)* instead
1190
1204
  */
1191
1205
  function SimplePipelineCollection() {
1192
1206
  var e_1, _a;
1193
- var promptbooks = [];
1207
+ var pipelines = [];
1194
1208
  for (var _i = 0; _i < arguments.length; _i++) {
1195
- promptbooks[_i] = arguments[_i];
1209
+ pipelines[_i] = arguments[_i];
1196
1210
  }
1197
1211
  this.collection = new Map();
1198
1212
  try {
1199
- for (var promptbooks_1 = __values(promptbooks), promptbooks_1_1 = promptbooks_1.next(); !promptbooks_1_1.done; promptbooks_1_1 = promptbooks_1.next()) {
1200
- var promptbook = promptbooks_1_1.value;
1201
- if (promptbook.pipelineUrl === undefined) {
1202
- throw new ReferenceError$1(spaceTrim.spaceTrim("\n Promptbook with name \"".concat(promptbook.title, "\" does not have defined URL\n\n File:\n ").concat(promptbook.sourceFile || 'Unknown', "\n\n Note: Promptbooks without URLs are called anonymous promptbooks\n They can be used as standalone promptbooks, but they cannot be referenced by other promptbooks\n And also they cannot be used in the pipeline collection\n\n ")));
1213
+ for (var pipelines_1 = __values(pipelines), pipelines_1_1 = pipelines_1.next(); !pipelines_1_1.done; pipelines_1_1 = pipelines_1.next()) {
1214
+ var pipeline = pipelines_1_1.value;
1215
+ if (pipeline.pipelineUrl === undefined) {
1216
+ throw new ReferenceError$1(spaceTrim.spaceTrim("\n Pipeline with name \"".concat(pipeline.title, "\" does not have defined URL\n\n File:\n ").concat(pipeline.sourceFile || 'Unknown', "\n\n Note: Pipelines without URLs are called anonymous pipelines\n They can be used as standalone pipelines, but they cannot be referenced by other pipelines\n And also they cannot be used in the pipeline collection\n\n ")));
1203
1217
  }
1204
- validatePipeline(promptbook);
1218
+ validatePipeline(pipeline);
1205
1219
  // Note: [🦄]
1206
- if (this.collection.has(promptbook.pipelineUrl) &&
1207
- pipelineJsonToString(promptbook) !== pipelineJsonToString(this.collection.get(promptbook.pipelineUrl))) {
1208
- var existing = this.collection.get(promptbook.pipelineUrl);
1209
- throw new ReferenceError$1(spaceTrim.spaceTrim("\n Promptbook with URL \"".concat(promptbook.pipelineUrl, "\" is already in the collection\n\n Conflicting files:\n ").concat(existing.sourceFile || 'Unknown', "\n ").concat(promptbook.sourceFile || 'Unknown', "\n\n Note: Promptbooks with the same URL are not allowed\n Only exepction is when the promptbooks are identical\n\n ")));
1220
+ if (this.collection.has(pipeline.pipelineUrl) &&
1221
+ pipelineJsonToString(unpreparePipeline(pipeline)) !==
1222
+ pipelineJsonToString(unpreparePipeline(this.collection.get(pipeline.pipelineUrl)))) {
1223
+ var existing = this.collection.get(pipeline.pipelineUrl);
1224
+ throw new ReferenceError$1(spaceTrim.spaceTrim("\n Pipeline with URL \"".concat(pipeline.pipelineUrl, "\" is already in the collection\n\n Conflicting files:\n ").concat(existing.sourceFile || 'Unknown', "\n ").concat(pipeline.sourceFile || 'Unknown', "\n\n Note: Pipelines with the same URL are not allowed\n Only exepction is when the pipelines are identical\n\n ")));
1210
1225
  }
1211
- this.collection.set(promptbook.pipelineUrl, promptbook);
1226
+ this.collection.set(pipeline.pipelineUrl, pipeline);
1212
1227
  }
1213
1228
  }
1214
1229
  catch (e_1_1) { e_1 = { error: e_1_1 }; }
1215
1230
  finally {
1216
1231
  try {
1217
- if (promptbooks_1_1 && !promptbooks_1_1.done && (_a = promptbooks_1.return)) _a.call(promptbooks_1);
1232
+ if (pipelines_1_1 && !pipelines_1_1.done && (_a = pipelines_1.return)) _a.call(pipelines_1);
1218
1233
  }
1219
1234
  finally { if (e_1) throw e_1.error; }
1220
1235
  }
1221
1236
  }
1222
1237
  /**
1223
- * Gets all promptbooks in the collection
1238
+ * Gets all pipelines in the collection
1224
1239
  */
1225
1240
  SimplePipelineCollection.prototype.listPipelines = function () {
1226
1241
  return Array.from(this.collection.keys());
1227
1242
  };
1228
1243
  /**
1229
- * Gets promptbook by its URL
1244
+ * Gets pipeline by its URL
1230
1245
  *
1231
1246
  * Note: This is not a direct fetching from the URL, but a lookup in the collection
1232
1247
  */
1233
1248
  SimplePipelineCollection.prototype.getPipelineByUrl = function (url) {
1234
1249
  var _this = this;
1235
- var promptbook = this.collection.get(url);
1236
- if (!promptbook) {
1250
+ var pipeline = this.collection.get(url);
1251
+ if (!pipeline) {
1237
1252
  if (this.listPipelines().length === 0) {
1238
- throw new NotFoundError(spaceTrim.spaceTrim("\n Promptbook with url \"".concat(url, "\" not found\n\n No promptbooks available\n ")));
1253
+ throw new NotFoundError(spaceTrim.spaceTrim("\n Pipeline with url \"".concat(url, "\" not found\n\n No pipelines available\n ")));
1239
1254
  }
1240
- throw new NotFoundError(spaceTrim.spaceTrim(function (block) { return "\n Promptbook with url \"".concat(url, "\" not found\n\n Available promptbooks:\n ").concat(block(_this.listPipelines()
1255
+ throw new NotFoundError(spaceTrim.spaceTrim(function (block) { return "\n Pipeline with url \"".concat(url, "\" not found\n\n Available pipelines:\n ").concat(block(_this.listPipelines()
1241
1256
  .map(function (pipelineUrl) { return "- ".concat(pipelineUrl); })
1242
1257
  .join('\n')), "\n\n "); }));
1243
1258
  }
1244
- return promptbook;
1259
+ return pipeline;
1245
1260
  };
1246
1261
  /**
1247
- * Checks whether given prompt was defined in any promptbook in the collection
1262
+ * Checks whether given prompt was defined in any pipeline in the collection
1248
1263
  */
1249
1264
  SimplePipelineCollection.prototype.isResponsibleForPrompt = function (prompt) {
1250
1265
  return true;
@@ -2019,7 +2034,7 @@
2019
2034
  throw new PipelineExecutionError(spaceTrim__default["default"](function (block) { return "\n All execution tools failed:\n\n ".concat(block(errors.map(function (error) { return "- ".concat(error.name || 'Error', ": ").concat(error.message); }).join('\n')), "\n\n "); }));
2020
2035
  }
2021
2036
  else {
2022
- throw new PipelineExecutionError(spaceTrim__default["default"](function (block) { return "\n No execution tools available for model variant \"".concat(prompt.modelRequirements.modelVariant, "\".\n\n tl;dr\n\n You have provided no LLM Execution Tools that support model variant \"").concat(prompt.modelRequirements.modelVariant, ":\n ").concat(block(_this.llmExecutionTools
2037
+ throw new PipelineExecutionError(spaceTrim__default["default"](function (block) { return "\n You have not provided any `LlmExecutionTools` that support model variant \"".concat(prompt.modelRequirements.modelVariant, "\n\n Available `LlmExecutionTools`:\n ").concat(block(_this.llmExecutionTools
2023
2038
  .map(function (tools) { return "- ".concat(tools.title, " ").concat(tools.description || ''); })
2024
2039
  .join('\n')), "\n\n "); }));
2025
2040
  }
@@ -2098,7 +2113,7 @@
2098
2113
  llmExecutionTools[_i] = arguments[_i];
2099
2114
  }
2100
2115
  if (llmExecutionTools.length === 0) {
2101
- var warningMessage = spaceTrim__default["default"]("\n You have provided no LLM Execution Tools.\n This means that you won't be able to execute any prompts that require large language models like GPT-4 or Anthropic's Claude.\n\n Technically, it's not an error, but it's probably not what you want because it does not make sense to use Promptbook without language models.\n ");
2116
+ var warningMessage = spaceTrim__default["default"]("\n You have not provided any `LlmExecutionTools`\n This means that you won't be able to execute any prompts that require large language models like GPT-4 or Anthropic's Claude.\n\n Technically, it's not an error, but it's probably not what you want because it does not make sense to use Promptbook without language models.\n ");
2102
2117
  // TODO: [🟥] Detect browser / node and make it colorfull
2103
2118
  console.warn(warningMessage);
2104
2119
  /*
@@ -2132,9 +2147,11 @@
2132
2147
  // Note: Ignoring `pipeline.preparations` @@@
2133
2148
  // Note: Ignoring `pipeline.knowledgePieces` @@@
2134
2149
  if (!pipeline.personas.every(function (persona) { return persona.modelRequirements !== undefined; })) {
2150
+ console.log('!!!!', 'Not all personas have modelRequirements');
2135
2151
  return false;
2136
2152
  }
2137
2153
  if (!pipeline.knowledgeSources.every(function (knowledgeSource) { return knowledgeSource.preparationIds !== undefined; })) {
2154
+ console.log('!!!!', 'Not all knowledgeSources have preparationIds');
2138
2155
  return false;
2139
2156
  }
2140
2157
  // TODO: !!!!! Is context in each template
@@ -2143,6 +2160,7 @@
2143
2160
  return true;
2144
2161
  }
2145
2162
  /**
2163
+ * TODO: [🐠] Maybe base this on `makeValidator`
2146
2164
  * TODO: [🔼] Export via core or utils
2147
2165
  * TODO: [🧊] Pipeline can be partially prepared, this should return true ONLY if fully prepared
2148
2166
  */
@@ -5460,11 +5478,11 @@
5460
5478
  }
5461
5479
 
5462
5480
  /**
5463
- * Constructs Promptbook from given directory
5481
+ * Constructs Pipeline from given directory
5464
5482
  *
5465
5483
  * Note: Works only in Node.js environment because it reads the file system
5466
5484
  *
5467
- * @param path - path to the directory with promptbooks
5485
+ * @param path - path to the directory with pipelines
5468
5486
  * @param options - Misc options for the collection
5469
5487
  * @returns PipelineCollection
5470
5488
  */
@@ -5494,20 +5512,31 @@
5494
5512
  }
5495
5513
  _a = options || {}, _b = _a.isRecursive, isRecursive = _b === void 0 ? true : _b, _c = _a.isVerbose, isVerbose = _c === void 0 ? false : _c, _d = _a.isLazyLoaded, isLazyLoaded = _d === void 0 ? false : _d, _e = _a.isCrashedOnError, isCrashedOnError = _e === void 0 ? true : _e;
5496
5514
  collection = createCollectionFromPromise(function () { return __awaiter(_this, void 0, void 0, function () {
5497
- var fileNames, promptbooks, _loop_1, fileNames_1, fileNames_1_1, fileName, e_1_1;
5515
+ var fileNames, pipelines, _loop_1, fileNames_1, fileNames_1_1, fileName, e_1_1;
5498
5516
  var e_1, _a;
5499
5517
  return __generator(this, function (_b) {
5500
5518
  switch (_b.label) {
5501
5519
  case 0:
5502
5520
  if (isVerbose) {
5503
- console.info("Creating pipeline collection from path ".concat(path$1.split('\\').join('/')));
5521
+ console.info(colors__default["default"].cyan("Creating pipeline collection from path ".concat(path$1.split('\\').join('/'))));
5504
5522
  }
5505
5523
  return [4 /*yield*/, listAllFiles(path$1, isRecursive)];
5506
5524
  case 1:
5507
5525
  fileNames = _b.sent();
5508
- promptbooks = [];
5526
+ // Note: First load all .ptbk.json and then .ptbk.md files
5527
+ // .ptbk.json can be prepared so it is faster to load
5528
+ fileNames.sort(function (a, b) {
5529
+ if (a.endsWith('.ptbk.json') && b.endsWith('.ptbk.md')) {
5530
+ return -1;
5531
+ }
5532
+ if (a.endsWith('.ptbk.md') && b.endsWith('.ptbk.json')) {
5533
+ return 1;
5534
+ }
5535
+ return 0;
5536
+ });
5537
+ pipelines = [];
5509
5538
  _loop_1 = function (fileName) {
5510
- var sourceFile, promptbook, pipelineString, _c, _d, error_1, wrappedErrorMessage;
5539
+ var sourceFile, pipeline, pipelineString, _c, _d, error_1, wrappedErrorMessage;
5511
5540
  return __generator(this, function (_e) {
5512
5541
  switch (_e.label) {
5513
5542
  case 0:
@@ -5515,53 +5544,52 @@
5515
5544
  _e.label = 1;
5516
5545
  case 1:
5517
5546
  _e.trys.push([1, 8, , 9]);
5518
- promptbook = null;
5547
+ pipeline = null;
5519
5548
  if (!fileName.endsWith('.ptbk.md')) return [3 /*break*/, 4];
5520
5549
  return [4 /*yield*/, promises.readFile(fileName, 'utf8')];
5521
5550
  case 2:
5522
5551
  pipelineString = (_e.sent());
5523
5552
  return [4 /*yield*/, pipelineStringToJson(pipelineString, options)];
5524
5553
  case 3:
5525
- promptbook = _e.sent();
5526
- promptbook = __assign(__assign({}, promptbook), { sourceFile: sourceFile });
5554
+ pipeline = _e.sent();
5555
+ pipeline = __assign(__assign({}, pipeline), { sourceFile: sourceFile });
5527
5556
  return [3 /*break*/, 7];
5528
5557
  case 4:
5529
5558
  if (!fileName.endsWith('.ptbk.json')) return [3 /*break*/, 6];
5530
- if (isVerbose) {
5531
- console.info("Loading ".concat(fileName.split('\\').join('/')));
5532
- }
5533
5559
  _d = (_c = JSON).parse;
5534
5560
  return [4 /*yield*/, promises.readFile(fileName, 'utf8')];
5535
5561
  case 5:
5536
5562
  // TODO: Handle non-valid JSON files
5537
- promptbook = _d.apply(_c, [_e.sent()]);
5563
+ pipeline = _d.apply(_c, [_e.sent()]);
5538
5564
  // TODO: [🌗]
5539
- promptbook = __assign(__assign({}, promptbook), { sourceFile: sourceFile });
5565
+ pipeline = __assign(__assign({}, pipeline), { sourceFile: sourceFile });
5540
5566
  return [3 /*break*/, 7];
5541
5567
  case 6:
5542
5568
  if (isVerbose) {
5543
- console.info("Skipping file ".concat(fileName.split('\\').join('/')));
5569
+ console.info(colors__default["default"].gray("Skipping file ".concat(fileName.split('\\').join('/'))));
5544
5570
  }
5545
5571
  _e.label = 7;
5546
5572
  case 7:
5547
5573
  // ---
5548
- if (promptbook !== null) {
5549
- if (!promptbook.pipelineUrl) {
5574
+ if (pipeline !== null) {
5575
+ if (!pipeline.pipelineUrl) {
5550
5576
  if (isVerbose) {
5551
- console.info("Not loading ".concat(fileName.split('\\').join('/'), " - missing URL"));
5577
+ console.info(colors__default["default"].red("Can not load pipeline from ".concat(fileName
5578
+ .split('\\')
5579
+ .join('/'), " because of missing URL")));
5552
5580
  }
5553
5581
  }
5554
5582
  else {
5555
- if (isVerbose) {
5556
- console.info("Loading ".concat(fileName.split('\\').join('/')));
5557
- }
5558
5583
  if (!isCrashedOnError) {
5559
- // Note: Validate promptbook to check if it is logically correct to not crash on invalid promptbooks
5584
+ // Note: Validate pipeline to check if it is logically correct to not crash on invalid pipelines
5560
5585
  // But be handled in current try-catch block
5561
- validatePipeline(promptbook);
5586
+ validatePipeline(pipeline);
5587
+ }
5588
+ if (isVerbose) {
5589
+ console.info(colors__default["default"].green("Loading ".concat(fileName.split('\\').join('/'))));
5562
5590
  }
5563
- // Note: [🦄] Promptbook with same url uniqueness will be checked automatically in SimplePipelineCollection
5564
- promptbooks.push(promptbook);
5591
+ // Note: [🦄] Pipeline with same url uniqueness will be checked automatically in SimplePipelineCollection
5592
+ pipelines.push(pipeline);
5565
5593
  }
5566
5594
  }
5567
5595
  return [3 /*break*/, 9];
@@ -5607,7 +5635,7 @@
5607
5635
  }
5608
5636
  finally { if (e_1) throw e_1.error; }
5609
5637
  return [7 /*endfinally*/];
5610
- case 9: return [2 /*return*/, promptbooks];
5638
+ case 9: return [2 /*return*/, pipelines];
5611
5639
  }
5612
5640
  });
5613
5641
  }); });
@@ -5681,8 +5709,8 @@
5681
5709
  });
5682
5710
  }
5683
5711
  /**
5684
- * TODO: !!!! [🧠] Library precompilation and do not mix markdown and json promptbooks
5685
- * Note: [🟢] This code should never be published outside of `@promptbook/node`
5712
+ * TODO: !!!! [🧠] Library precompilation and do not mix markdown and json pipelines
5713
+ * Note: [🟢] This code should never be published outside of `@pipeline/node`
5686
5714
  */
5687
5715
 
5688
5716
  /**