@promptbook/cli 0.112.0-115 → 0.112.0-118
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/apps/agents-server/src/app/agents/[agentName]/chat/AgentChatSidebarDefault.tsx +5 -6
- package/apps/agents-server/src/utils/externalChatRunner/processExternalUserChatJob.ts +17 -7
- package/apps/agents-server/src/utils/localChatRunner/processLocalUserChatJob.ts +17 -7
- package/apps/agents-server/src/utils/userChat/createImmediateUserChatAnswerModelRequirements.ts +11 -0
- package/apps/agents-server/src/utils/userChat/listUserChats.ts +5 -7
- package/esm/index.es.js +451 -95
- package/esm/index.es.js.map +1 -1
- package/esm/scripts/run-codex-prompts/common/parseDuration.d.ts +19 -0
- package/esm/src/_packages/components.index.d.ts +2 -0
- package/esm/src/_packages/node.index.d.ts +20 -0
- package/esm/src/book-3.0/BookNodeAgentSource.d.ts +1 -1
- package/esm/src/book-3.0/CliAgent.d.ts +15 -17
- package/esm/src/book-3.0/agentFolderPaths.d.ts +30 -0
- package/esm/src/book-3.0/cliAgentEnv.d.ts +33 -0
- package/esm/src/book-components/BookEditor/BookEditorBrowserConfig.d.ts +2 -0
- package/esm/src/book-components/BookEditor/BookEditorForClient.d.ts +7 -0
- package/esm/src/book-components/BookEditor/createDeprecatedCommitmentDiagnostics.browser.d.ts +9 -0
- package/esm/src/cli/cli-commands/agent-folder/agentProjectPaths.d.ts +2 -30
- package/esm/src/cli/cli-commands/common/promptRunnerCliOptions.d.ts +2 -18
- package/esm/src/scrapers/website/utils/createShowdownConverter.d.ts +2 -2
- package/esm/src/version.d.ts +1 -1
- package/package.json +1 -1
- package/src/_packages/components.index.ts +2 -0
- package/src/_packages/node.index.ts +20 -0
- package/src/avatars/avatarAnimationScheduler.ts +33 -2
- package/src/avatars/visuals/fractalAvatarVisual.ts +5 -4
- package/src/avatars/visuals/minecraft2AvatarVisual.ts +16 -11
- package/src/avatars/visuals/minecraftAvatarVisual.ts +21 -7
- package/src/avatars/visuals/octopus3d2AvatarVisual.ts +69 -17
- package/src/avatars/visuals/octopus3d3AvatarVisual.ts +81 -18
- package/src/avatars/visuals/octopus3dAvatarVisual.ts +69 -17
- package/src/book-3.0/Book.ts +3 -1
- package/src/book-3.0/BookNodeAgentSource.ts +2 -2
- package/src/book-3.0/CliAgent.ts +87 -71
- package/src/book-3.0/agentFolderPaths.ts +38 -0
- package/src/book-3.0/cliAgentEnv.ts +46 -0
- package/src/book-components/BookEditor/BookEditor.tsx +1 -1
- package/src/book-components/BookEditor/BookEditorAboutPromptbookInformation.tsx +2 -4
- package/src/book-components/BookEditor/BookEditorActionbar.tsx +32 -2
- package/src/book-components/BookEditor/BookEditorBrowserConfig.ts +11 -0
- package/src/book-components/BookEditor/BookEditorForClient.tsx +33 -0
- package/src/book-components/BookEditor/BookEditorMonaco.tsx +1 -1
- package/src/book-components/BookEditor/BookEditorMonacoTokenization.ts +83 -15
- package/src/book-components/BookEditor/createDeprecatedCommitmentDiagnostics.browser.ts +11 -0
- package/src/book-components/BookEditor/useBookEditorMonacoLanguage.ts +32 -46
- package/src/book-components/BookEditor/useBookEditorMonacoStyles.ts +1 -1
- package/src/book-components/BookEditor/useBookEditorMonacoUploads.ts +1 -1
- package/src/book-components/Chat/utils/renderMarkdown.ts +3 -2
- package/src/cli/cli-commands/agent-folder/agentProjectPaths.ts +15 -35
- package/src/cli/cli-commands/coder/run.ts +28 -3
- package/src/cli/cli-commands/common/promptRunnerCliOptions.ts +9 -29
- package/src/commands/KNOWLEDGE/utils/knowledgeSourceContentToName.ts +2 -2
- package/src/commitments/_common/teamInternalAgentAccess.ts +2 -2
- package/src/formats/csv/CsvFormatParser.ts +4 -4
- package/src/formats/csv/utils/csvParse.ts +2 -2
- package/src/llm-providers/agent/AgentLlmExecutionTools.ts +2 -2
- package/src/llm-providers/agent/AgentLlmExecutionToolsAgentKitRunner.ts +2 -2
- package/src/llm-providers/agent/AgentLlmExecutionToolsOpenAiAssistantRunner.ts +2 -2
- package/src/other/templates/getTemplatesPipelineCollection.ts +712 -807
- package/src/scrapers/_common/utils/getScraperIntermediateSource.ts +2 -2
- package/src/scrapers/website/WebsiteScraper.ts +1 -1
- package/src/scrapers/website/utils/createShowdownConverter.ts +2 -2
- package/src/utils/misc/computeHash.ts +2 -2
- package/src/utils/random/$randomToken.ts +2 -2
- package/src/version.ts +2 -2
- package/src/versions.txt +3 -0
- package/umd/index.umd.js +453 -94
- package/umd/index.umd.js.map +1 -1
- package/umd/scripts/run-codex-prompts/common/parseDuration.d.ts +19 -0
- package/umd/src/_packages/components.index.d.ts +2 -0
- package/umd/src/_packages/node.index.d.ts +20 -0
- package/umd/src/book-3.0/BookNodeAgentSource.d.ts +1 -1
- package/umd/src/book-3.0/CliAgent.d.ts +15 -17
- package/umd/src/book-3.0/agentFolderPaths.d.ts +30 -0
- package/umd/src/book-3.0/cliAgentEnv.d.ts +33 -0
- package/umd/src/book-components/BookEditor/BookEditorBrowserConfig.d.ts +2 -0
- package/umd/src/book-components/BookEditor/BookEditorForClient.d.ts +7 -0
- package/umd/src/book-components/BookEditor/createDeprecatedCommitmentDiagnostics.browser.d.ts +9 -0
- package/umd/src/cli/cli-commands/agent-folder/agentProjectPaths.d.ts +2 -30
- package/umd/src/cli/cli-commands/common/promptRunnerCliOptions.d.ts +2 -18
- package/umd/src/scrapers/website/utils/createShowdownConverter.d.ts +2 -2
- package/umd/src/version.d.ts +1 -1
package/esm/index.es.js
CHANGED
|
@@ -17,8 +17,8 @@ import { io } from 'socket.io-client';
|
|
|
17
17
|
import JSZip from 'jszip';
|
|
18
18
|
import { Readability } from '@mozilla/readability';
|
|
19
19
|
import { JSDOM } from 'jsdom';
|
|
20
|
-
import
|
|
21
|
-
import
|
|
20
|
+
import CryptoJS from 'crypto-js';
|
|
21
|
+
import showdown from 'showdown';
|
|
22
22
|
import glob from 'glob-promise';
|
|
23
23
|
import http from 'http';
|
|
24
24
|
import express from 'express';
|
|
@@ -32,7 +32,7 @@ import Bottleneck from 'bottleneck';
|
|
|
32
32
|
import { OpenAIClient, AzureKeyCredential } from '@azure/openai';
|
|
33
33
|
import { Subject, BehaviorSubject } from 'rxjs';
|
|
34
34
|
import { lookup, extension } from 'mime-types';
|
|
35
|
-
import
|
|
35
|
+
import papaparse from 'papaparse';
|
|
36
36
|
import { fileSearchTool, tool, Agent as Agent$1, webSearchTool, run, setDefaultOpenAIClient, setDefaultOpenAIKey } from '@openai/agents';
|
|
37
37
|
import OpenAI from 'openai';
|
|
38
38
|
import * as ts from 'typescript';
|
|
@@ -58,7 +58,7 @@ const BOOK_LANGUAGE_VERSION = '2.0.0';
|
|
|
58
58
|
* @generated
|
|
59
59
|
* @see https://github.com/webgptorg/promptbook
|
|
60
60
|
*/
|
|
61
|
-
const PROMPTBOOK_ENGINE_VERSION = '0.112.0-
|
|
61
|
+
const PROMPTBOOK_ENGINE_VERSION = '0.112.0-118';
|
|
62
62
|
/**
|
|
63
63
|
* TODO: string_promptbook_version should be constrained to the all versions of Promptbook engine
|
|
64
64
|
* Note: [💞] Ignore a discrepancy between file name and entity name
|
|
@@ -1740,12 +1740,13 @@ function parseThinkingLevel(thinkingLevelValue) {
|
|
|
1740
1740
|
}
|
|
1741
1741
|
// Note: [🟡] Code for CLI command [run](src/cli/cli-commands/coder/run.ts) should never be published outside of `@promptbook/cli`
|
|
1742
1742
|
|
|
1743
|
+
// Note: [💞] Ignore a discrepancy between file name and entity name
|
|
1743
1744
|
/**
|
|
1744
|
-
*
|
|
1745
|
+
* All CLI harness names supported by `CliAgent` and `ptbk agent exec`.
|
|
1745
1746
|
*
|
|
1746
|
-
* @
|
|
1747
|
+
* @public exported from `@promptbook/node`
|
|
1747
1748
|
*/
|
|
1748
|
-
const
|
|
1749
|
+
const CLI_AGENT_HARNESS_NAMES = [
|
|
1749
1750
|
'openai-codex',
|
|
1750
1751
|
'github-copilot',
|
|
1751
1752
|
'cline',
|
|
@@ -1754,23 +1755,33 @@ const PROMPT_RUNNER_HARNESS_NAMES = [
|
|
|
1754
1755
|
'gemini',
|
|
1755
1756
|
];
|
|
1756
1757
|
/**
|
|
1757
|
-
* Environment variable used as the default runner identifier when `--harness` is omitted
|
|
1758
|
+
* Environment variable used as the default runner identifier when `--harness` is omitted or not set in `CliAgent`.
|
|
1758
1759
|
*
|
|
1759
|
-
*
|
|
1760
|
+
* Set this to one of the harness names (`openai-codex`, `github-copilot`, `cline`, `claude-code`, `opencode`, `gemini`)
|
|
1761
|
+
* so that `CliAgent` and `ptbk agent exec` can run without an explicit `harness` option.
|
|
1762
|
+
*
|
|
1763
|
+
* @public exported from `@promptbook/node`
|
|
1760
1764
|
*/
|
|
1761
1765
|
const PTBK_HARNESS_ENV = 'PTBK_HARNESS';
|
|
1762
1766
|
/**
|
|
1763
|
-
* Environment variable used as the default runner model when `--model` is omitted
|
|
1767
|
+
* Environment variable used as the default runner model when `--model` is omitted or not set in `CliAgent`.
|
|
1764
1768
|
*
|
|
1765
|
-
* @
|
|
1769
|
+
* @public exported from `@promptbook/node`
|
|
1766
1770
|
*/
|
|
1767
1771
|
const PTBK_MODEL_ENV = 'PTBK_MODEL';
|
|
1768
1772
|
/**
|
|
1769
|
-
* Environment variable used as the default
|
|
1773
|
+
* Environment variable used as the default thinking level when `--thinking-level` is omitted or not set in `CliAgent`.
|
|
1770
1774
|
*
|
|
1771
|
-
* @
|
|
1775
|
+
* @public exported from `@promptbook/node`
|
|
1772
1776
|
*/
|
|
1773
1777
|
const PTBK_THINKING_LEVEL_ENV = 'PTBK_THINKING_LEVEL';
|
|
1778
|
+
|
|
1779
|
+
/**
|
|
1780
|
+
* Runner identifiers supported by Promptbook CLI agent orchestration commands.
|
|
1781
|
+
*
|
|
1782
|
+
* @private internal utility of `promptbookCli`
|
|
1783
|
+
*/
|
|
1784
|
+
const PROMPT_RUNNER_HARNESS_NAMES = CLI_AGENT_HARNESS_NAMES;
|
|
1774
1785
|
/**
|
|
1775
1786
|
* Description block shared by runner-backed CLI commands.
|
|
1776
1787
|
*
|
|
@@ -2054,42 +2065,44 @@ function $initializeAgentCommand(program) {
|
|
|
2054
2065
|
// Note: [🟡] Code for CLI command [agent](src/cli/cli-commands/agent.ts) should never be published outside of `@promptbook/cli`
|
|
2055
2066
|
// Note: [💞] Ignore a discrepancy between file name and entity name
|
|
2056
2067
|
|
|
2068
|
+
// Note: [💞] Ignore a discrepancy between file name and entity name
|
|
2057
2069
|
/**
|
|
2058
|
-
* Relative path to the local agent source
|
|
2070
|
+
* Relative path to the local agent source used by the agent folder convention.
|
|
2059
2071
|
*
|
|
2060
|
-
* @
|
|
2072
|
+
* @public exported from `@promptbook/node`
|
|
2061
2073
|
*/
|
|
2062
2074
|
const AGENT_BOOK_FILE_PATH = 'agent.book';
|
|
2063
2075
|
/**
|
|
2064
|
-
* Relative path to
|
|
2076
|
+
* Relative path to the message queue root used by the agent folder convention.
|
|
2065
2077
|
*
|
|
2066
|
-
* @
|
|
2067
|
-
*/
|
|
2068
|
-
const AGENT_KNOWLEDGE_DIRECTORY_PATH = 'knowledge';
|
|
2069
|
-
/**
|
|
2070
|
-
* Relative path to the message queue root initialized by `ptbk agent-folder init`.
|
|
2071
|
-
*
|
|
2072
|
-
* @private internal utility of `ptbk agent-folder`
|
|
2078
|
+
* @public exported from `@promptbook/node`
|
|
2073
2079
|
*/
|
|
2074
2080
|
const AGENT_MESSAGES_DIRECTORY_PATH = 'messages';
|
|
2075
2081
|
/**
|
|
2076
|
-
* Relative path to queued user messages consumed by
|
|
2082
|
+
* Relative path to queued user messages consumed by the agent runner.
|
|
2077
2083
|
*
|
|
2078
|
-
* @
|
|
2084
|
+
* @public exported from `@promptbook/node`
|
|
2079
2085
|
*/
|
|
2080
2086
|
const AGENT_QUEUED_MESSAGES_DIRECTORY_PATH = join(AGENT_MESSAGES_DIRECTORY_PATH, 'queued');
|
|
2081
2087
|
/**
|
|
2082
|
-
* Relative path to answered messages written by
|
|
2088
|
+
* Relative path to answered messages written by the agent runner.
|
|
2083
2089
|
*
|
|
2084
|
-
* @
|
|
2090
|
+
* @public exported from `@promptbook/node`
|
|
2085
2091
|
*/
|
|
2086
2092
|
const AGENT_FINISHED_MESSAGES_DIRECTORY_PATH = join(AGENT_MESSAGES_DIRECTORY_PATH, 'finished');
|
|
2087
2093
|
/**
|
|
2088
2094
|
* Relative path to messages that the agent runner stopped retrying.
|
|
2089
2095
|
*
|
|
2090
|
-
* @
|
|
2096
|
+
* @public exported from `@promptbook/node`
|
|
2091
2097
|
*/
|
|
2092
2098
|
const AGENT_FAILED_MESSAGES_DIRECTORY_PATH = join(AGENT_MESSAGES_DIRECTORY_PATH, 'failed');
|
|
2099
|
+
|
|
2100
|
+
/**
|
|
2101
|
+
* Relative path to local knowledge files initialized by `ptbk agent-folder init`.
|
|
2102
|
+
*
|
|
2103
|
+
* @private internal utility of `ptbk agent-folder`
|
|
2104
|
+
*/
|
|
2105
|
+
const AGENT_KNOWLEDGE_DIRECTORY_PATH = 'knowledge';
|
|
2093
2106
|
/**
|
|
2094
2107
|
* Relative path to generated local agent documentation initialized by `ptbk agent-folder init`.
|
|
2095
2108
|
*
|
|
@@ -5122,6 +5135,7 @@ function createCoderRunOptionsForAgent(options) {
|
|
|
5122
5135
|
noUi: options.noUi,
|
|
5123
5136
|
thinkingLevel: options.thinkingLevel,
|
|
5124
5137
|
waitForUser: false,
|
|
5138
|
+
waitBetweenPrompts: 0,
|
|
5125
5139
|
noCommit: options.noCommit,
|
|
5126
5140
|
ignoreGitChanges: options.ignoreGitChanges,
|
|
5127
5141
|
normalizeLineEndings: options.normalizeLineEndings,
|
|
@@ -6109,7 +6123,7 @@ function valueToString(value) {
|
|
|
6109
6123
|
* @public exported from `@promptbook/utils`
|
|
6110
6124
|
*/
|
|
6111
6125
|
function computeHash(value) {
|
|
6112
|
-
return SHA256(hexEncoder.parse(spaceTrim$1(valueToString(value)))).toString( /* hex */);
|
|
6126
|
+
return CryptoJS.SHA256(hexEncoder.parse(spaceTrim$1(valueToString(value)))).toString( /* hex */);
|
|
6113
6127
|
}
|
|
6114
6128
|
// TODO: [🥬][🥬] Use this ACRY
|
|
6115
6129
|
|
|
@@ -10814,21 +10828,22 @@ function getPointBounds(points) {
|
|
|
10814
10828
|
* @private helper of `fractalAvatarVisual`
|
|
10815
10829
|
*/
|
|
10816
10830
|
function drawDragonCurveLayer(context, points, options) {
|
|
10817
|
-
const {
|
|
10831
|
+
const { primaryColor, secondaryColor, tertiaryColor, shadowColor, strokeWidth, timeMs, layerIndex } = options;
|
|
10818
10832
|
const firstPoint = points[0];
|
|
10819
10833
|
const lastPoint = points[points.length - 1];
|
|
10820
10834
|
const ribbonGradient = context.createLinearGradient(firstPoint.x, firstPoint.y, lastPoint.x, lastPoint.y);
|
|
10821
10835
|
ribbonGradient.addColorStop(0, `${primaryColor}f2`);
|
|
10822
10836
|
ribbonGradient.addColorStop(0.5, `${secondaryColor}e6`);
|
|
10823
10837
|
ribbonGradient.addColorStop(1, `${tertiaryColor}f2`);
|
|
10838
|
+
// Approximate the blurred shadow stroke with a wider semi-transparent stroke instead of
|
|
10839
|
+
// context.filter blur, which triggers a costly software rasterization pass every frame.
|
|
10824
10840
|
context.save();
|
|
10825
10841
|
context.beginPath();
|
|
10826
10842
|
tracePolyline(context, points);
|
|
10827
|
-
context.strokeStyle = `${shadowColor}
|
|
10828
|
-
context.lineWidth = strokeWidth *
|
|
10843
|
+
context.strokeStyle = `${shadowColor}48`;
|
|
10844
|
+
context.lineWidth = strokeWidth * 4.5;
|
|
10829
10845
|
context.lineJoin = 'round';
|
|
10830
10846
|
context.lineCap = 'round';
|
|
10831
|
-
context.filter = `blur(${size * 0.022}px)`;
|
|
10832
10847
|
context.stroke();
|
|
10833
10848
|
context.restore();
|
|
10834
10849
|
context.beginPath();
|
|
@@ -11412,11 +11427,23 @@ function drawMinecraftBackdrop(context, size, palette, sceneCenterX, spotlightY,
|
|
|
11412
11427
|
* @private helper of `minecraft2AvatarVisual`
|
|
11413
11428
|
*/
|
|
11414
11429
|
function drawMinecraftShadow(context, size, palette, interaction, timeMs) {
|
|
11430
|
+
const cx = size * 0.5 + interaction.gazeX * size * 0.03;
|
|
11431
|
+
const cy = size * 0.85 + Math.sin(timeMs / 880) * size * 0.01;
|
|
11432
|
+
const rx = size * (0.16 + interaction.intensity * 0.015);
|
|
11433
|
+
const ry = size * 0.055;
|
|
11434
|
+
// Radial gradient approximates the blurry ellipse shadow without context.filter blur.
|
|
11415
11435
|
context.save();
|
|
11416
|
-
context.
|
|
11417
|
-
context.
|
|
11436
|
+
context.translate(cx, cy);
|
|
11437
|
+
context.scale(1, ry / rx);
|
|
11438
|
+
const blurRadius = rx * 1.4;
|
|
11439
|
+
const shadowGradient = context.createRadialGradient(0, 0, 0, 0, 0, blurRadius);
|
|
11440
|
+
shadowGradient.addColorStop(0, `${palette.shadow}7a`);
|
|
11441
|
+
shadowGradient.addColorStop(0.45, `${palette.shadow}44`);
|
|
11442
|
+
shadowGradient.addColorStop(0.8, `${palette.shadow}1a`);
|
|
11443
|
+
shadowGradient.addColorStop(1, `${palette.shadow}00`);
|
|
11444
|
+
context.fillStyle = shadowGradient;
|
|
11418
11445
|
context.beginPath();
|
|
11419
|
-
context.
|
|
11446
|
+
context.arc(0, 0, blurRadius, 0, Math.PI * 2);
|
|
11420
11447
|
context.fill();
|
|
11421
11448
|
context.restore();
|
|
11422
11449
|
}
|
|
@@ -11640,13 +11667,27 @@ const minecraftAvatarVisual = {
|
|
|
11640
11667
|
spotlight.addColorStop(1, `${palette.highlight}00`);
|
|
11641
11668
|
context.fillStyle = spotlight;
|
|
11642
11669
|
context.fillRect(0, 0, size, size);
|
|
11643
|
-
|
|
11644
|
-
|
|
11645
|
-
|
|
11646
|
-
|
|
11647
|
-
|
|
11648
|
-
|
|
11649
|
-
|
|
11670
|
+
{
|
|
11671
|
+
// Radial gradient approximates the blurry ellipse shadow without context.filter blur.
|
|
11672
|
+
const cx = size * 0.5;
|
|
11673
|
+
const cy = size * 0.86;
|
|
11674
|
+
const rx = size * 0.2;
|
|
11675
|
+
const ry = size * 0.06;
|
|
11676
|
+
const blurRadius = rx * 1.4;
|
|
11677
|
+
const shadowGradient = context.createRadialGradient(0, 0, 0, 0, 0, blurRadius);
|
|
11678
|
+
shadowGradient.addColorStop(0, 'rgba(0,0,0,0.28)');
|
|
11679
|
+
shadowGradient.addColorStop(0.45, 'rgba(0,0,0,0.14)');
|
|
11680
|
+
shadowGradient.addColorStop(0.8, 'rgba(0,0,0,0.05)');
|
|
11681
|
+
shadowGradient.addColorStop(1, 'rgba(0,0,0,0)');
|
|
11682
|
+
context.save();
|
|
11683
|
+
context.translate(cx, cy);
|
|
11684
|
+
context.scale(1, ry / rx);
|
|
11685
|
+
context.fillStyle = shadowGradient;
|
|
11686
|
+
context.beginPath();
|
|
11687
|
+
context.arc(0, 0, blurRadius, 0, Math.PI * 2);
|
|
11688
|
+
context.fill();
|
|
11689
|
+
context.restore();
|
|
11690
|
+
}
|
|
11650
11691
|
drawVoxelCuboid(context, {
|
|
11651
11692
|
x: bodyX,
|
|
11652
11693
|
y: bodyY,
|
|
@@ -12698,6 +12739,35 @@ const LIGHT_DIRECTION$2 = normalizeVector3({
|
|
|
12698
12739
|
y: -0.62,
|
|
12699
12740
|
z: 0.94,
|
|
12700
12741
|
});
|
|
12742
|
+
/**
|
|
12743
|
+
* Cache keyed by the `createRandom` factory reference (stable per mounted `<Avatar/>`).
|
|
12744
|
+
*
|
|
12745
|
+
* @private helper of `octopus3dAvatarVisual`
|
|
12746
|
+
*/
|
|
12747
|
+
const octopus3dStableStateCache = new WeakMap();
|
|
12748
|
+
/**
|
|
12749
|
+
* Returns the stable per-avatar state, computing it on first access and caching for subsequent frames.
|
|
12750
|
+
*
|
|
12751
|
+
* @private helper of `octopus3dAvatarVisual`
|
|
12752
|
+
*/
|
|
12753
|
+
function getOctopus3dStableState(createRandom) {
|
|
12754
|
+
const cached = octopus3dStableStateCache.get(createRandom);
|
|
12755
|
+
if (cached !== undefined) {
|
|
12756
|
+
return cached;
|
|
12757
|
+
}
|
|
12758
|
+
const animationRandom = createRandom('octopus3d-animation-profile');
|
|
12759
|
+
const eyeRandom = createRandom('octopus3d-eye-profile');
|
|
12760
|
+
const leftEyePhaseOffset = eyeRandom() * 0.6;
|
|
12761
|
+
const rightEyePhaseOffset = eyeRandom() * 0.6;
|
|
12762
|
+
const state = {
|
|
12763
|
+
morphologyProfile: createOctopus3MorphologyProfile(createRandom),
|
|
12764
|
+
animationPhase: animationRandom() * Math.PI * 2,
|
|
12765
|
+
leftEyePhaseOffset,
|
|
12766
|
+
rightEyePhaseOffset,
|
|
12767
|
+
};
|
|
12768
|
+
octopus3dStableStateCache.set(createRandom, state);
|
|
12769
|
+
return state;
|
|
12770
|
+
}
|
|
12701
12771
|
/**
|
|
12702
12772
|
* Proper 3D Octopus visual built from projected organic meshes and tentacles.
|
|
12703
12773
|
*
|
|
@@ -12710,10 +12780,7 @@ const octopus3dAvatarVisual = {
|
|
|
12710
12780
|
isAnimated: true,
|
|
12711
12781
|
supportsPointerTracking: true,
|
|
12712
12782
|
render({ context, size, palette, createRandom, timeMs, interaction }) {
|
|
12713
|
-
const morphologyProfile =
|
|
12714
|
-
const animationRandom = createRandom('octopus3d-animation-profile');
|
|
12715
|
-
const eyeRandom = createRandom('octopus3d-eye-profile');
|
|
12716
|
-
const animationPhase = animationRandom() * Math.PI * 2;
|
|
12783
|
+
const { morphologyProfile, animationPhase, leftEyePhaseOffset, rightEyePhaseOffset } = getOctopus3dStableState(createRandom);
|
|
12717
12784
|
const sceneCenterX = size * 0.5;
|
|
12718
12785
|
const sceneCenterY = size * 0.56;
|
|
12719
12786
|
const bob = Math.sin(timeMs / 920 + animationPhase) * size * 0.014;
|
|
@@ -12810,12 +12877,12 @@ const octopus3dAvatarVisual = {
|
|
|
12810
12877
|
x: -faceEyeSpacing,
|
|
12811
12878
|
y: faceEyeYOffset,
|
|
12812
12879
|
z: resolveEllipsoidSurfaceDepth(mantleRadiusX, mantleRadiusY, mantleRadiusZ, -faceEyeSpacing, faceEyeYOffset),
|
|
12813
|
-
}, faceEyeRadiusX, faceEyeRadiusY, mantleCenter, headPitch, headYaw, sceneCenterX, sceneCenterY, size, palette, timeMs, animationPhase +
|
|
12880
|
+
}, faceEyeRadiusX, faceEyeRadiusY, mantleCenter, headPitch, headYaw, sceneCenterX, sceneCenterY, size, palette, timeMs, animationPhase + leftEyePhaseOffset, interaction, morphologyProfile.face.eyeStyle);
|
|
12814
12881
|
drawProjectedOrganicEye(context, {
|
|
12815
12882
|
x: faceEyeSpacing,
|
|
12816
12883
|
y: faceEyeYOffset,
|
|
12817
12884
|
z: resolveEllipsoidSurfaceDepth(mantleRadiusX, mantleRadiusY, mantleRadiusZ, faceEyeSpacing, faceEyeYOffset),
|
|
12818
|
-
}, faceEyeRadiusX, faceEyeRadiusY, mantleCenter, headPitch, headYaw, sceneCenterX, sceneCenterY, size, palette, timeMs, animationPhase + 0.7 +
|
|
12885
|
+
}, faceEyeRadiusX, faceEyeRadiusY, mantleCenter, headPitch, headYaw, sceneCenterX, sceneCenterY, size, palette, timeMs, animationPhase + 0.7 + rightEyePhaseOffset, interaction, morphologyProfile.face.eyeStyle);
|
|
12819
12886
|
drawProjectedOrganicMouth(context, [
|
|
12820
12887
|
{
|
|
12821
12888
|
x: -mouthHalfWidth,
|
|
@@ -12859,14 +12926,28 @@ function drawOctopus3dAtmosphere(context, size, palette, sceneCenterX, sceneCent
|
|
|
12859
12926
|
/**
|
|
12860
12927
|
* Draws the soft ground shadow below the octopus.
|
|
12861
12928
|
*
|
|
12929
|
+
* Uses a scaled radial gradient instead of `context.filter = 'blur()'` to approximate the
|
|
12930
|
+
* blurry ellipse without triggering a costly software rasterization pass on every frame.
|
|
12931
|
+
*
|
|
12862
12932
|
* @private helper of `octopus3dAvatarVisual`
|
|
12863
12933
|
*/
|
|
12864
12934
|
function drawOctopus3dShadow(context, size, palette, interaction, timeMs) {
|
|
12935
|
+
const cx = size * 0.5 + interaction.gazeX * size * 0.04;
|
|
12936
|
+
const cy = size * 0.87 + Math.sin(timeMs / 920) * size * 0.008;
|
|
12937
|
+
const rx = size * (0.18 + interaction.intensity * 0.02);
|
|
12938
|
+
const ry = size * 0.06;
|
|
12865
12939
|
context.save();
|
|
12866
|
-
context.
|
|
12867
|
-
context.
|
|
12940
|
+
context.translate(cx, cy);
|
|
12941
|
+
context.scale(1, ry / rx);
|
|
12942
|
+
const blurRadius = rx * 1.4;
|
|
12943
|
+
const shadowGradient = context.createRadialGradient(0, 0, 0, 0, 0, blurRadius);
|
|
12944
|
+
shadowGradient.addColorStop(0, `${palette.shadow}7a`);
|
|
12945
|
+
shadowGradient.addColorStop(0.45, `${palette.shadow}44`);
|
|
12946
|
+
shadowGradient.addColorStop(0.8, `${palette.shadow}1a`);
|
|
12947
|
+
shadowGradient.addColorStop(1, `${palette.shadow}00`);
|
|
12948
|
+
context.fillStyle = shadowGradient;
|
|
12868
12949
|
context.beginPath();
|
|
12869
|
-
context.
|
|
12950
|
+
context.arc(0, 0, blurRadius, 0, Math.PI * 2);
|
|
12870
12951
|
context.fill();
|
|
12871
12952
|
context.restore();
|
|
12872
12953
|
}
|
|
@@ -13097,6 +13178,35 @@ const LIGHT_DIRECTION$1 = normalizeVector3({
|
|
|
13097
13178
|
y: -0.6,
|
|
13098
13179
|
z: 0.98,
|
|
13099
13180
|
});
|
|
13181
|
+
/**
|
|
13182
|
+
* Cache keyed by the `createRandom` factory reference (stable per mounted `<Avatar/>`).
|
|
13183
|
+
*
|
|
13184
|
+
* @private helper of `octopus3d2AvatarVisual`
|
|
13185
|
+
*/
|
|
13186
|
+
const octopus3d2StableStateCache = new WeakMap();
|
|
13187
|
+
/**
|
|
13188
|
+
* Returns the stable per-avatar state, computing it on first access and caching for subsequent frames.
|
|
13189
|
+
*
|
|
13190
|
+
* @private helper of `octopus3d2AvatarVisual`
|
|
13191
|
+
*/
|
|
13192
|
+
function getOctopus3d2StableState(createRandom) {
|
|
13193
|
+
const cached = octopus3d2StableStateCache.get(createRandom);
|
|
13194
|
+
if (cached !== undefined) {
|
|
13195
|
+
return cached;
|
|
13196
|
+
}
|
|
13197
|
+
const animationRandom = createRandom('octopus3d2-animation-profile');
|
|
13198
|
+
const eyeRandom = createRandom('octopus3d2-eye-profile');
|
|
13199
|
+
const leftEyePhaseOffset = eyeRandom() * 0.7;
|
|
13200
|
+
const rightEyePhaseOffset = eyeRandom() * 0.7;
|
|
13201
|
+
const state = {
|
|
13202
|
+
morphologyProfile: createOctopus3MorphologyProfile(createRandom),
|
|
13203
|
+
animationPhase: animationRandom() * Math.PI * 2,
|
|
13204
|
+
leftEyePhaseOffset,
|
|
13205
|
+
rightEyePhaseOffset,
|
|
13206
|
+
};
|
|
13207
|
+
octopus3d2StableStateCache.set(createRandom, state);
|
|
13208
|
+
return state;
|
|
13209
|
+
}
|
|
13100
13210
|
/**
|
|
13101
13211
|
* Octopus 3D 2 avatar visual.
|
|
13102
13212
|
*
|
|
@@ -13109,10 +13219,7 @@ const octopus3d2AvatarVisual = {
|
|
|
13109
13219
|
isAnimated: true,
|
|
13110
13220
|
supportsPointerTracking: true,
|
|
13111
13221
|
render({ context, size, palette, createRandom, timeMs, interaction }) {
|
|
13112
|
-
const morphologyProfile =
|
|
13113
|
-
const animationRandom = createRandom('octopus3d2-animation-profile');
|
|
13114
|
-
const eyeRandom = createRandom('octopus3d2-eye-profile');
|
|
13115
|
-
const animationPhase = animationRandom() * Math.PI * 2;
|
|
13222
|
+
const { morphologyProfile, animationPhase, leftEyePhaseOffset, rightEyePhaseOffset } = getOctopus3d2StableState(createRandom);
|
|
13116
13223
|
const sceneCenterX = size * 0.5;
|
|
13117
13224
|
const sceneCenterY = size * 0.575;
|
|
13118
13225
|
const bob = Math.sin(timeMs / 940 + animationPhase) * size * 0.013;
|
|
@@ -13165,8 +13272,8 @@ const octopus3d2AvatarVisual = {
|
|
|
13165
13272
|
const rightEyeLocalCenter = sampleBlobbyOctopusSurfacePoint(surfaceOptions, eyeLatitude, eyeLongitude);
|
|
13166
13273
|
const eyeRadiusX = size * morphologyProfile.face.eyeRadiusXRatio * 0.78;
|
|
13167
13274
|
const eyeRadiusY = eyeRadiusX * morphologyProfile.face.eyeHeightRatio * 0.92;
|
|
13168
|
-
drawProjectedOrganicEye(context, leftEyeLocalCenter, eyeRadiusX, eyeRadiusY, meshCenter, rotationX, rotationY, sceneCenterX, sceneCenterY, size, palette, timeMs, animationPhase +
|
|
13169
|
-
drawProjectedOrganicEye(context, rightEyeLocalCenter, eyeRadiusX, eyeRadiusY, meshCenter, rotationX, rotationY, sceneCenterX, sceneCenterY, size, palette, timeMs, animationPhase + 0.9 +
|
|
13275
|
+
drawProjectedOrganicEye(context, leftEyeLocalCenter, eyeRadiusX, eyeRadiusY, meshCenter, rotationX, rotationY, sceneCenterX, sceneCenterY, size, palette, timeMs, animationPhase + leftEyePhaseOffset, interaction, morphologyProfile.face.eyeStyle);
|
|
13276
|
+
drawProjectedOrganicEye(context, rightEyeLocalCenter, eyeRadiusX, eyeRadiusY, meshCenter, rotationX, rotationY, sceneCenterX, sceneCenterY, size, palette, timeMs, animationPhase + 0.9 + rightEyePhaseOffset, interaction, morphologyProfile.face.eyeStyle);
|
|
13170
13277
|
drawProjectedOrganicMouth(context, [
|
|
13171
13278
|
sampleBlobbyOctopusSurfacePoint(surfaceOptions, mouthLatitude, mouthCenterLongitude - mouthHalfLongitude),
|
|
13172
13279
|
sampleBlobbyOctopusSurfacePoint(surfaceOptions, mouthCurveLatitude, mouthCenterLongitude),
|
|
@@ -13195,14 +13302,28 @@ function drawBlobbyOctopusAtmosphere(context, size, palette, sceneCenterX, scene
|
|
|
13195
13302
|
/**
|
|
13196
13303
|
* Draws the soft floor shadow that anchors the single mesh in the frame.
|
|
13197
13304
|
*
|
|
13305
|
+
* Uses a scaled radial gradient instead of `context.filter = 'blur()'` to approximate the
|
|
13306
|
+
* blurry ellipse without triggering a costly software rasterization pass on every frame.
|
|
13307
|
+
*
|
|
13198
13308
|
* @private helper of `octopus3d2AvatarVisual`
|
|
13199
13309
|
*/
|
|
13200
13310
|
function drawBlobbyOctopusShadow(context, size, palette, interaction, timeMs, morphologyProfile) {
|
|
13311
|
+
const cx = size * 0.5 + interaction.gazeX * size * 0.045;
|
|
13312
|
+
const cy = size * 0.88 + Math.sin(timeMs / 940) * size * 0.008;
|
|
13313
|
+
const rx = size * (0.18 + (morphologyProfile.body.horizontalStretch - 1) * 0.04 + interaction.intensity * 0.018);
|
|
13314
|
+
const ry = size * 0.062;
|
|
13201
13315
|
context.save();
|
|
13202
|
-
context.
|
|
13203
|
-
context.
|
|
13316
|
+
context.translate(cx, cy);
|
|
13317
|
+
context.scale(1, ry / rx);
|
|
13318
|
+
const blurRadius = rx * 1.4;
|
|
13319
|
+
const shadowGradient = context.createRadialGradient(0, 0, 0, 0, 0, blurRadius);
|
|
13320
|
+
shadowGradient.addColorStop(0, `${palette.shadow}7a`);
|
|
13321
|
+
shadowGradient.addColorStop(0.45, `${palette.shadow}44`);
|
|
13322
|
+
shadowGradient.addColorStop(0.8, `${palette.shadow}1a`);
|
|
13323
|
+
shadowGradient.addColorStop(1, `${palette.shadow}00`);
|
|
13324
|
+
context.fillStyle = shadowGradient;
|
|
13204
13325
|
context.beginPath();
|
|
13205
|
-
context.
|
|
13326
|
+
context.arc(0, 0, blurRadius, 0, Math.PI * 2);
|
|
13206
13327
|
context.fill();
|
|
13207
13328
|
context.restore();
|
|
13208
13329
|
}
|
|
@@ -13358,6 +13479,40 @@ const LIGHT_DIRECTION = normalizeVector3({
|
|
|
13358
13479
|
* @private helper of `octopus3d3AvatarVisual`
|
|
13359
13480
|
*/
|
|
13360
13481
|
const OCTOPUS_TENTACLE_COUNT = 8;
|
|
13482
|
+
/**
|
|
13483
|
+
* Cache keyed by the `createRandom` factory reference, which is stable for the lifetime of one
|
|
13484
|
+
* mounted `<Avatar/>` component (created inside `resolveAvatarRenderDefinition` and held in a
|
|
13485
|
+
* React `useMemo`). Using a `WeakMap` ensures the entry is collected when the component unmounts.
|
|
13486
|
+
*
|
|
13487
|
+
* @private helper of `octopus3d3AvatarVisual`
|
|
13488
|
+
*/
|
|
13489
|
+
const stableStateCache = new WeakMap();
|
|
13490
|
+
/**
|
|
13491
|
+
* Returns the stable per-avatar state, computing it on first access and returning the cached
|
|
13492
|
+
* result on every subsequent call within the same `<Avatar/>` mount.
|
|
13493
|
+
*
|
|
13494
|
+
* @private helper of `octopus3d3AvatarVisual`
|
|
13495
|
+
*/
|
|
13496
|
+
function getOctopus3d3StableState(createRandom) {
|
|
13497
|
+
const cached = stableStateCache.get(createRandom);
|
|
13498
|
+
if (cached !== undefined) {
|
|
13499
|
+
return cached;
|
|
13500
|
+
}
|
|
13501
|
+
const morphologyProfile = createOctopus3MorphologyProfile(createRandom);
|
|
13502
|
+
const animationRandom = createRandom('octopus3d3-animation-profile');
|
|
13503
|
+
const eyeRandom = createRandom('octopus3d3-eye-profile');
|
|
13504
|
+
const leftEyePhaseOffset = eyeRandom() * 0.7;
|
|
13505
|
+
const rightEyePhaseOffset = eyeRandom() * 0.7;
|
|
13506
|
+
const state = {
|
|
13507
|
+
morphologyProfile,
|
|
13508
|
+
animationPhase: animationRandom() * Math.PI * 2,
|
|
13509
|
+
leftEyePhaseOffset,
|
|
13510
|
+
rightEyePhaseOffset,
|
|
13511
|
+
tentacleProfiles: createContinuousTentacleProfiles(createRandom, morphologyProfile),
|
|
13512
|
+
};
|
|
13513
|
+
stableStateCache.set(createRandom, state);
|
|
13514
|
+
return state;
|
|
13515
|
+
}
|
|
13361
13516
|
/**
|
|
13362
13517
|
* Octopus 3D 3 avatar visual.
|
|
13363
13518
|
*
|
|
@@ -13370,11 +13525,7 @@ const octopus3d3AvatarVisual = {
|
|
|
13370
13525
|
isAnimated: true,
|
|
13371
13526
|
supportsPointerTracking: true,
|
|
13372
13527
|
render({ context, size, palette, createRandom, timeMs, interaction }) {
|
|
13373
|
-
const morphologyProfile =
|
|
13374
|
-
const animationRandom = createRandom('octopus3d3-animation-profile');
|
|
13375
|
-
const eyeRandom = createRandom('octopus3d3-eye-profile');
|
|
13376
|
-
const animationPhase = animationRandom() * Math.PI * 2;
|
|
13377
|
-
const tentacleProfiles = createContinuousTentacleProfiles(createRandom, morphologyProfile);
|
|
13528
|
+
const { morphologyProfile, animationPhase, leftEyePhaseOffset, rightEyePhaseOffset, tentacleProfiles } = getOctopus3d3StableState(createRandom);
|
|
13378
13529
|
const sceneCenterX = size * 0.5;
|
|
13379
13530
|
const sceneCenterY = size * 0.535;
|
|
13380
13531
|
const bob = Math.sin(timeMs / 960 + animationPhase) * size * 0.012;
|
|
@@ -13451,8 +13602,8 @@ const octopus3d3AvatarVisual = {
|
|
|
13451
13602
|
size,
|
|
13452
13603
|
palette,
|
|
13453
13604
|
});
|
|
13454
|
-
drawProjectedOrganicEye(context, sampleContinuousOctopusSurfacePoint(surfaceOptions, eyeLatitude, -eyeLongitude), eyeRadiusX, eyeRadiusY, meshCenter, rotationX, rotationY, sceneCenterX, sceneCenterY, size, palette, timeMs, animationPhase +
|
|
13455
|
-
drawProjectedOrganicEye(context, sampleContinuousOctopusSurfacePoint(surfaceOptions, eyeLatitude, eyeLongitude), eyeRadiusX, eyeRadiusY, meshCenter, rotationX, rotationY, sceneCenterX, sceneCenterY, size, palette, timeMs, animationPhase + 0.85 +
|
|
13605
|
+
drawProjectedOrganicEye(context, sampleContinuousOctopusSurfacePoint(surfaceOptions, eyeLatitude, -eyeLongitude), eyeRadiusX, eyeRadiusY, meshCenter, rotationX, rotationY, sceneCenterX, sceneCenterY, size, palette, timeMs, animationPhase + leftEyePhaseOffset, interaction, morphologyProfile.face.eyeStyle);
|
|
13606
|
+
drawProjectedOrganicEye(context, sampleContinuousOctopusSurfacePoint(surfaceOptions, eyeLatitude, eyeLongitude), eyeRadiusX, eyeRadiusY, meshCenter, rotationX, rotationY, sceneCenterX, sceneCenterY, size, palette, timeMs, animationPhase + 0.85 + rightEyePhaseOffset, interaction, morphologyProfile.face.eyeStyle);
|
|
13456
13607
|
drawProjectedOrganicMouth(context, [
|
|
13457
13608
|
sampleContinuousOctopusSurfacePoint(surfaceOptions, mouthLatitude, mouthCenterLongitude - mouthHalfLongitude),
|
|
13458
13609
|
sampleContinuousOctopusSurfacePoint(surfaceOptions, mouthCurveLatitude, mouthCenterLongitude),
|
|
@@ -13503,14 +13654,30 @@ function drawContinuousOctopusAtmosphere(context, size, palette, sceneCenterX, s
|
|
|
13503
13654
|
/**
|
|
13504
13655
|
* Draws the soft lower shadow that anchors the octopus in the avatar frame.
|
|
13505
13656
|
*
|
|
13657
|
+
* Uses a scaled radial gradient instead of `context.filter = 'blur()'` to approximate the
|
|
13658
|
+
* blurry ellipse without triggering a costly software rasterization pass on every frame.
|
|
13659
|
+
*
|
|
13506
13660
|
* @private helper of `octopus3d3AvatarVisual`
|
|
13507
13661
|
*/
|
|
13508
13662
|
function drawContinuousOctopusShadow(context, size, palette, interaction, timeMs, morphologyProfile) {
|
|
13663
|
+
const cx = size * 0.5 + interaction.gazeX * size * 0.045;
|
|
13664
|
+
const cy = size * 0.9 + Math.sin(timeMs / 980) * size * 0.007;
|
|
13665
|
+
const rx = size * (0.19 + morphologyProfile.tentacles.rootSpreadScale * 0.022 + interaction.intensity * 0.02);
|
|
13666
|
+
const ry = size * 0.06;
|
|
13667
|
+
// Scale the context so that drawing a circle produces the correct ellipse aspect ratio,
|
|
13668
|
+
// then fill with a radial gradient that approximates the blurry edge without context.filter.
|
|
13509
13669
|
context.save();
|
|
13510
|
-
context.
|
|
13511
|
-
context.
|
|
13670
|
+
context.translate(cx, cy);
|
|
13671
|
+
context.scale(1, ry / rx);
|
|
13672
|
+
const blurRadius = rx * 1.4;
|
|
13673
|
+
const shadowGradient = context.createRadialGradient(0, 0, 0, 0, 0, blurRadius);
|
|
13674
|
+
shadowGradient.addColorStop(0, `${palette.shadow}7a`);
|
|
13675
|
+
shadowGradient.addColorStop(0.45, `${palette.shadow}44`);
|
|
13676
|
+
shadowGradient.addColorStop(0.8, `${palette.shadow}1a`);
|
|
13677
|
+
shadowGradient.addColorStop(1, `${palette.shadow}00`);
|
|
13678
|
+
context.fillStyle = shadowGradient;
|
|
13512
13679
|
context.beginPath();
|
|
13513
|
-
context.
|
|
13680
|
+
context.arc(0, 0, blurRadius, 0, Math.PI * 2);
|
|
13514
13681
|
context.fill();
|
|
13515
13682
|
context.restore();
|
|
13516
13683
|
}
|
|
@@ -22115,7 +22282,7 @@ function getTimeoutToolRuntimeAdapterOrDisabledResult(action, runtimeContext) {
|
|
|
22115
22282
|
* @private internal helper function
|
|
22116
22283
|
*/
|
|
22117
22284
|
function $randomToken(randomness) {
|
|
22118
|
-
return
|
|
22285
|
+
return CryptoJS.lib.WordArray.random(randomness).toString(CryptoJS.enc.Hex);
|
|
22119
22286
|
}
|
|
22120
22287
|
// TODO: [🤶] Maybe export through `@promptbook/utils` or `@promptbook/random` package
|
|
22121
22288
|
// TODO: Maybe use nanoid instead https://github.com/ai/nanoid
|
|
@@ -28419,7 +28586,7 @@ function createOpenAiCodexRunnerResolution(options) {
|
|
|
28419
28586
|
askForApproval: 'never',
|
|
28420
28587
|
allowCredits: options.allowCredits,
|
|
28421
28588
|
});
|
|
28422
|
-
if (!options.allowCredits) {
|
|
28589
|
+
if (!options.allowCredits && options.isVerbose === true) {
|
|
28423
28590
|
console.info(colors.gray('OpenAI Codex credit spending is disabled. Use `--allow-credits` to explicitly opt in.'));
|
|
28424
28591
|
}
|
|
28425
28592
|
return createRunnerResolution(options, runner, actualRunnerModel);
|
|
@@ -28735,14 +28902,50 @@ function buildAgentMessageCommitMessage(messageFile) {
|
|
|
28735
28902
|
* Builds the prompt sent to the selected coding runner for one queued user-thread book.
|
|
28736
28903
|
*/
|
|
28737
28904
|
function buildAgentMessagePrompt(messageRelativePath, agentSystemMessage) {
|
|
28738
|
-
|
|
28739
|
-
|
|
28905
|
+
return spaceTrim$1((block) => `
|
|
28906
|
+
# Answer 1 user question
|
|
28740
28907
|
|
|
28741
|
-
|
|
28742
|
-
|
|
28743
|
-
|
|
28744
|
-
|
|
28745
|
-
|
|
28908
|
+
- Read \`${messageRelativePath}\` and answer the most recent \`MESSAGE @User\`
|
|
28909
|
+
- Only change the queued message file by appending one new \`MESSAGE @Agent\` block
|
|
28910
|
+
- Do not modify any other file in the repository
|
|
28911
|
+
|
|
28912
|
+
## Rules for the answering
|
|
28913
|
+
|
|
28914
|
+
## Formatting
|
|
28915
|
+
|
|
28916
|
+
- You can use Markdown formatting in the messages like **bold** or *italic*
|
|
28917
|
+
|
|
28918
|
+
## Sources and citations
|
|
28919
|
+
|
|
28920
|
+
Mark sources and citations like this "【https://example.com/document123.pdf 】"
|
|
28921
|
+
|
|
28922
|
+
At the same time, you can write sources naturally in the text of the answers
|
|
28923
|
+
|
|
28924
|
+
For example:
|
|
28925
|
+
|
|
28926
|
+
> According to paragraph §745b, the fee can be waived for a person over 65 years old. 【https://praha13.cz/2026/paragraph-745.doc】
|
|
28927
|
+
|
|
28928
|
+
- "paragraph §745b" fits naturally in the text.
|
|
28929
|
+
- "【https://praha13.cz/2026/paragraph-745.doc】" The exact format of the quote is important for further processing of the answer.
|
|
28930
|
+
- The "【" and "】" symbols are used to mark the source and will be parsed, inside should be valid URL used as a source for the answer.
|
|
28931
|
+
|
|
28932
|
+
## Quick buttons
|
|
28933
|
+
|
|
28934
|
+
If there is a meaningful follow-up procedure, use quick buttons at the end of the answer:
|
|
28935
|
+
|
|
28936
|
+
\`\`\`
|
|
28937
|
+
How big is the contract you are posting?
|
|
28938
|
+
|
|
28939
|
+
[Up to 50,000 CZK](?message=We are posting an order up to 50,000 CZK)
|
|
28940
|
+
[Up to 100,000 CZK](?message=We are posting an order up to 100,000 CZK)
|
|
28941
|
+
[Over 100,000 CZK](?message=We are posting an order over 100,000 CZK)
|
|
28942
|
+
\`\`\`
|
|
28943
|
+
|
|
28944
|
+
|
|
28945
|
+
## This is how you should behave
|
|
28946
|
+
|
|
28947
|
+
${block(agentSystemMessage)}
|
|
28948
|
+
`);
|
|
28746
28949
|
}
|
|
28747
28950
|
|
|
28748
28951
|
/**
|
|
@@ -31356,7 +31559,7 @@ function $registeredScrapersMessage(availableScrapers) {
|
|
|
31356
31559
|
* @public exported from `@promptbook/editable`
|
|
31357
31560
|
*/
|
|
31358
31561
|
function knowledgeSourceContentToName(knowledgeSourceContent) {
|
|
31359
|
-
const hash = SHA256(hexEncoder.parse(JSON.stringify(knowledgeSourceContent)))
|
|
31562
|
+
const hash = CryptoJS.SHA256(hexEncoder.parse(JSON.stringify(knowledgeSourceContent)))
|
|
31360
31563
|
// <- TODO: [🥬] Encapsulate sha256 to some private utility function
|
|
31361
31564
|
.toString( /* hex */)
|
|
31362
31565
|
.substring(0, 20);
|
|
@@ -32204,7 +32407,7 @@ function csvParse(value /* <- TODO: string_csv */, settings, schema /* <- TODO:
|
|
|
32204
32407
|
console.warn('CSV string contains carriage return characters, but in the CSV settings the `newline` setting does not include them. Autohealing the CSV string.');
|
|
32205
32408
|
value = value.replace(/\r\n/g, '\n').replace(/\r/g, '\n');
|
|
32206
32409
|
}
|
|
32207
|
-
const csv = parse(value, settings);
|
|
32410
|
+
const csv = papaparse.parse(value, settings);
|
|
32208
32411
|
return csv;
|
|
32209
32412
|
}
|
|
32210
32413
|
|
|
@@ -32289,10 +32492,10 @@ const CsvFormatParser = {
|
|
|
32289
32492
|
i > index ? { ...row, [outputParameterName]: PENDING_VALUE_PLACEHOLDER } : row,
|
|
32290
32493
|
);
|
|
32291
32494
|
*/
|
|
32292
|
-
await onProgress(unparse(mappedData, { ...settings, ...MANDATORY_CSV_SETTINGS }));
|
|
32495
|
+
await onProgress(papaparse.unparse(mappedData, { ...settings, ...MANDATORY_CSV_SETTINGS }));
|
|
32293
32496
|
}
|
|
32294
32497
|
}
|
|
32295
|
-
return unparse(mappedData, { ...settings, ...MANDATORY_CSV_SETTINGS });
|
|
32498
|
+
return papaparse.unparse(mappedData, { ...settings, ...MANDATORY_CSV_SETTINGS });
|
|
32296
32499
|
},
|
|
32297
32500
|
},
|
|
32298
32501
|
{
|
|
@@ -32320,7 +32523,7 @@ const CsvFormatParser = {
|
|
|
32320
32523
|
return /* not await */ mapCallback({ [key]: value }, index, array.length);
|
|
32321
32524
|
}));
|
|
32322
32525
|
}));
|
|
32323
|
-
return unparse(mappedData, { ...settings, ...MANDATORY_CSV_SETTINGS });
|
|
32526
|
+
return papaparse.unparse(mappedData, { ...settings, ...MANDATORY_CSV_SETTINGS });
|
|
32324
32527
|
},
|
|
32325
32528
|
},
|
|
32326
32529
|
],
|
|
@@ -35887,7 +36090,9 @@ function parseBookMessageHeader(line) {
|
|
|
35887
36090
|
* @private internal utility of `Book`
|
|
35888
36091
|
*/
|
|
35889
36092
|
function parseCommitmentHeader(line) {
|
|
35890
|
-
|
|
36093
|
+
// Require at least 2 characters in the first keyword word to avoid treating common
|
|
36094
|
+
// single-letter words (e.g. "V" in Czech, "I" or "A" in English) as commitment headers.
|
|
36095
|
+
const match = /^([A-Z][A-Z0-9]+(?: [A-Z0-9]+)*)(?:\s+(.*))?$/u.exec(line);
|
|
35891
36096
|
if (!match) {
|
|
35892
36097
|
return null;
|
|
35893
36098
|
}
|
|
@@ -39301,6 +39506,57 @@ function listDefaultCoderProjectPromptTemplateDisplayPaths() {
|
|
|
39301
39506
|
// Note: [🟡] Code for CLI command [init](src/cli/cli-commands/coder/init.ts) should never be published outside of `@promptbook/cli`
|
|
39302
39507
|
// Note: [💞] Ignore a discrepancy between file name and entity name
|
|
39303
39508
|
|
|
39509
|
+
/**
|
|
39510
|
+
* Pattern that matches durations like "1h", "30m", "5s", "1h30m", "1h30m5s".
|
|
39511
|
+
*/
|
|
39512
|
+
const DURATION_PATTERN = /^(?:(\d+)h)?(?:(\d+)m(?:in)?)?(?:(\d+)s)?$/;
|
|
39513
|
+
/**
|
|
39514
|
+
* Parses a human-readable duration string into milliseconds.
|
|
39515
|
+
*
|
|
39516
|
+
* Supported formats: `Xh`, `Xm`, `Xs`, and combinations like `1h30m`, `1h30m5s`.
|
|
39517
|
+
*
|
|
39518
|
+
* @returns Duration in milliseconds
|
|
39519
|
+
* @throws When the string does not match any supported format
|
|
39520
|
+
*
|
|
39521
|
+
* @private internal utility of `ptbk coder run`
|
|
39522
|
+
*/
|
|
39523
|
+
function parseDuration(durationString) {
|
|
39524
|
+
var _a, _b, _c;
|
|
39525
|
+
const trimmed = durationString.trim();
|
|
39526
|
+
if (!trimmed) {
|
|
39527
|
+
throw new Error(`Invalid duration: empty string. Expected a format like "1h", "30m", "5s", or combinations like "1h30m".`);
|
|
39528
|
+
}
|
|
39529
|
+
const match = trimmed.match(DURATION_PATTERN);
|
|
39530
|
+
if (!match || (match[1] === undefined && match[2] === undefined && match[3] === undefined)) {
|
|
39531
|
+
throw new Error(`Invalid duration: "${durationString}". Expected a format like "1h", "30m", "5s", or combinations like "1h30m5s".`);
|
|
39532
|
+
}
|
|
39533
|
+
const hours = parseInt((_a = match[1]) !== null && _a !== void 0 ? _a : '0', 10);
|
|
39534
|
+
const minutes = parseInt((_b = match[2]) !== null && _b !== void 0 ? _b : '0', 10);
|
|
39535
|
+
const seconds = parseInt((_c = match[3]) !== null && _c !== void 0 ? _c : '0', 10);
|
|
39536
|
+
return (hours * 3600 + minutes * 60 + seconds) * 1000;
|
|
39537
|
+
}
|
|
39538
|
+
/**
|
|
39539
|
+
* Formats a duration in milliseconds into a compact human-readable string.
|
|
39540
|
+
*
|
|
39541
|
+
* Examples: `3600000` → `"1h"`, `90000` → `"1m 30s"`, `5000` → `"5s"`.
|
|
39542
|
+
*
|
|
39543
|
+
* @private internal utility of `ptbk coder run`
|
|
39544
|
+
*/
|
|
39545
|
+
function formatDurationMs(ms) {
|
|
39546
|
+
const totalSeconds = Math.ceil(ms / 1000);
|
|
39547
|
+
const hours = Math.floor(totalSeconds / 3600);
|
|
39548
|
+
const minutes = Math.floor((totalSeconds % 3600) / 60);
|
|
39549
|
+
const seconds = totalSeconds % 60;
|
|
39550
|
+
const parts = [];
|
|
39551
|
+
if (hours > 0)
|
|
39552
|
+
parts.push(`${hours}h`);
|
|
39553
|
+
if (minutes > 0)
|
|
39554
|
+
parts.push(`${minutes}m`);
|
|
39555
|
+
if (seconds > 0 || parts.length === 0)
|
|
39556
|
+
parts.push(`${seconds}s`);
|
|
39557
|
+
return parts.join(' ');
|
|
39558
|
+
}
|
|
39559
|
+
|
|
39304
39560
|
/**
|
|
39305
39561
|
* Initializes `coder run` command for Promptbook CLI utilities
|
|
39306
39562
|
*
|
|
@@ -39333,7 +39589,13 @@ function $initializeCoderRunCommand(program) {
|
|
|
39333
39589
|
command.option('--preserve-logs', 'Keep generated temp prompt/log artifacts after successful rounds for debugging and analytics', false);
|
|
39334
39590
|
addPromptRunnerExecutionOptions(command);
|
|
39335
39591
|
command.option('--priority <minimum-priority>', 'Filter prompts by minimum priority level', parseIntOption, 0);
|
|
39336
|
-
command.option('--
|
|
39592
|
+
command.option('--wait [duration]', spaceTrim$1(`
|
|
39593
|
+
Wait between prompt rounds.
|
|
39594
|
+
Without a value (default): waits for user confirmation before each prompt (interactive mode).
|
|
39595
|
+
With a duration like 1h, 30m, 5s: waits that long between prompts to avoid hitting rate limits of the harness.
|
|
39596
|
+
`), true);
|
|
39597
|
+
// Note: --no-wait disables the default interactive wait-for-user behaviour
|
|
39598
|
+
command.option('--no-wait', 'Skip all waiting between prompts and run non-interactively');
|
|
39337
39599
|
command.option('--auto-migrate', 'Run testing-server database migrations automatically after each successfully processed prompt');
|
|
39338
39600
|
command.option('--allow-destructive-auto-migrate', 'Allow auto-migrate even when heuristic SQL safety check flags destructive pending migrations');
|
|
39339
39601
|
command.action(handleActionErrors(async (cliOptions) => {
|
|
@@ -39342,10 +39604,23 @@ function $initializeCoderRunCommand(program) {
|
|
|
39342
39604
|
const runnerOptions = normalizePromptRunnerCliOptions(cliOptions, {
|
|
39343
39605
|
isAgentRequired: !dryRun,
|
|
39344
39606
|
});
|
|
39607
|
+
// [1] Parse the --wait option:
|
|
39608
|
+
// true (default or --wait without value): wait for user confirmation
|
|
39609
|
+
// false (--no-wait): no waiting at all
|
|
39610
|
+
// string (--wait 1h): wait that long between prompt rounds
|
|
39611
|
+
let waitForUser = false;
|
|
39612
|
+
let waitBetweenPrompts = 0;
|
|
39613
|
+
if (wait === true) {
|
|
39614
|
+
waitForUser = true;
|
|
39615
|
+
}
|
|
39616
|
+
else if (typeof wait === 'string' && wait !== '') {
|
|
39617
|
+
waitBetweenPrompts = parseDuration(wait);
|
|
39618
|
+
}
|
|
39345
39619
|
// Convert commander options to RunOptions format
|
|
39346
39620
|
const runOptions = {
|
|
39347
39621
|
dryRun,
|
|
39348
|
-
waitForUser
|
|
39622
|
+
waitForUser,
|
|
39623
|
+
waitBetweenPrompts,
|
|
39349
39624
|
noCommit: runnerOptions.noCommit,
|
|
39350
39625
|
ignoreGitChanges: runnerOptions.ignoreGitChanges,
|
|
39351
39626
|
agentName: runnerOptions.agentName,
|
|
@@ -45336,7 +45611,7 @@ async function getScraperIntermediateSource(source, options) {
|
|
|
45336
45611
|
const { filename: sourceFilename, url } = source;
|
|
45337
45612
|
const { rootDirname, cacheDirname, intermediateFilesStrategy, extension, isVerbose } = options;
|
|
45338
45613
|
// TODO: [👬] DRY
|
|
45339
|
-
const hash = SHA256(
|
|
45614
|
+
const hash = CryptoJS.SHA256(
|
|
45340
45615
|
// <- TODO: [🥬] Encapsulate sha256 to some private utility function
|
|
45341
45616
|
hexEncoder.parse(sourceFilename || url || 'untitled'))
|
|
45342
45617
|
.toString( /* hex */)
|
|
@@ -45427,7 +45702,7 @@ const _WebsiteScraperMetadataRegistration = $scrapersMetadataRegister.register(w
|
|
|
45427
45702
|
* @private utility of `WebsiteScraper`
|
|
45428
45703
|
*/
|
|
45429
45704
|
function createShowdownConverter() {
|
|
45430
|
-
return new Converter({
|
|
45705
|
+
return new showdown.Converter({
|
|
45431
45706
|
flavor: 'github',
|
|
45432
45707
|
/*
|
|
45433
45708
|
> import showdownHighlight from 'showdown-highlight';
|
|
@@ -62788,10 +63063,12 @@ function createPromptRunnerOptions(options) {
|
|
|
62788
63063
|
noUi: options.noUi,
|
|
62789
63064
|
thinkingLevel: options.thinkingLevel,
|
|
62790
63065
|
waitForUser: false,
|
|
63066
|
+
waitBetweenPrompts: 0,
|
|
62791
63067
|
noCommit: true,
|
|
62792
63068
|
ignoreGitChanges: true,
|
|
62793
63069
|
normalizeLineEndings: false,
|
|
62794
63070
|
allowCredits: options.allowCredits,
|
|
63071
|
+
isVerbose: options.isVerbose,
|
|
62795
63072
|
autoMigrate: false,
|
|
62796
63073
|
allowDestructiveAutoMigrate: false,
|
|
62797
63074
|
autoPush: false,
|
|
@@ -64824,7 +65101,7 @@ function emitAgentLlmExecutionToolsAssistantPreparationProgress(options) {
|
|
|
64824
65101
|
* Computes one stable hash from a JSON-serializable value.
|
|
64825
65102
|
*/
|
|
64826
65103
|
function computeJsonHash$1(value) {
|
|
64827
|
-
return SHA256(JSON.stringify(value)).toString();
|
|
65104
|
+
return CryptoJS.SHA256(JSON.stringify(value)).toString();
|
|
64828
65105
|
}
|
|
64829
65106
|
/**
|
|
64830
65107
|
* Handles OpenAI AgentKit-backed executions for `AgentLlmExecutionTools`.
|
|
@@ -64982,7 +65259,7 @@ AgentLlmExecutionToolsAgentKitRunner.vectorStoreCache = new Map();
|
|
|
64982
65259
|
* Computes one stable hash from a JSON-serializable value.
|
|
64983
65260
|
*/
|
|
64984
65261
|
function computeJsonHash(value) {
|
|
64985
|
-
return SHA256(JSON.stringify(value)).toString();
|
|
65262
|
+
return CryptoJS.SHA256(JSON.stringify(value)).toString();
|
|
64986
65263
|
}
|
|
64987
65264
|
/**
|
|
64988
65265
|
* Removes assistant-managed requirements before the prompt is executed via OpenAI Assistants.
|
|
@@ -65784,7 +66061,7 @@ class AgentLlmExecutionTools {
|
|
|
65784
66061
|
* Returns a virtual model name representing the agent behavior.
|
|
65785
66062
|
*/
|
|
65786
66063
|
get modelName() {
|
|
65787
|
-
const hash = SHA256(hexEncoder.parse(this.options.agentSource)).toString( /* hex */);
|
|
66064
|
+
const hash = CryptoJS.SHA256(hexEncoder.parse(this.options.agentSource)).toString( /* hex */);
|
|
65788
66065
|
const agentId = hash.substring(0, 10);
|
|
65789
66066
|
return (normalizeToKebabCase(this.title) + '-' + agentId);
|
|
65790
66067
|
}
|
|
@@ -68321,7 +68598,7 @@ var findRefactorCandidates$1 = /*#__PURE__*/Object.freeze({
|
|
|
68321
68598
|
/**
|
|
68322
68599
|
* CLI usage text for this script.
|
|
68323
68600
|
*/
|
|
68324
|
-
const USAGE = 'Usage: run-codex-prompts [--dry-run] [--harness <harness-name>] [--model <model>] [--context <context-or-file>] [--test <test-command...>] [--preserve-logs] [--no-ui] [--thinking-level <thinking-level>] [--priority <minimum-priority>] [--allow-credits] [--auto-migrate] [--allow-destructive-auto-migrate] [--no-wait] [--no-commit] [--ignore-git-changes] [--no-normalize-line-endings] [--auto-push] [--auto-pull]';
|
|
68601
|
+
const USAGE = 'Usage: run-codex-prompts [--dry-run] [--harness <harness-name>] [--model <model>] [--context <context-or-file>] [--test <test-command...>] [--preserve-logs] [--no-ui] [--thinking-level <thinking-level>] [--priority <minimum-priority>] [--allow-credits] [--auto-migrate] [--allow-destructive-auto-migrate] [--wait [duration]] [--no-wait] [--no-commit] [--ignore-git-changes] [--no-normalize-line-endings] [--auto-push] [--auto-pull]';
|
|
68325
68602
|
/**
|
|
68326
68603
|
* Top-level flags supported by this command.
|
|
68327
68604
|
*/
|
|
@@ -68338,6 +68615,7 @@ const KNOWN_OPTION_FLAGS = new Set([
|
|
|
68338
68615
|
'--allow-credits',
|
|
68339
68616
|
'--auto-migrate',
|
|
68340
68617
|
'--allow-destructive-auto-migrate',
|
|
68618
|
+
'--wait',
|
|
68341
68619
|
'--no-wait',
|
|
68342
68620
|
'--no-commit',
|
|
68343
68621
|
'--ignore-git-changes',
|
|
@@ -68376,6 +68654,22 @@ function parseRunOptions(args) {
|
|
|
68376
68654
|
const allowDestructiveAutoMigrate = args.includes('--allow-destructive-auto-migrate');
|
|
68377
68655
|
const autoPush = args.includes('--auto-push');
|
|
68378
68656
|
const autoPull = args.includes('--auto-pull');
|
|
68657
|
+
// [1] Parse --wait [duration]:
|
|
68658
|
+
// absent or --no-wait: no waiting
|
|
68659
|
+
// --wait (no value): wait for user confirmation
|
|
68660
|
+
// --wait 1h: wait 1h between prompt rounds to avoid rate limits
|
|
68661
|
+
const waitOptionalValue = readOptionalOptionValue(args, '--wait');
|
|
68662
|
+
let waitForUser = false;
|
|
68663
|
+
let waitBetweenPrompts = 0;
|
|
68664
|
+
if (waitOptionalValue === null) {
|
|
68665
|
+
// --wait present without a duration value: interactive mode
|
|
68666
|
+
waitForUser = true;
|
|
68667
|
+
}
|
|
68668
|
+
else if (waitOptionalValue !== undefined) {
|
|
68669
|
+
// --wait <duration>: time-based wait between rounds
|
|
68670
|
+
waitBetweenPrompts = parseDuration(waitOptionalValue);
|
|
68671
|
+
}
|
|
68672
|
+
// --no-wait (or no flag): both waitForUser and waitBetweenPrompts remain false/0
|
|
68379
68673
|
let thinkingLevel;
|
|
68380
68674
|
if (hasTestCommandFlag && testCommand === undefined) {
|
|
68381
68675
|
exitWithUsageError('Missing value for --test. Use a shell command such as `npm run test` and quote it when it contains top-level CLI flags.');
|
|
@@ -68394,7 +68688,8 @@ function parseRunOptions(args) {
|
|
|
68394
68688
|
}
|
|
68395
68689
|
return {
|
|
68396
68690
|
dryRun,
|
|
68397
|
-
waitForUser
|
|
68691
|
+
waitForUser,
|
|
68692
|
+
waitBetweenPrompts,
|
|
68398
68693
|
noCommit,
|
|
68399
68694
|
ignoreGitChanges,
|
|
68400
68695
|
normalizeLineEndings,
|
|
@@ -68413,6 +68708,23 @@ function parseRunOptions(args) {
|
|
|
68413
68708
|
priority,
|
|
68414
68709
|
};
|
|
68415
68710
|
}
|
|
68711
|
+
/**
|
|
68712
|
+
* Reads an optional value for a flag that may appear with or without a following value.
|
|
68713
|
+
*
|
|
68714
|
+
* Returns `undefined` when the flag is absent, `null` when the flag is present but has no value
|
|
68715
|
+
* (the next token is another flag or the end of args), and the value string otherwise.
|
|
68716
|
+
*/
|
|
68717
|
+
function readOptionalOptionValue(args, flag) {
|
|
68718
|
+
if (!args.includes(flag)) {
|
|
68719
|
+
return undefined;
|
|
68720
|
+
}
|
|
68721
|
+
const index = args.indexOf(flag);
|
|
68722
|
+
const nextArg = args[index + 1];
|
|
68723
|
+
if (nextArg === undefined || nextArg.startsWith('-')) {
|
|
68724
|
+
return null;
|
|
68725
|
+
}
|
|
68726
|
+
return nextArg;
|
|
68727
|
+
}
|
|
68416
68728
|
/**
|
|
68417
68729
|
* Reads a value of a CLI option that follows a given flag.
|
|
68418
68730
|
*/
|
|
@@ -70868,6 +71180,7 @@ async function runCodexPrompts(providedOptions) {
|
|
|
70868
71180
|
initializeRunUi(uiHandle, runner.name, actualRunnerModel, options);
|
|
70869
71181
|
let hasShownUpcomingTasks = false;
|
|
70870
71182
|
let hasWaitedForStart = false;
|
|
71183
|
+
let hasRunAtLeastOneRound = false;
|
|
70871
71184
|
while (just(true)) {
|
|
70872
71185
|
if (options.autoPull && !options.dryRun) {
|
|
70873
71186
|
await waitForRequestedPause({
|
|
@@ -70903,6 +71216,16 @@ async function runCodexPrompts(providedOptions) {
|
|
|
70903
71216
|
}
|
|
70904
71217
|
const nextPrompt = promptQueueSnapshot.nextPrompt;
|
|
70905
71218
|
const promptLabel = buildPromptLabelForDisplay(nextPrompt.file, nextPrompt.section);
|
|
71219
|
+
// Wait between prompt rounds (skipped for the first round)
|
|
71220
|
+
if (hasRunAtLeastOneRound) {
|
|
71221
|
+
await waitBetweenPromptRoundsIfNeeded({
|
|
71222
|
+
options,
|
|
71223
|
+
isRichUiEnabled,
|
|
71224
|
+
progressDisplay,
|
|
71225
|
+
uiHandle,
|
|
71226
|
+
});
|
|
71227
|
+
}
|
|
71228
|
+
hasRunAtLeastOneRound = true;
|
|
70906
71229
|
hasWaitedForStart = await waitForPromptConfirmationIfNeeded({
|
|
70907
71230
|
options,
|
|
70908
71231
|
nextPrompt,
|
|
@@ -71138,6 +71461,39 @@ async function waitForPromptConfirmationIfNeeded(options) {
|
|
|
71138
71461
|
uiHandle === null || uiHandle === void 0 ? void 0 : uiHandle.state.resumeTimer();
|
|
71139
71462
|
return true;
|
|
71140
71463
|
}
|
|
71464
|
+
/**
|
|
71465
|
+
* Countdown update interval for the between-rounds wait display.
|
|
71466
|
+
*/
|
|
71467
|
+
const WAIT_COUNTDOWN_UPDATE_INTERVAL_MS = 30000;
|
|
71468
|
+
/**
|
|
71469
|
+
* Waits the configured time between prompt rounds to avoid hitting harness rate limits.
|
|
71470
|
+
* Does nothing when `waitBetweenPrompts` is zero.
|
|
71471
|
+
*/
|
|
71472
|
+
async function waitBetweenPromptRoundsIfNeeded(options) {
|
|
71473
|
+
const { options: runOptions, isRichUiEnabled, progressDisplay, uiHandle } = options;
|
|
71474
|
+
const { waitBetweenPrompts } = runOptions;
|
|
71475
|
+
if (waitBetweenPrompts <= 0) {
|
|
71476
|
+
return;
|
|
71477
|
+
}
|
|
71478
|
+
progressDisplay === null || progressDisplay === void 0 ? void 0 : progressDisplay.pauseTimer();
|
|
71479
|
+
uiHandle === null || uiHandle === void 0 ? void 0 : uiHandle.state.pauseTimer();
|
|
71480
|
+
uiHandle === null || uiHandle === void 0 ? void 0 : uiHandle.state.setPhase('waiting');
|
|
71481
|
+
let remaining = waitBetweenPrompts;
|
|
71482
|
+
while (remaining > 0) {
|
|
71483
|
+
const statusMessage = `Waiting ${formatDurationMs(remaining)} before next prompt to avoid rate limits...`;
|
|
71484
|
+
if (!isRichUiEnabled) {
|
|
71485
|
+
console.info(colors.gray(statusMessage));
|
|
71486
|
+
}
|
|
71487
|
+
else {
|
|
71488
|
+
uiHandle === null || uiHandle === void 0 ? void 0 : uiHandle.state.setStatusMessage(statusMessage);
|
|
71489
|
+
}
|
|
71490
|
+
const sleepMs = Math.min(WAIT_COUNTDOWN_UPDATE_INTERVAL_MS, remaining);
|
|
71491
|
+
await new Promise((resolve) => setTimeout(resolve, sleepMs));
|
|
71492
|
+
remaining -= sleepMs;
|
|
71493
|
+
}
|
|
71494
|
+
progressDisplay === null || progressDisplay === void 0 ? void 0 : progressDisplay.resumeTimer();
|
|
71495
|
+
uiHandle === null || uiHandle === void 0 ? void 0 : uiHandle.state.resumeTimer();
|
|
71496
|
+
}
|
|
71141
71497
|
/**
|
|
71142
71498
|
* Stops active displays and prints the git identity tip for real runs.
|
|
71143
71499
|
*/
|