Arm keepalive for regenerated responses

345ef5f3a92198f55aac8e36c9303c1744a8b044

permissionBRICK <40219477+permissionBRICK@users.noreply.github.com>

3 files changed, +17 -14Ignore whitespace
public/scripts/extensions/keepalive/index.js+15 -12
@@ -60,9 +60,8 @@ let retryTimer = null;
60let preparingJob = false;60let preparingJob = false;
61let lifecycleVersion = 0;61let lifecycleVersion = 0;
62// Whether keepalive is "armed" for the CURRENT chat. It stays dormant until the user sends a new62// Whether keepalive is "armed" for the CURRENT chat. It stays dormant until the user sends a new
63// message in the open chat — on a freshly loaded or switched-to chat (even with history already63// message or starts another foreground generation in the open chat. Merely loading a chat does not
64// present) we have no way to know whether its prompt is still cached server-side, so pinging would64// prove that its prompt is cached server-side. Reset on page reload and whenever the chat changes.
65// be pointless. Reset on page reload and whenever the chat changes.
66let armed = false;65let armed = false;
67// Per-profile "time since last message", keyed by connection profile id (or NONE_KEY).66// Per-profile "time since last message", keyed by connection profile id (or NONE_KEY).
68// In-memory only: on reload every profile is treated as freshly active.67// In-memory only: on reload every profile is treated as freshly active.
@@ -152,10 +151,7 @@ function markActivity() {
152}151}
153152
154/**153/**
155 * The user sent a new message in the current chat — the ONLY thing that arms keepalive.154 * A new user message arms keepalive before its foreground generation begins.
156 * Background/quiet generations, swipes, regenerations, and loading chat history deliberately do
157 * NOT arm it: none of those prove the user is actively continuing THIS chat from a known-cached
158 * prompt (GENERATION_STARTED in particular fires for every quiet/background generation too).
159 */155 */
160function onMessageSent() {156function onMessageSent() {
161 armed = true;157 armed = true;
@@ -164,7 +160,7 @@ function onMessageSent() {
164160
165/**161/**
166 * Opening or switching chats disarms keepalive: a freshly loaded chat is not proof its prompt is162 * Opening or switching chats disarms keepalive: a freshly loaded chat is not proof its prompt is
167 * still cached server-side, so we wait for a new sent message in that chat before running again.163 * still cached server-side, so we wait for a new message or foreground generation before running.
168 */164 */
169function onChatChanged() {165function onChatChanged() {
170 armed = false;166 armed = false;
@@ -454,10 +450,16 @@ function setupListeners() {
454 });450 });
455}451}
456452
457function onGenerationStarted(_type, _options, dryRun) {453function onGenerationStarted(type, _options, dryRun) {
458 if (!dryRun) {454 if (dryRun) {
459 markActivity();455 return;
456 }
457 // Regenerates, swipes, and continues send the current prompt to the provider without emitting
458 // MESSAGE_SENT. They are just as valid proof of a warm prompt as a newly typed message.
459 if (type !== 'quiet') {
460 armed = true;
460 }461 }
462 markActivity();
461}463}
462464
463function onGenerationEnded() {465function onGenerationEnded() {
@@ -493,7 +495,8 @@ async function init() {
493 setupListeners();495 setupListeners();
494 setupHeartbeatLoop();496 setupHeartbeatLoop();
495497
496 // Only the user sending a new message arms keepalive (for the current chat).498 // A new user message arms keepalive before generation starts. Foreground generations that do
499 // not send a new message (regenerate/swipe/continue) are armed by onGenerationStarted instead.
497 eventSource.on(event_types.MESSAGE_SENT, onMessageSent);500 eventSource.on(event_types.MESSAGE_SENT, onMessageSent);
498501
499 // Activity resets the backend deadline but never arms keepalive on its own. A completed502 // Activity resets the backend deadline but never arms keepalive on its own. A completed
public/scripts/extensions/keepalive/manifest.json+1 -1
@@ -6,7 +6,7 @@
6 "js": "index.js",6 "js": "index.js",
7 "css": "",7 "css": "",
8 "author": "SillyTavern",8 "author": "SillyTavern",
9 "version": "1.1.0",9 "version": "1.1.1",
10 "homePage": "https://github.com/SillyTavern/SillyTavern",10 "homePage": "https://github.com/SillyTavern/SillyTavern",
11 "hooks": {11 "hooks": {
12 "activate": "init"12 "activate": "init"
public/scripts/extensions/keepalive/settings.html+1 -1
@@ -16,7 +16,7 @@
16 <label for="keepalive_message" data-i18n="ext_keepalive_message">Keepalive message</label>16 <label for="keepalive_message" data-i18n="ext_keepalive_message">Keepalive message</label>
17 <input id="keepalive_message" class="text_pole" type="text" />17 <input id="keepalive_message" class="text_pole" type="text" />
1818
19 <small data-i18n="ext_keepalive_help">After this many seconds without activity on the active connection profile, the current chat plus this message (sent as a hidden user message) is submitted to that profile to keep its server-side prompt cache warm. The completion is capped to a single token and is never saved to the chat. The server owns the keepalive timer, while this tab renews its lease every 20 seconds; if the tab sleeps or closes, the server continues on schedule for up to five minutes after the last heartbeat. Only the profile you're currently using is pinged. Keepalive stays off until you send a new message in the current chat (opening, switching to, or reloading a chat isn't proof its prompt is still cached).</small>19 <small data-i18n="ext_keepalive_help">After this many seconds without activity on the active connection profile, the current chat plus this message (sent as a hidden user message) is submitted to that profile to keep its server-side prompt cache warm. The completion is capped to a single token and is never saved to the chat. The server owns the keepalive timer, while this tab renews its lease every 20 seconds; if the tab sleeps or closes, the server continues on schedule for up to five minutes after the last heartbeat. Only the profile you're currently using is pinged. Keepalive stays off until you send a message or start a foreground generation (including regenerate, swipe, or continue); merely opening, switching to, or reloading a chat is not proof its prompt is cached.</small>
2020
21 <hr>21 <hr>
2222