@promptbook/cli 0.77.0-3 → 0.77.0-4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/umd/index.umd.js CHANGED
@@ -49,7 +49,7 @@
49
49
  *
50
50
  * @see https://github.com/webgptorg/promptbook
51
51
  */
52
- var PROMPTBOOK_ENGINE_VERSION = '0.77.0-2';
52
+ var PROMPTBOOK_ENGINE_VERSION = '0.77.0-3';
53
53
  /**
54
54
  * TODO: string_promptbook_version should be constrained to the all versions of Promptbook engine
55
55
  * Note: [💞] Ignore a discrepancy between file name and entity name
@@ -672,6 +672,312 @@
672
672
  * Note: [🟡] Code in this file should never be published outside of `@promptbook/cli`
673
673
  */
674
674
 
675
+ /**
676
+ * This error type indicates that some part of the code is not implemented yet
677
+ *
678
+ * @public exported from `@promptbook/core`
679
+ */
680
+ var NotYetImplementedError = /** @class */ (function (_super) {
681
+ __extends(NotYetImplementedError, _super);
682
+ function NotYetImplementedError(message) {
683
+ var _this = _super.call(this, spaceTrim.spaceTrim(function (block) { return "\n ".concat(block(message), "\n\n Note: This feature is not implemented yet but it will be soon.\n\n If you want speed up the implementation or just read more, look here:\n https://github.com/webgptorg/promptbook\n\n Or contact us on me@pavolhejny.com\n\n "); })) || this;
684
+ _this.name = 'NotYetImplementedError';
685
+ Object.setPrototypeOf(_this, NotYetImplementedError.prototype);
686
+ return _this;
687
+ }
688
+ return NotYetImplementedError;
689
+ }(Error));
690
+
691
+ /**
692
+ * @@@
693
+ *
694
+ * Note: `$` is used to indicate that this function is not a pure function - it access global scope
695
+ *
696
+ * @private internal function of `$Register`
697
+ */
698
+ function $getGlobalScope() {
699
+ return Function('return this')();
700
+ }
701
+
702
+ /**
703
+ * @@@
704
+ *
705
+ * @param text @@@
706
+ * @returns @@@
707
+ * @example 'HELLO_WORLD'
708
+ * @example 'I_LOVE_PROMPTBOOK'
709
+ * @public exported from `@promptbook/utils`
710
+ */
711
+ function normalizeTo_SCREAMING_CASE(text) {
712
+ var e_1, _a;
713
+ var charType;
714
+ var lastCharType = 'OTHER';
715
+ var normalizedName = '';
716
+ try {
717
+ for (var text_1 = __values(text), text_1_1 = text_1.next(); !text_1_1.done; text_1_1 = text_1.next()) {
718
+ var char = text_1_1.value;
719
+ var normalizedChar = void 0;
720
+ if (/^[a-z]$/.test(char)) {
721
+ charType = 'LOWERCASE';
722
+ normalizedChar = char.toUpperCase();
723
+ }
724
+ else if (/^[A-Z]$/.test(char)) {
725
+ charType = 'UPPERCASE';
726
+ normalizedChar = char;
727
+ }
728
+ else if (/^[0-9]$/.test(char)) {
729
+ charType = 'NUMBER';
730
+ normalizedChar = char;
731
+ }
732
+ else {
733
+ charType = 'OTHER';
734
+ normalizedChar = '_';
735
+ }
736
+ if (charType !== lastCharType &&
737
+ !(lastCharType === 'UPPERCASE' && charType === 'LOWERCASE') &&
738
+ !(lastCharType === 'NUMBER') &&
739
+ !(charType === 'NUMBER')) {
740
+ normalizedName += '_';
741
+ }
742
+ normalizedName += normalizedChar;
743
+ lastCharType = charType;
744
+ }
745
+ }
746
+ catch (e_1_1) { e_1 = { error: e_1_1 }; }
747
+ finally {
748
+ try {
749
+ if (text_1_1 && !text_1_1.done && (_a = text_1.return)) _a.call(text_1);
750
+ }
751
+ finally { if (e_1) throw e_1.error; }
752
+ }
753
+ normalizedName = normalizedName.replace(/_+/g, '_');
754
+ normalizedName = normalizedName.replace(/_?\/_?/g, '/');
755
+ normalizedName = normalizedName.replace(/^_/, '');
756
+ normalizedName = normalizedName.replace(/_$/, '');
757
+ return normalizedName;
758
+ }
759
+ /**
760
+ * TODO: Tests
761
+ * > expect(encodeRoutePath({ uriId: 'VtG7sR9rRJqwNEdM2', name: 'Moje tabule' })).toEqual('/VtG7sR9rRJqwNEdM2/Moje tabule');
762
+ * > expect(encodeRoutePath({ uriId: 'VtG7sR9rRJqwNEdM2', name: 'ěščřžžýáíúů' })).toEqual('/VtG7sR9rRJqwNEdM2/escrzyaieuu');
763
+ * > expect(encodeRoutePath({ uriId: 'VtG7sR9rRJqwNEdM2', name: ' ahoj ' })).toEqual('/VtG7sR9rRJqwNEdM2/ahoj');
764
+ * > expect(encodeRoutePath({ uriId: 'VtG7sR9rRJqwNEdM2', name: ' ahoj_ahojAhoj ahoj ' })).toEqual('/VtG7sR9rRJqwNEdM2/ahoj-ahoj-ahoj-ahoj');
765
+ * TODO: [🌺] Use some intermediate util splitWords
766
+ */
767
+
768
+ /**
769
+ * @@@
770
+ *
771
+ * @param text @@@
772
+ * @returns @@@
773
+ * @example 'hello_world'
774
+ * @example 'i_love_promptbook'
775
+ * @public exported from `@promptbook/utils`
776
+ */
777
+ function normalizeTo_snake_case(text) {
778
+ return normalizeTo_SCREAMING_CASE(text).toLowerCase();
779
+ }
780
+
781
+ /**
782
+ * Register is @@@
783
+ *
784
+ * Note: `$` is used to indicate that this function is not a pure function - it accesses and adds variables in global scope.
785
+ *
786
+ * @private internal utility, exported are only signleton instances of this class
787
+ */
788
+ var $Register = /** @class */ (function () {
789
+ function $Register(registerName) {
790
+ this.registerName = registerName;
791
+ var storageName = "_promptbook_".concat(normalizeTo_snake_case(registerName));
792
+ var globalScope = $getGlobalScope();
793
+ if (globalScope[storageName] === undefined) {
794
+ globalScope[storageName] = [];
795
+ }
796
+ else if (!Array.isArray(globalScope[storageName])) {
797
+ throw new UnexpectedError("Expected (global) ".concat(storageName, " to be an array, but got ").concat(typeof globalScope[storageName]));
798
+ }
799
+ this.storage = globalScope[storageName];
800
+ }
801
+ $Register.prototype.list = function () {
802
+ // <- TODO: ReadonlyDeep<ReadonlyArray<TRegistered>>
803
+ return this.storage;
804
+ };
805
+ $Register.prototype.register = function (registered) {
806
+ var packageName = registered.packageName, className = registered.className;
807
+ var existingRegistrationIndex = this.storage.findIndex(function (item) { return item.packageName === packageName && item.className === className; });
808
+ var existingRegistration = this.storage[existingRegistrationIndex];
809
+ if (!existingRegistration) {
810
+ this.storage.push(registered);
811
+ }
812
+ else {
813
+ this.storage[existingRegistrationIndex] = registered;
814
+ }
815
+ return {
816
+ registerName: this.registerName,
817
+ packageName: packageName,
818
+ className: className,
819
+ get isDestroyed() {
820
+ return false;
821
+ },
822
+ destroy: function () {
823
+ throw new NotYetImplementedError("Registration to ".concat(this.registerName, " is permanent in this version of Promptbook"));
824
+ },
825
+ };
826
+ };
827
+ return $Register;
828
+ }());
829
+
830
+ /**
831
+ * @@@
832
+ *
833
+ * Note: `$` is used to indicate that this interacts with the global scope
834
+ * @singleton Only one instance of each register is created per build, but thare can be more @@@
835
+ * @public exported from `@promptbook/core`
836
+ */
837
+ var $llmToolsMetadataRegister = new $Register('llm_tools_metadata');
838
+ /**
839
+ * TODO: [®] DRY Register logic
840
+ */
841
+
842
+ /**
843
+ * @@@
844
+ *
845
+ * Note: `$` is used to indicate that this interacts with the global scope
846
+ * @singleton Only one instance of each register is created per build, but thare can be more @@@
847
+ * @public exported from `@promptbook/core`
848
+ */
849
+ var $llmToolsRegister = new $Register('llm_execution_tools_constructors');
850
+ /**
851
+ * TODO: [®] DRY Register logic
852
+ */
853
+
854
+ /**
855
+ * Creates a message with all registered LLM tools
856
+ *
857
+ * Note: This function is used to create a (error) message when there is no constructor for some LLM provider
858
+ *
859
+ * @private internal function of `createLlmToolsFromConfiguration` and `$provideLlmToolsFromEnv`
860
+ */
861
+ function $registeredLlmToolsMessage() {
862
+ var e_1, _a, e_2, _b;
863
+ /**
864
+ * Mixes registered LLM tools from $llmToolsMetadataRegister and $llmToolsRegister
865
+ */
866
+ var all = [];
867
+ var _loop_1 = function (packageName, className, envVariables) {
868
+ if (all.some(function (item) { return item.packageName === packageName && item.className === className; })) {
869
+ return "continue";
870
+ }
871
+ all.push({ packageName: packageName, className: className, envVariables: envVariables });
872
+ };
873
+ try {
874
+ for (var _c = __values($llmToolsMetadataRegister.list()), _d = _c.next(); !_d.done; _d = _c.next()) {
875
+ var _e = _d.value, packageName = _e.packageName, className = _e.className, envVariables = _e.envVariables;
876
+ _loop_1(packageName, className, envVariables);
877
+ }
878
+ }
879
+ catch (e_1_1) { e_1 = { error: e_1_1 }; }
880
+ finally {
881
+ try {
882
+ if (_d && !_d.done && (_a = _c.return)) _a.call(_c);
883
+ }
884
+ finally { if (e_1) throw e_1.error; }
885
+ }
886
+ var _loop_2 = function (packageName, className) {
887
+ if (all.some(function (item) { return item.packageName === packageName && item.className === className; })) {
888
+ return "continue";
889
+ }
890
+ all.push({ packageName: packageName, className: className });
891
+ };
892
+ try {
893
+ for (var _f = __values($llmToolsRegister.list()), _g = _f.next(); !_g.done; _g = _f.next()) {
894
+ var _h = _g.value, packageName = _h.packageName, className = _h.className;
895
+ _loop_2(packageName, className);
896
+ }
897
+ }
898
+ catch (e_2_1) { e_2 = { error: e_2_1 }; }
899
+ finally {
900
+ try {
901
+ if (_g && !_g.done && (_b = _f.return)) _b.call(_f);
902
+ }
903
+ finally { if (e_2) throw e_2.error; }
904
+ }
905
+ var metadata = all.map(function (metadata) {
906
+ var isMetadataAviailable = $llmToolsMetadataRegister
907
+ .list()
908
+ .find(function (_a) {
909
+ var packageName = _a.packageName, className = _a.className;
910
+ return metadata.packageName === packageName && metadata.className === className;
911
+ });
912
+ var isInstalled = $llmToolsRegister
913
+ .list()
914
+ .find(function (_a) {
915
+ var packageName = _a.packageName, className = _a.className;
916
+ return metadata.packageName === packageName && metadata.className === className;
917
+ });
918
+ return __assign(__assign({}, metadata), { isMetadataAviailable: isMetadataAviailable, isInstalled: isInstalled });
919
+ });
920
+ if (metadata.length === 0) {
921
+ return "No LLM providers are available.";
922
+ }
923
+ return spaceTrim__default["default"](function (block) { return "\n Available LLM providers are:\n ".concat(block(metadata
924
+ .map(function (_a, i) {
925
+ var packageName = _a.packageName, className = _a.className, envVariables = _a.envVariables, isMetadataAviailable = _a.isMetadataAviailable, isInstalled = _a.isInstalled;
926
+ var more;
927
+ if (just(false)) {
928
+ more = '';
929
+ }
930
+ else if (!isMetadataAviailable && !isInstalled) {
931
+ // TODO: [�][�] Maybe do allow to do auto-install if package not registered and not found
932
+ more = "(not installed and no metadata, looks like a unexpected behavior)";
933
+ }
934
+ else if (isMetadataAviailable && !isInstalled) {
935
+ // TODO: [�][�]
936
+ more = "(not installed)";
937
+ }
938
+ else if (!isMetadataAviailable && isInstalled) {
939
+ more = "(no metadata, looks like a unexpected behavior)";
940
+ }
941
+ else if (isMetadataAviailable && isInstalled) {
942
+ more = "(installed)";
943
+ }
944
+ else {
945
+ more = "(unknown state, looks like a unexpected behavior)";
946
+ }
947
+ var envVariablesMessage = '';
948
+ if (envVariables) {
949
+ envVariablesMessage = 'Configured by ' + envVariables.join(' + ');
950
+ }
951
+ return spaceTrim__default["default"]("\n ".concat(i + 1, ") `").concat(className, "` from `").concat(packageName, "`\n ").concat(more, "\n ").concat(envVariablesMessage, "\n "));
952
+ // <- TODO: !!!!!! Is this indented correctly?
953
+ })
954
+ .join('\n')), "\n "); });
955
+ }
956
+ /**
957
+ * TODO: [®] DRY Register logic
958
+ */
959
+
960
+ /**
961
+ * Initializes `list-models` command for Promptbook CLI utilities
962
+ *
963
+ * @private internal function of `promptbookCli`
964
+ */
965
+ function initializeListModelsCommand(program) {
966
+ var _this = this;
967
+ var listModelsCommand = program.command('list-models');
968
+ listModelsCommand.description(spaceTrim__default["default"]("\n List all available and configured LLM models\n "));
969
+ listModelsCommand.action(function () { return __awaiter(_this, void 0, void 0, function () {
970
+ return __generator(this, function (_a) {
971
+ console.info($registeredLlmToolsMessage());
972
+ return [2 /*return*/, process.exit(0)];
973
+ });
974
+ }); });
975
+ }
976
+ /**
977
+ * Note: [💞] Ignore a discrepancy between file name and entity name
978
+ * Note: [🟡] Code in this file should never be published outside of `@promptbook/cli`
979
+ */
980
+
675
981
  /**
676
982
  * Converts PipelineCollection to serialized JSON
677
983
  *
@@ -2336,22 +2642,6 @@
2336
2642
  return LimitReachedError;
2337
2643
  }(Error));
2338
2644
 
2339
- /**
2340
- * This error type indicates that some part of the code is not implemented yet
2341
- *
2342
- * @public exported from `@promptbook/core`
2343
- */
2344
- var NotYetImplementedError = /** @class */ (function (_super) {
2345
- __extends(NotYetImplementedError, _super);
2346
- function NotYetImplementedError(message) {
2347
- var _this = _super.call(this, spaceTrim.spaceTrim(function (block) { return "\n ".concat(block(message), "\n\n Note: This feature is not implemented yet but it will be soon.\n\n If you want speed up the implementation or just read more, look here:\n https://github.com/webgptorg/promptbook\n\n Or contact us on me@pavolhejny.com\n\n "); })) || this;
2348
- _this.name = 'NotYetImplementedError';
2349
- Object.setPrototypeOf(_this, NotYetImplementedError.prototype);
2350
- return _this;
2351
- }
2352
- return NotYetImplementedError;
2353
- }(Error));
2354
-
2355
2645
  /**
2356
2646
  * Index of all custom errors
2357
2647
  *
@@ -4745,218 +5035,79 @@
4745
5035
  })];
4746
5036
  });
4747
5037
  }); };
4748
- return pipelineExecutor;
4749
- }
4750
- /**
4751
- * TODO: [🐚] Change onProgress to object that represents the running execution, can be subscribed via RxJS to and also awaited
4752
- */
4753
-
4754
- /**
4755
- * Prepares the persona for the pipeline
4756
- *
4757
- * @see https://github.com/webgptorg/promptbook/discussions/22
4758
- * @public exported from `@promptbook/core`
4759
- */
4760
- function preparePersona(personaDescription, tools, options) {
4761
- return __awaiter(this, void 0, void 0, function () {
4762
- var _a, isVerbose, collection, preparePersonaExecutor, _b, _llms, llmTools, availableModels, availableModelNames, result, outputParameters, modelRequirementsRaw, modelRequirements, modelName, systemMessage, temperature;
4763
- var _c;
4764
- return __generator(this, function (_d) {
4765
- switch (_d.label) {
4766
- case 0:
4767
- _a = options.isVerbose, isVerbose = _a === void 0 ? DEFAULT_IS_VERBOSE : _a;
4768
- if (tools === undefined || tools.llm === undefined) {
4769
- throw new MissingToolsError('LLM tools are required for preparing persona');
4770
- }
4771
- collection = createCollectionFromJson.apply(void 0, __spreadArray([], __read(PipelineCollection), false));
4772
- _b = createPipelineExecutor;
4773
- _c = {};
4774
- return [4 /*yield*/, collection.getPipelineByUrl('https://promptbook.studio/promptbook/prepare-persona.book.md')];
4775
- case 1:
4776
- preparePersonaExecutor = _b.apply(void 0, [(_c.pipeline = _d.sent(),
4777
- _c.tools = tools,
4778
- _c)]);
4779
- _llms = arrayableToArray(tools.llm);
4780
- llmTools = _llms.length === 1 ? _llms[0] : joinLlmExecutionTools.apply(void 0, __spreadArray([], __read(_llms), false));
4781
- return [4 /*yield*/, llmTools.listModels()];
4782
- case 2:
4783
- availableModels = _d.sent();
4784
- availableModelNames = availableModels
4785
- .filter(function (_a) {
4786
- var modelVariant = _a.modelVariant;
4787
- return modelVariant === 'CHAT';
4788
- })
4789
- .map(function (_a) {
4790
- var modelName = _a.modelName;
4791
- return modelName;
4792
- })
4793
- .join(',');
4794
- return [4 /*yield*/, preparePersonaExecutor({ availableModelNames: availableModelNames, personaDescription: personaDescription })];
4795
- case 3:
4796
- result = _d.sent();
4797
- assertsExecutionSuccessful(result);
4798
- outputParameters = result.outputParameters;
4799
- modelRequirementsRaw = outputParameters.modelRequirements;
4800
- modelRequirements = JSON.parse(modelRequirementsRaw);
4801
- if (isVerbose) {
4802
- console.info("PERSONA ".concat(personaDescription), modelRequirements);
4803
- }
4804
- modelName = modelRequirements.modelName, systemMessage = modelRequirements.systemMessage, temperature = modelRequirements.temperature;
4805
- return [2 /*return*/, {
4806
- modelVariant: 'CHAT',
4807
- modelName: modelName,
4808
- systemMessage: systemMessage,
4809
- temperature: temperature,
4810
- }];
4811
- }
4812
- });
4813
- });
4814
- }
4815
- /**
4816
- * TODO: [🔃][main] !! If the persona was prepared with different version or different set of models, prepare it once again
4817
- * TODO: [🏢] !! Check validity of `modelName` in pipeline
4818
- * TODO: [🏢] !! Check validity of `systemMessage` in pipeline
4819
- * TODO: [🏢] !! Check validity of `temperature` in pipeline
4820
- */
4821
-
4822
- /**
4823
- * @@@
4824
- *
4825
- * Note: `$` is used to indicate that this function is not a pure function - it access global scope
4826
- *
4827
- * @private internal function of `$Register`
4828
- */
4829
- function $getGlobalScope() {
4830
- return Function('return this')();
4831
- }
4832
-
4833
- /**
4834
- * @@@
4835
- *
4836
- * @param text @@@
4837
- * @returns @@@
4838
- * @example 'HELLO_WORLD'
4839
- * @example 'I_LOVE_PROMPTBOOK'
4840
- * @public exported from `@promptbook/utils`
4841
- */
4842
- function normalizeTo_SCREAMING_CASE(text) {
4843
- var e_1, _a;
4844
- var charType;
4845
- var lastCharType = 'OTHER';
4846
- var normalizedName = '';
4847
- try {
4848
- for (var text_1 = __values(text), text_1_1 = text_1.next(); !text_1_1.done; text_1_1 = text_1.next()) {
4849
- var char = text_1_1.value;
4850
- var normalizedChar = void 0;
4851
- if (/^[a-z]$/.test(char)) {
4852
- charType = 'LOWERCASE';
4853
- normalizedChar = char.toUpperCase();
4854
- }
4855
- else if (/^[A-Z]$/.test(char)) {
4856
- charType = 'UPPERCASE';
4857
- normalizedChar = char;
4858
- }
4859
- else if (/^[0-9]$/.test(char)) {
4860
- charType = 'NUMBER';
4861
- normalizedChar = char;
4862
- }
4863
- else {
4864
- charType = 'OTHER';
4865
- normalizedChar = '_';
4866
- }
4867
- if (charType !== lastCharType &&
4868
- !(lastCharType === 'UPPERCASE' && charType === 'LOWERCASE') &&
4869
- !(lastCharType === 'NUMBER') &&
4870
- !(charType === 'NUMBER')) {
4871
- normalizedName += '_';
4872
- }
4873
- normalizedName += normalizedChar;
4874
- lastCharType = charType;
4875
- }
4876
- }
4877
- catch (e_1_1) { e_1 = { error: e_1_1 }; }
4878
- finally {
4879
- try {
4880
- if (text_1_1 && !text_1_1.done && (_a = text_1.return)) _a.call(text_1);
4881
- }
4882
- finally { if (e_1) throw e_1.error; }
4883
- }
4884
- normalizedName = normalizedName.replace(/_+/g, '_');
4885
- normalizedName = normalizedName.replace(/_?\/_?/g, '/');
4886
- normalizedName = normalizedName.replace(/^_/, '');
4887
- normalizedName = normalizedName.replace(/_$/, '');
4888
- return normalizedName;
5038
+ return pipelineExecutor;
4889
5039
  }
4890
5040
  /**
4891
- * TODO: Tests
4892
- * > expect(encodeRoutePath({ uriId: 'VtG7sR9rRJqwNEdM2', name: 'Moje tabule' })).toEqual('/VtG7sR9rRJqwNEdM2/Moje tabule');
4893
- * > expect(encodeRoutePath({ uriId: 'VtG7sR9rRJqwNEdM2', name: 'ěščřžžýáíúů' })).toEqual('/VtG7sR9rRJqwNEdM2/escrzyaieuu');
4894
- * > expect(encodeRoutePath({ uriId: 'VtG7sR9rRJqwNEdM2', name: ' ahoj ' })).toEqual('/VtG7sR9rRJqwNEdM2/ahoj');
4895
- * > expect(encodeRoutePath({ uriId: 'VtG7sR9rRJqwNEdM2', name: ' ahoj_ahojAhoj ahoj ' })).toEqual('/VtG7sR9rRJqwNEdM2/ahoj-ahoj-ahoj-ahoj');
4896
- * TODO: [🌺] Use some intermediate util splitWords
5041
+ * TODO: [🐚] Change onProgress to object that represents the running execution, can be subscribed via RxJS to and also awaited
4897
5042
  */
4898
5043
 
4899
5044
  /**
4900
- * @@@
5045
+ * Prepares the persona for the pipeline
4901
5046
  *
4902
- * @param text @@@
4903
- * @returns @@@
4904
- * @example 'hello_world'
4905
- * @example 'i_love_promptbook'
4906
- * @public exported from `@promptbook/utils`
5047
+ * @see https://github.com/webgptorg/promptbook/discussions/22
5048
+ * @public exported from `@promptbook/core`
4907
5049
  */
4908
- function normalizeTo_snake_case(text) {
4909
- return normalizeTo_SCREAMING_CASE(text).toLowerCase();
5050
+ function preparePersona(personaDescription, tools, options) {
5051
+ return __awaiter(this, void 0, void 0, function () {
5052
+ var _a, isVerbose, collection, preparePersonaExecutor, _b, _llms, llmTools, availableModels, availableModelNames, result, outputParameters, modelRequirementsRaw, modelRequirements, modelName, systemMessage, temperature;
5053
+ var _c;
5054
+ return __generator(this, function (_d) {
5055
+ switch (_d.label) {
5056
+ case 0:
5057
+ _a = options.isVerbose, isVerbose = _a === void 0 ? DEFAULT_IS_VERBOSE : _a;
5058
+ if (tools === undefined || tools.llm === undefined) {
5059
+ throw new MissingToolsError('LLM tools are required for preparing persona');
5060
+ }
5061
+ collection = createCollectionFromJson.apply(void 0, __spreadArray([], __read(PipelineCollection), false));
5062
+ _b = createPipelineExecutor;
5063
+ _c = {};
5064
+ return [4 /*yield*/, collection.getPipelineByUrl('https://promptbook.studio/promptbook/prepare-persona.book.md')];
5065
+ case 1:
5066
+ preparePersonaExecutor = _b.apply(void 0, [(_c.pipeline = _d.sent(),
5067
+ _c.tools = tools,
5068
+ _c)]);
5069
+ _llms = arrayableToArray(tools.llm);
5070
+ llmTools = _llms.length === 1 ? _llms[0] : joinLlmExecutionTools.apply(void 0, __spreadArray([], __read(_llms), false));
5071
+ return [4 /*yield*/, llmTools.listModels()];
5072
+ case 2:
5073
+ availableModels = _d.sent();
5074
+ availableModelNames = availableModels
5075
+ .filter(function (_a) {
5076
+ var modelVariant = _a.modelVariant;
5077
+ return modelVariant === 'CHAT';
5078
+ })
5079
+ .map(function (_a) {
5080
+ var modelName = _a.modelName;
5081
+ return modelName;
5082
+ })
5083
+ .join(',');
5084
+ return [4 /*yield*/, preparePersonaExecutor({ availableModelNames: availableModelNames, personaDescription: personaDescription })];
5085
+ case 3:
5086
+ result = _d.sent();
5087
+ assertsExecutionSuccessful(result);
5088
+ outputParameters = result.outputParameters;
5089
+ modelRequirementsRaw = outputParameters.modelRequirements;
5090
+ modelRequirements = JSON.parse(modelRequirementsRaw);
5091
+ if (isVerbose) {
5092
+ console.info("PERSONA ".concat(personaDescription), modelRequirements);
5093
+ }
5094
+ modelName = modelRequirements.modelName, systemMessage = modelRequirements.systemMessage, temperature = modelRequirements.temperature;
5095
+ return [2 /*return*/, {
5096
+ modelVariant: 'CHAT',
5097
+ modelName: modelName,
5098
+ systemMessage: systemMessage,
5099
+ temperature: temperature,
5100
+ }];
5101
+ }
5102
+ });
5103
+ });
4910
5104
  }
4911
-
4912
5105
  /**
4913
- * Register is @@@
4914
- *
4915
- * Note: `$` is used to indicate that this function is not a pure function - it accesses and adds variables in global scope.
4916
- *
4917
- * @private internal utility, exported are only signleton instances of this class
5106
+ * TODO: [🔃][main] !! If the persona was prepared with different version or different set of models, prepare it once again
5107
+ * TODO: [🏢] !! Check validity of `modelName` in pipeline
5108
+ * TODO: [🏢] !! Check validity of `systemMessage` in pipeline
5109
+ * TODO: [🏢] !! Check validity of `temperature` in pipeline
4918
5110
  */
4919
- var $Register = /** @class */ (function () {
4920
- function $Register(registerName) {
4921
- this.registerName = registerName;
4922
- var storageName = "_promptbook_".concat(normalizeTo_snake_case(registerName));
4923
- var globalScope = $getGlobalScope();
4924
- if (globalScope[storageName] === undefined) {
4925
- globalScope[storageName] = [];
4926
- }
4927
- else if (!Array.isArray(globalScope[storageName])) {
4928
- throw new UnexpectedError("Expected (global) ".concat(storageName, " to be an array, but got ").concat(typeof globalScope[storageName]));
4929
- }
4930
- this.storage = globalScope[storageName];
4931
- }
4932
- $Register.prototype.list = function () {
4933
- // <- TODO: ReadonlyDeep<ReadonlyArray<TRegistered>>
4934
- return this.storage;
4935
- };
4936
- $Register.prototype.register = function (registered) {
4937
- var packageName = registered.packageName, className = registered.className;
4938
- var existingRegistrationIndex = this.storage.findIndex(function (item) { return item.packageName === packageName && item.className === className; });
4939
- var existingRegistration = this.storage[existingRegistrationIndex];
4940
- if (!existingRegistration) {
4941
- this.storage.push(registered);
4942
- }
4943
- else {
4944
- this.storage[existingRegistrationIndex] = registered;
4945
- }
4946
- return {
4947
- registerName: this.registerName,
4948
- packageName: packageName,
4949
- className: className,
4950
- get isDestroyed() {
4951
- return false;
4952
- },
4953
- destroy: function () {
4954
- throw new NotYetImplementedError("Registration to ".concat(this.registerName, " is permanent in this version of Promptbook"));
4955
- },
4956
- };
4957
- };
4958
- return $Register;
4959
- }());
4960
5111
 
4961
5112
  /**
4962
5113
  * @@@
@@ -9093,18 +9244,6 @@
9093
9244
  * Note: [🟢] Code in this file should never be never released in packages that could be imported into browser environment
9094
9245
  */
9095
9246
 
9096
- /**
9097
- * @@@
9098
- *
9099
- * Note: `$` is used to indicate that this interacts with the global scope
9100
- * @singleton Only one instance of each register is created per build, but thare can be more @@@
9101
- * @public exported from `@promptbook/core`
9102
- */
9103
- var $llmToolsMetadataRegister = new $Register('llm_tools_metadata');
9104
- /**
9105
- * TODO: [®] DRY Register logic
9106
- */
9107
-
9108
9247
  /**
9109
9248
  * @@@
9110
9249
  *
@@ -9113,6 +9252,7 @@
9113
9252
  * It looks for environment variables:
9114
9253
  * - `process.env.OPENAI_API_KEY`
9115
9254
  * - `process.env.ANTHROPIC_CLAUDE_API_KEY`
9255
+ * - ...
9116
9256
  *
9117
9257
  * @returns @@@
9118
9258
  * @public exported from `@promptbook/node`
@@ -9141,119 +9281,6 @@
9141
9281
  * TODO: [🧠] Maybe pass env as argument
9142
9282
  * TODO: [®] DRY Register logic */
9143
9283
 
9144
- /**
9145
- * @@@
9146
- *
9147
- * Note: `$` is used to indicate that this interacts with the global scope
9148
- * @singleton Only one instance of each register is created per build, but thare can be more @@@
9149
- * @public exported from `@promptbook/core`
9150
- */
9151
- var $llmToolsRegister = new $Register('llm_execution_tools_constructors');
9152
- /**
9153
- * TODO: [®] DRY Register logic
9154
- */
9155
-
9156
- /**
9157
- * Creates a message with all registered LLM tools
9158
- *
9159
- * Note: This function is used to create a (error) message when there is no constructor for some LLM provider
9160
- *
9161
- * @private internal function of `createLlmToolsFromConfiguration` and `$provideLlmToolsFromEnv`
9162
- */
9163
- function $registeredLlmToolsMessage() {
9164
- var e_1, _a, e_2, _b;
9165
- /**
9166
- * Mixes registered LLM tools from $llmToolsMetadataRegister and $llmToolsRegister
9167
- */
9168
- var all = [];
9169
- var _loop_1 = function (packageName, className) {
9170
- if (all.some(function (item) { return item.packageName === packageName && item.className === className; })) {
9171
- return "continue";
9172
- }
9173
- all.push({ packageName: packageName, className: className });
9174
- };
9175
- try {
9176
- for (var _c = __values($llmToolsMetadataRegister.list()), _d = _c.next(); !_d.done; _d = _c.next()) {
9177
- var _e = _d.value, packageName = _e.packageName, className = _e.className;
9178
- _loop_1(packageName, className);
9179
- }
9180
- }
9181
- catch (e_1_1) { e_1 = { error: e_1_1 }; }
9182
- finally {
9183
- try {
9184
- if (_d && !_d.done && (_a = _c.return)) _a.call(_c);
9185
- }
9186
- finally { if (e_1) throw e_1.error; }
9187
- }
9188
- var _loop_2 = function (packageName, className) {
9189
- if (all.some(function (item) { return item.packageName === packageName && item.className === className; })) {
9190
- return "continue";
9191
- }
9192
- all.push({ packageName: packageName, className: className });
9193
- };
9194
- try {
9195
- for (var _f = __values($llmToolsRegister.list()), _g = _f.next(); !_g.done; _g = _f.next()) {
9196
- var _h = _g.value, packageName = _h.packageName, className = _h.className;
9197
- _loop_2(packageName, className);
9198
- }
9199
- }
9200
- catch (e_2_1) { e_2 = { error: e_2_1 }; }
9201
- finally {
9202
- try {
9203
- if (_g && !_g.done && (_b = _f.return)) _b.call(_f);
9204
- }
9205
- finally { if (e_2) throw e_2.error; }
9206
- }
9207
- var metadata = all.map(function (metadata) {
9208
- var isMetadataAviailable = $llmToolsMetadataRegister
9209
- .list()
9210
- .find(function (_a) {
9211
- var packageName = _a.packageName, className = _a.className;
9212
- return metadata.packageName === packageName && metadata.className === className;
9213
- });
9214
- var isInstalled = $llmToolsRegister
9215
- .list()
9216
- .find(function (_a) {
9217
- var packageName = _a.packageName, className = _a.className;
9218
- return metadata.packageName === packageName && metadata.className === className;
9219
- });
9220
- return __assign(__assign({}, metadata), { isMetadataAviailable: isMetadataAviailable, isInstalled: isInstalled });
9221
- });
9222
- if (metadata.length === 0) {
9223
- return "No LLM providers are available.";
9224
- }
9225
- return spaceTrim__default["default"](function (block) { return "\n Available LLM providers are:\n ".concat(block(metadata
9226
- .map(function (_a, i) {
9227
- var packageName = _a.packageName, className = _a.className, isMetadataAviailable = _a.isMetadataAviailable, isInstalled = _a.isInstalled;
9228
- var more;
9229
- if (just(false)) {
9230
- more = '';
9231
- }
9232
- else if (!isMetadataAviailable && !isInstalled) {
9233
- // TODO: [�][�] Maybe do allow to do auto-install if package not registered and not found
9234
- more = "(not installed and no metadata, looks like a unexpected behavior)";
9235
- }
9236
- else if (isMetadataAviailable && !isInstalled) {
9237
- // TODO: [�][�]
9238
- more = "(not installed)";
9239
- }
9240
- else if (!isMetadataAviailable && isInstalled) {
9241
- more = "(no metadata, looks like a unexpected behavior)";
9242
- }
9243
- else if (isMetadataAviailable && isInstalled) {
9244
- more = "(installed)";
9245
- }
9246
- else {
9247
- more = "(unknown state, looks like a unexpected behavior)";
9248
- }
9249
- return "".concat(i + 1, ") `").concat(className, "` from `").concat(packageName, "` ").concat(more);
9250
- })
9251
- .join('\n')), "\n "); });
9252
- }
9253
- /**
9254
- * TODO: [®] DRY Register logic
9255
- */
9256
-
9257
9284
  /**
9258
9285
  * @@@
9259
9286
  *
@@ -9299,6 +9326,7 @@
9299
9326
  * It looks for environment variables:
9300
9327
  * - `process.env.OPENAI_API_KEY`
9301
9328
  * - `process.env.ANTHROPIC_CLAUDE_API_KEY`
9329
+ * - ...
9302
9330
  *
9303
9331
  * @returns @@@
9304
9332
  * @public exported from `@promptbook/node`
@@ -11559,7 +11587,13 @@
11559
11587
  if (!error.message.includes('No LLM tools')) {
11560
11588
  throw error;
11561
11589
  }
11562
- console.error(colors__default["default"].red(spaceTrim__default["default"]("\n You need to configure LLM tools first\n\n 1) Create .env file\n 2) Add OPENAI_API_KEY=...\n 3) *(and/or)* Add ANTHROPIC_CLAUDE_API_KEY=...\n ")));
11590
+ console.error(colors__default["default"].red(spaceTrim__default["default"](function (block) { return "\n You need to configure LLM tools first\n\n \n 1) Create .env file at the root of your project\n 2) Configure API keys for LLM tools\n \n For example:\n ".concat(block($llmToolsMetadataRegister
11591
+ .list()
11592
+ .map(function (_a) {
11593
+ var title = _a.title, envVariables = _a.envVariables;
11594
+ return "- ".concat(envVariables.join(' + '), " (").concat(title, ")");
11595
+ })
11596
+ .join('\n')), "\n "); })));
11563
11597
  return [2 /*return*/, process.exit(1)];
11564
11598
  }
11565
11599
  return [4 /*yield*/, $provideExecutablesForNode(prepareAndScrapeOptions)];
@@ -11938,6 +11972,7 @@
11938
11972
  initializeMakeCommand(program);
11939
11973
  initializePrettifyCommand(program);
11940
11974
  initializeTestCommand(program);
11975
+ initializeListModelsCommand(program);
11941
11976
  program.parse(process.argv);
11942
11977
  return [2 /*return*/];
11943
11978
  });
@@ -11980,6 +12015,7 @@
11980
12015
  title: 'Anthropic Claude',
11981
12016
  packageName: '@promptbook/anthropic-claude',
11982
12017
  className: 'AnthropicClaudeExecutionTools',
12018
+ envVariables: ['ANTHROPIC_CLAUDE_API_KEY'],
11983
12019
  getBoilerplateConfiguration: function () {
11984
12020
  return {
11985
12021
  title: 'Anthropic Claude (boilerplate)',
@@ -12699,6 +12735,7 @@
12699
12735
  title: 'Azure Open AI',
12700
12736
  packageName: '@promptbook/azure-openai',
12701
12737
  className: 'AzureOpenAiExecutionTools',
12738
+ envVariables: ['AZUREOPENAI_RESOURCE_NAME', 'AZUREOPENAI_DEPLOYMENT_NAME', 'AZUREOPENAI_API_KEY'],
12702
12739
  getBoilerplateConfiguration: function () {
12703
12740
  return {
12704
12741
  title: 'Azure Open AI (boilerplate)',
@@ -13478,6 +13515,15 @@
13478
13515
  * Note: [💞] Ignore a discrepancy between file name and entity name
13479
13516
  */
13480
13517
 
13518
+ /**
13519
+ * Detects if the code is running in jest environment
13520
+ *
13521
+ * Note: `$` is used to indicate that this function is not a pure function - it looks at the global object to determine the environment
13522
+ *
13523
+ * @public exported from `@promptbook/utils`
13524
+ */
13525
+ var $isRunningInJest = new Function("\n try {\n return process.env.JEST_WORKER_ID !== undefined;\n } catch (e) {\n return false;\n }\n");
13526
+
13481
13527
  /**
13482
13528
  * Registration of LLM provider metadata
13483
13529
  *
@@ -13490,6 +13536,7 @@
13490
13536
  title: 'Google Gemini',
13491
13537
  packageName: '@promptbook/google',
13492
13538
  className: 'GoogleExecutionTools',
13539
+ envVariables: ['GOOGLE_GENERATIVE_AI_API_KEY'],
13493
13540
  getBoilerplateConfiguration: function () {
13494
13541
  return {
13495
13542
  title: 'Google Gemini (boilerplate)',
@@ -13504,14 +13551,20 @@
13504
13551
  };
13505
13552
  },
13506
13553
  createConfigurationFromEnv: function (env) {
13554
+ if ($isRunningInJest()
13555
+ // <- TODO: Maybe check `env.JEST_WORKER_ID` directly here or pass `env` into `$isRunningInJest`
13556
+ ) {
13557
+ // Note: [🔘] Gemini makes problems in Jest environment
13558
+ return null;
13559
+ }
13507
13560
  // Note: Note using `process.env` BUT `env` to pass in the environment variables dynamically
13508
- if (typeof env.GOOGLE_GEMINI_API_KEY === 'string') {
13561
+ if (typeof env.GOOGLE_GENERATIVE_AI_API_KEY === 'string') {
13509
13562
  return {
13510
13563
  title: 'Google Gemini (from env)',
13511
13564
  packageName: '@promptbook/google',
13512
13565
  className: 'GoogleExecutionTools',
13513
13566
  options: {
13514
- apiKey: env.GOOGLE_GEMINI_API_KEY,
13567
+ apiKey: env.GOOGLE_GENERATIVE_AI_API_KEY,
13515
13568
  },
13516
13569
  };
13517
13570
  }
@@ -13646,6 +13699,10 @@
13646
13699
  * @public exported from `@promptbook/google`
13647
13700
  */
13648
13701
  var createGoogleExecutionTools = Object.assign(function (options) {
13702
+ if ($isRunningInJest()) {
13703
+ // Note: [🔘]
13704
+ throw new Error('GoogleExecutionTools are not supported in Jest environment');
13705
+ }
13649
13706
  // Note: [🔘] There is a compatibility when using import from '@ai-sdk/google'
13650
13707
  // eslint-disable-next-line @typescript-eslint/no-var-requires
13651
13708
  var createGoogleGenerativeAI = require('@ai-sdk/google').createGoogleGenerativeAI;
@@ -13706,6 +13763,7 @@
13706
13763
  title: 'Open AI',
13707
13764
  packageName: '@promptbook/openai',
13708
13765
  className: 'OpenAiExecutionTools',
13766
+ envVariables: ['OPENAI_API_KEY'],
13709
13767
  getBoilerplateConfiguration: function () {
13710
13768
  return {
13711
13769
  title: 'Open AI (boilerplate)',
@@ -13743,6 +13801,9 @@
13743
13801
  title: 'Open AI Assistant',
13744
13802
  packageName: '@promptbook/openai',
13745
13803
  className: 'OpenAiAssistantExecutionTools',
13804
+ envVariables: [
13805
+ /* TODO: 'OPENAI_API_KEY', 'OPENAI_ASSISTANT_ID' */
13806
+ ],
13746
13807
  getBoilerplateConfiguration: function () {
13747
13808
  return {
13748
13809
  title: 'Open AI Assistant (boilerplate)',