clay-server 2.27.1 → 2.28.0-beta.2
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/lib/daemon.js +21 -0
- package/lib/mcp-local.js +355 -0
- package/lib/project-connection.js +2 -0
- package/lib/project-loop.js +116 -34
- package/lib/project-mcp.js +371 -0
- package/lib/project-user-message.js +6 -3
- package/lib/project.js +51 -11
- package/lib/public/app.js +4 -0
- package/lib/public/css/filebrowser.css +204 -0
- package/lib/public/css/scheduler-modal.css +156 -1
- package/lib/public/css/scheduler.css +81 -0
- package/lib/public/index.html +99 -59
- package/lib/public/modules/app-loop-ui.js +85 -2
- package/lib/public/modules/app-messages.js +11 -1
- package/lib/public/modules/app-misc.js +104 -0
- package/lib/public/modules/mcp-ui.js +295 -0
- package/lib/public/modules/scheduler-config.js +241 -162
- package/lib/public/modules/scheduler-history.js +57 -5
- package/lib/public/modules/scheduler.js +80 -36
- package/lib/sdk-bridge.js +86 -17
- package/lib/server-mates.js +7 -2
- package/lib/server.js +6 -0
- package/lib/ws-schema.js +10 -0
- package/package.json +1 -1
package/lib/public/index.html
CHANGED
|
@@ -191,6 +191,7 @@
|
|
|
191
191
|
<button id="file-browser-btn"><i data-lucide="folder-tree"></i> <span>File browser</span></button>
|
|
192
192
|
<button id="terminal-sidebar-btn"><i data-lucide="square-terminal"></i> <span>Terminal</span><span id="terminal-sidebar-count" class="sidebar-badge hidden"></span></button>
|
|
193
193
|
<button id="sticky-notes-sidebar-btn"><i data-lucide="sticky-note"></i> <span>Sticky Notes</span><span id="sticky-notes-sidebar-count" class="sidebar-badge hidden"></span></button>
|
|
194
|
+
<button id="mcp-btn"><i data-lucide="cable"></i> <span>MCP Servers</span><span id="mcp-sidebar-count" class="sidebar-badge hidden"></span></button>
|
|
194
195
|
<button id="skills-btn"><i data-lucide="puzzle"></i> <span>Skills</span></button>
|
|
195
196
|
<button id="scheduler-btn"><i data-lucide="calendar-clock"></i> <span>Scheduled Tasks</span></button>
|
|
196
197
|
</div>
|
|
@@ -255,6 +256,7 @@
|
|
|
255
256
|
<button id="mate-memory-btn"><i data-lucide="brain"></i> <span>Memory</span><span id="mate-memory-count" class="sidebar-badge hidden"></span></button>
|
|
256
257
|
<button id="mate-knowledge-btn"><i data-lucide="book-open"></i> <span>Knowledge</span><span id="mate-knowledge-count" class="sidebar-badge hidden"></span></button>
|
|
257
258
|
<button id="mate-sticky-notes-btn"><i data-lucide="sticky-note"></i> <span>Sticky Notes</span></button>
|
|
259
|
+
<button id="mate-mcp-btn"><i data-lucide="cable"></i> <span>MCP Servers</span><span id="mate-mcp-sidebar-count" class="sidebar-badge hidden"></span></button>
|
|
258
260
|
<button id="mate-skills-btn"><i data-lucide="puzzle"></i> <span>Skills</span></button>
|
|
259
261
|
<button id="mate-scheduler-btn"><i data-lucide="calendar-clock"></i> <span>Scheduled Tasks</span></button>
|
|
260
262
|
</div>
|
|
@@ -1507,6 +1509,20 @@
|
|
|
1507
1509
|
</div>
|
|
1508
1510
|
</div>
|
|
1509
1511
|
|
|
1512
|
+
<!-- MCP Servers Modal -->
|
|
1513
|
+
<div id="mcp-modal" class="hidden">
|
|
1514
|
+
<div class="confirm-backdrop"></div>
|
|
1515
|
+
<div class="confirm-dialog mcp-dialog">
|
|
1516
|
+
<div class="mcp-header">
|
|
1517
|
+
<span class="mcp-title"><i data-lucide="cable"></i> MCP Servers</span>
|
|
1518
|
+
<button class="skills-close" id="mcp-modal-close"><i data-lucide="x"></i></button>
|
|
1519
|
+
</div>
|
|
1520
|
+
<div class="mcp-content" id="mcp-content">
|
|
1521
|
+
<p class="mcp-no-servers">No MCP servers detected. Configure in Clay Chrome Extension.</p>
|
|
1522
|
+
</div>
|
|
1523
|
+
</div>
|
|
1524
|
+
</div>
|
|
1525
|
+
|
|
1510
1526
|
<!-- Debate Modal (Wizard) -->
|
|
1511
1527
|
<div id="debate-modal" class="hidden">
|
|
1512
1528
|
<div class="debate-modal-backdrop"></div>
|
|
@@ -1672,6 +1688,7 @@
|
|
|
1672
1688
|
<div class="ralph-preview-tabs">
|
|
1673
1689
|
<button class="ralph-tab active" data-tab="prompt">PROMPT.md</button>
|
|
1674
1690
|
<button class="ralph-tab" data-tab="judge">JUDGE.md</button>
|
|
1691
|
+
<button class="ralph-tab" data-tab="model">Model</button>
|
|
1675
1692
|
</div>
|
|
1676
1693
|
<div id="ralph-preview-body" class="ralph-preview-body"></div>
|
|
1677
1694
|
<div class="ralph-preview-footer" id="ralph-preview-footer">
|
|
@@ -1899,8 +1916,6 @@
|
|
|
1899
1916
|
<div class="sched-create-date-chips">
|
|
1900
1917
|
<input type="date" class="sched-create-date-input" id="sched-create-date-picker" value="">
|
|
1901
1918
|
<input type="time" class="sched-create-time-input" id="sched-create-time" value="09:00">
|
|
1902
|
-
<button class="sched-create-recurrence-btn" id="sched-create-recurrence-btn" title="Recurrence"><i data-lucide="repeat"></i></button>
|
|
1903
|
-
<button class="sched-create-interval-btn" id="sched-create-interval-btn" title="Interval"><i data-lucide="timer"></i></button>
|
|
1904
1919
|
</div>
|
|
1905
1920
|
<button class="sched-create-close-btn" id="sched-create-cancel" title="Close"><i data-lucide="x"></i></button>
|
|
1906
1921
|
</div>
|
|
@@ -1925,7 +1940,7 @@
|
|
|
1925
1940
|
</div>
|
|
1926
1941
|
<input type="text" class="sched-create-title-input" id="sched-create-title" placeholder="Schedule Title" maxlength="80" spellcheck="false" autocomplete="off">
|
|
1927
1942
|
</div>
|
|
1928
|
-
<!-- Task
|
|
1943
|
+
<!-- Task -->
|
|
1929
1944
|
<div class="sched-create-row">
|
|
1930
1945
|
<i data-lucide="list-todo" class="sched-create-row-icon"></i>
|
|
1931
1946
|
<div class="sched-create-task-dropdown" id="sched-create-task-wrap">
|
|
@@ -1937,31 +1952,40 @@
|
|
|
1937
1952
|
<div class="sched-create-task-list hidden" id="sched-create-task-list"></div>
|
|
1938
1953
|
</div>
|
|
1939
1954
|
</div>
|
|
1940
|
-
<!--
|
|
1955
|
+
<!-- Review toggle -->
|
|
1941
1956
|
<div class="sched-create-row">
|
|
1957
|
+
<div class="sched-create-row-icon-spacer"></div>
|
|
1958
|
+
<label class="sched-review-toggle">
|
|
1959
|
+
<input type="checkbox" id="sched-review-check">
|
|
1960
|
+
<span class="sched-review-label">Review multiple times</span>
|
|
1961
|
+
<span class="sched-review-count hidden" id="sched-review-count">
|
|
1962
|
+
<input type="number" id="sched-create-iterations" min="2" max="100" value="3" class="sched-create-iter-input">
|
|
1963
|
+
<span class="sched-create-iter-hint">x</span>
|
|
1964
|
+
</span>
|
|
1965
|
+
</label>
|
|
1966
|
+
</div>
|
|
1967
|
+
<!-- Description (shown only when editing a record that has one) -->
|
|
1968
|
+
<div class="sched-create-row hidden" id="sched-create-desc-row">
|
|
1942
1969
|
<i data-lucide="align-left" class="sched-create-row-icon"></i>
|
|
1943
|
-
<textarea class="sched-create-row-textarea" id="sched-create-desc" rows="
|
|
1970
|
+
<textarea class="sched-create-row-textarea" id="sched-create-desc" rows="2" placeholder="Description"></textarea>
|
|
1944
1971
|
</div>
|
|
1945
|
-
<!--
|
|
1946
|
-
<div class="sched-
|
|
1947
|
-
<div class="sched-
|
|
1948
|
-
|
|
1949
|
-
|
|
1950
|
-
<
|
|
1951
|
-
<
|
|
1952
|
-
<
|
|
1953
|
-
<span class="sched-
|
|
1954
|
-
</
|
|
1972
|
+
<!-- Repeat accordion -->
|
|
1973
|
+
<div class="sched-accordion" id="sched-accordion-repeat">
|
|
1974
|
+
<div class="sched-accordion-divider"></div>
|
|
1975
|
+
<button class="sched-accordion-header" id="sched-accordion-repeat-header" type="button">
|
|
1976
|
+
<div class="sched-accordion-header-left">
|
|
1977
|
+
<i data-lucide="repeat" class="sched-accordion-icon"></i>
|
|
1978
|
+
<div class="sched-accordion-text">
|
|
1979
|
+
<span class="sched-accordion-title">Repeat</span>
|
|
1980
|
+
<span class="sched-accordion-subtitle" id="sched-accordion-repeat-subtitle">Which days to run</span>
|
|
1981
|
+
</div>
|
|
1955
1982
|
</div>
|
|
1956
|
-
|
|
1957
|
-
|
|
1958
|
-
|
|
1959
|
-
|
|
1960
|
-
</
|
|
1961
|
-
|
|
1962
|
-
<!-- Recurrence dropdown -->
|
|
1963
|
-
<div class="sched-create-recurrence-dropdown hidden" id="sched-create-recurrence-dropdown">
|
|
1964
|
-
<div class="sched-custom-repeat-panel" id="sched-custom-repeat-panel">
|
|
1983
|
+
<div class="sched-accordion-header-right">
|
|
1984
|
+
<span class="sched-accordion-clear hidden" id="sched-accordion-repeat-clear" title="Clear"><i data-lucide="x"></i></span>
|
|
1985
|
+
<i data-lucide="chevron-right" class="sched-accordion-chevron"></i>
|
|
1986
|
+
</div>
|
|
1987
|
+
</button>
|
|
1988
|
+
<div class="sched-accordion-body hidden" id="sched-accordion-repeat-body">
|
|
1965
1989
|
<div class="sched-custom-row">
|
|
1966
1990
|
<span class="sched-custom-label">Every</span>
|
|
1967
1991
|
<input type="number" class="sched-custom-interval" id="sched-custom-interval" value="1" min="1" max="99">
|
|
@@ -2006,7 +2030,6 @@
|
|
|
2006
2030
|
<span class="sched-custom-end-after-suffix">times</span>
|
|
2007
2031
|
</div>
|
|
2008
2032
|
</div>
|
|
2009
|
-
<!-- Inline calendar for "Until" date picking -->
|
|
2010
2033
|
<div class="sched-custom-end-calendar hidden" id="sched-custom-end-calendar">
|
|
2011
2034
|
<div class="sched-cal-header">
|
|
2012
2035
|
<span class="sched-cal-title" id="sched-cal-title">April 2026</span>
|
|
@@ -2020,48 +2043,65 @@
|
|
|
2020
2043
|
</div>
|
|
2021
2044
|
<div class="sched-cal-grid" id="sched-cal-grid"></div>
|
|
2022
2045
|
</div>
|
|
2023
|
-
<div class="sched-custom-actions">
|
|
2024
|
-
<button class="sched-btn sched-btn-cancel" id="sched-custom-cancel">Cancel</button>
|
|
2025
|
-
<button class="sched-btn sched-btn-save" id="sched-custom-ok">OK</button>
|
|
2026
|
-
</div>
|
|
2027
2046
|
</div>
|
|
2028
2047
|
</div>
|
|
2029
|
-
<!-- Interval
|
|
2030
|
-
<div class="sched-
|
|
2031
|
-
<div class="sched-
|
|
2032
|
-
|
|
2033
|
-
<
|
|
2034
|
-
|
|
2035
|
-
<
|
|
2048
|
+
<!-- Interval accordion -->
|
|
2049
|
+
<div class="sched-accordion" id="sched-accordion-interval">
|
|
2050
|
+
<div class="sched-accordion-divider"></div>
|
|
2051
|
+
<button class="sched-accordion-header" id="sched-accordion-interval-header" type="button">
|
|
2052
|
+
<div class="sched-accordion-header-left">
|
|
2053
|
+
<i data-lucide="timer" class="sched-accordion-icon"></i>
|
|
2054
|
+
<div class="sched-accordion-text">
|
|
2055
|
+
<span class="sched-accordion-title">Interval</span>
|
|
2056
|
+
<span class="sched-accordion-subtitle" id="sched-accordion-interval-subtitle">How often within each day</span>
|
|
2057
|
+
</div>
|
|
2036
2058
|
</div>
|
|
2037
|
-
|
|
2038
|
-
|
|
2039
|
-
|
|
2040
|
-
<div class="sched-interval-end-options">
|
|
2041
|
-
<button class="sched-interval-end-opt active" data-iend="allday">All day</button>
|
|
2042
|
-
<button class="sched-interval-end-opt" data-iend="after">Stop after</button>
|
|
2043
|
-
<button class="sched-interval-end-opt" data-iend="until">Stop at</button>
|
|
2059
|
+
<div class="sched-accordion-header-right">
|
|
2060
|
+
<span class="sched-accordion-clear hidden" id="sched-accordion-interval-clear" title="Clear"><i data-lucide="x"></i></span>
|
|
2061
|
+
<i data-lucide="chevron-right" class="sched-accordion-chevron"></i>
|
|
2044
2062
|
</div>
|
|
2045
|
-
|
|
2046
|
-
|
|
2047
|
-
|
|
2063
|
+
</button>
|
|
2064
|
+
<div class="sched-accordion-body hidden" id="sched-accordion-interval-body">
|
|
2065
|
+
<div class="sched-interval-custom-row">
|
|
2066
|
+
<span class="sched-custom-label">Every</span>
|
|
2067
|
+
<input type="number" class="sched-custom-interval" id="sched-interval-custom-value" value="10" min="1" max="999">
|
|
2068
|
+
<div class="sched-interval-unit-toggle" id="sched-interval-custom-unit">
|
|
2069
|
+
<button type="button" class="sched-interval-seg active" data-unit="minute">min</button><button type="button" class="sched-interval-seg" data-unit="hour">hrs</button>
|
|
2070
|
+
</div>
|
|
2048
2071
|
</div>
|
|
2049
|
-
<div class="sched-interval-end-
|
|
2050
|
-
<
|
|
2072
|
+
<div class="sched-interval-end-section hidden" id="sched-interval-end-section">
|
|
2073
|
+
<div class="sched-interval-end-divider"></div>
|
|
2074
|
+
<div class="sched-interval-end-options">
|
|
2075
|
+
<button class="sched-interval-end-opt active" data-iend="allday">All day</button>
|
|
2076
|
+
<button class="sched-interval-end-opt" data-iend="after">Stop after</button>
|
|
2077
|
+
<button class="sched-interval-end-opt" data-iend="until">Stop at</button>
|
|
2078
|
+
</div>
|
|
2079
|
+
<div class="sched-interval-end-after hidden" id="sched-interval-end-after-row">
|
|
2080
|
+
<input type="number" class="sched-interval-end-input" id="sched-interval-end-after" value="5" min="1" max="999">
|
|
2081
|
+
<span class="sched-interval-end-label">runs</span>
|
|
2082
|
+
</div>
|
|
2083
|
+
<div class="sched-interval-end-until hidden" id="sched-interval-end-until-row">
|
|
2084
|
+
<input type="time" class="sched-interval-end-time" id="sched-interval-end-time" value="18:00">
|
|
2085
|
+
</div>
|
|
2086
|
+
</div>
|
|
2087
|
+
<div class="sched-skip-running-row" id="sched-skip-running-row">
|
|
2088
|
+
<label class="sched-switch-label" for="sched-skip-running">
|
|
2089
|
+
<div class="sched-switch">
|
|
2090
|
+
<input type="checkbox" id="sched-skip-running" checked>
|
|
2091
|
+
<span class="sched-switch-slider"></span>
|
|
2092
|
+
</div>
|
|
2093
|
+
<span class="sched-switch-text">Skip if previous run still active</span>
|
|
2094
|
+
</label>
|
|
2051
2095
|
</div>
|
|
2052
2096
|
</div>
|
|
2053
|
-
|
|
2054
|
-
|
|
2055
|
-
|
|
2056
|
-
|
|
2057
|
-
|
|
2058
|
-
</div>
|
|
2059
|
-
<span class="sched-switch-text">Skip if previous run still active</span>
|
|
2060
|
-
</label>
|
|
2097
|
+
</div>
|
|
2098
|
+
<!-- Bottom bar -->
|
|
2099
|
+
<div class="sched-create-bottom">
|
|
2100
|
+
<div class="sched-create-bottom-left">
|
|
2101
|
+
<button class="sched-create-delete-btn hidden" id="sched-create-delete" title="Delete"><i data-lucide="trash-2"></i></button>
|
|
2061
2102
|
</div>
|
|
2062
|
-
<div class="sched-
|
|
2063
|
-
<button class="sched-
|
|
2064
|
-
<button class="sched-btn sched-btn-save" id="sched-interval-ok">OK</button>
|
|
2103
|
+
<div class="sched-create-bottom-right">
|
|
2104
|
+
<button class="sched-create-save-btn" id="sched-create-submit">Save</button>
|
|
2065
2105
|
</div>
|
|
2066
2106
|
</div>
|
|
2067
2107
|
</div>
|
|
@@ -8,6 +8,7 @@ import { getWs } from './ws-ref.js';
|
|
|
8
8
|
import { showConfirm } from './app-misc.js';
|
|
9
9
|
import { openRalphWizard } from './app-loop-wizard.js';
|
|
10
10
|
import { openSchedulerToTab } from './scheduler.js';
|
|
11
|
+
import { renderModelList, renderModeList, renderEffortBar, renderThinkingBar } from './settings-defaults.js';
|
|
11
12
|
import { showDebateSticky } from './app-debate-ui.js';
|
|
12
13
|
|
|
13
14
|
// Execution modal: module-internal UI var (not in store)
|
|
@@ -128,7 +129,11 @@ function startLoopFromUi() {
|
|
|
128
129
|
function sendLoopStart() {
|
|
129
130
|
var ws = getWs();
|
|
130
131
|
if (ws && ws.readyState === 1) {
|
|
131
|
-
|
|
132
|
+
var msg = { type: "loop_start", maxIterations: pendingIterations };
|
|
133
|
+
if (Object.keys(_previewLoopSettings).length > 0) {
|
|
134
|
+
msg.settings = _previewLoopSettings;
|
|
135
|
+
}
|
|
136
|
+
ws.send(JSON.stringify(msg));
|
|
132
137
|
}
|
|
133
138
|
}
|
|
134
139
|
|
|
@@ -526,10 +531,14 @@ export function updateExecModalStatus() {
|
|
|
526
531
|
}
|
|
527
532
|
|
|
528
533
|
export function openRalphPreviewModal() {
|
|
534
|
+
// Only show for loop (ralph) source, not scheduled tasks
|
|
535
|
+
var st = store.getState();
|
|
536
|
+
if (st.ralphCraftingSource !== "ralph") return;
|
|
537
|
+
|
|
529
538
|
var modal = document.getElementById("ralph-preview-modal");
|
|
530
539
|
if (!modal) return;
|
|
531
540
|
|
|
532
|
-
var wizData =
|
|
541
|
+
var wizData = st.wizardData || {};
|
|
533
542
|
var isSimple = wizData.loopMode === "simple";
|
|
534
543
|
|
|
535
544
|
// Set defaults if not yet set
|
|
@@ -557,6 +566,7 @@ export function openRalphPreviewModal() {
|
|
|
557
566
|
var runBtn = document.getElementById("ralph-preview-run");
|
|
558
567
|
if (runBtn) runBtn.disabled = !store.getState().ralphFilesReady.bothReady;
|
|
559
568
|
|
|
569
|
+
_previewLoopSettings = {};
|
|
560
570
|
showRalphPreviewTab("prompt");
|
|
561
571
|
modal.classList.remove("hidden");
|
|
562
572
|
refreshIcons();
|
|
@@ -568,6 +578,11 @@ function closeRalphPreviewModal() {
|
|
|
568
578
|
if (modal) modal.classList.add("hidden");
|
|
569
579
|
}
|
|
570
580
|
|
|
581
|
+
// Pending loop settings for the preview modal (saved to LOOP.json on launch)
|
|
582
|
+
var _previewLoopSettings = {};
|
|
583
|
+
|
|
584
|
+
function getPreviewLoopSettings() { return _previewLoopSettings; }
|
|
585
|
+
|
|
571
586
|
function showRalphPreviewTab(tab) {
|
|
572
587
|
var tabs = document.querySelectorAll("#ralph-preview-modal .ralph-tab");
|
|
573
588
|
for (var i = 0; i < tabs.length; i++) {
|
|
@@ -579,6 +594,12 @@ function showRalphPreviewTab(tab) {
|
|
|
579
594
|
}
|
|
580
595
|
var body = document.getElementById("ralph-preview-body");
|
|
581
596
|
if (!body) return;
|
|
597
|
+
|
|
598
|
+
if (tab === "model") {
|
|
599
|
+
renderPreviewModelTab(body);
|
|
600
|
+
return;
|
|
601
|
+
}
|
|
602
|
+
|
|
582
603
|
var _rpc = store.getState().ralphPreviewContent;
|
|
583
604
|
var content = tab === "prompt" ? _rpc.prompt : _rpc.judge;
|
|
584
605
|
if (typeof marked !== "undefined" && marked.parse) {
|
|
@@ -587,3 +608,65 @@ function showRalphPreviewTab(tab) {
|
|
|
587
608
|
body.textContent = content;
|
|
588
609
|
}
|
|
589
610
|
}
|
|
611
|
+
|
|
612
|
+
function renderPreviewModelTab(bodyEl) {
|
|
613
|
+
var s = store.getState();
|
|
614
|
+
|
|
615
|
+
bodyEl.innerHTML =
|
|
616
|
+
'<div class="scheduler-model-settings">' +
|
|
617
|
+
'<div class="settings-card"><div class="settings-field">' +
|
|
618
|
+
'<label class="settings-label">Model</label>' +
|
|
619
|
+
'<div class="settings-hint">Choose the Claude model for this loop.</div>' +
|
|
620
|
+
'<div id="rp-model-list" class="settings-model-list"></div>' +
|
|
621
|
+
'</div></div>' +
|
|
622
|
+
'<div class="settings-card"><div class="settings-field">' +
|
|
623
|
+
'<label class="settings-label">Mode</label>' +
|
|
624
|
+
'<div class="settings-hint">Controls how Claude handles tool use and file edits.</div>' +
|
|
625
|
+
'<div id="rp-mode-list" class="settings-model-list"></div>' +
|
|
626
|
+
'</div></div>' +
|
|
627
|
+
'<div class="settings-card"><div class="settings-field">' +
|
|
628
|
+
'<label class="settings-label">Effort</label>' +
|
|
629
|
+
'<div class="settings-hint">Controls how much thinking effort Claude puts into responses.</div>' +
|
|
630
|
+
'<div class="settings-btn-group" id="rp-effort-bar"></div>' +
|
|
631
|
+
'</div></div>' +
|
|
632
|
+
'<div class="settings-card"><div class="settings-field">' +
|
|
633
|
+
'<label class="settings-label">Thinking</label>' +
|
|
634
|
+
'<div class="settings-hint">Controls whether Claude shows its reasoning process.</div>' +
|
|
635
|
+
'<div class="settings-btn-group" id="rp-thinking-bar"></div>' +
|
|
636
|
+
'<div id="rp-thinking-budget-row" class="settings-budget-row" style="display:none">' +
|
|
637
|
+
'<label class="settings-budget-label">Budget tokens</label>' +
|
|
638
|
+
'<input id="rp-thinking-budget" type="number" class="settings-budget-input" min="1024" max="128000" step="1024" value="10000">' +
|
|
639
|
+
'</div>' +
|
|
640
|
+
'</div></div>' +
|
|
641
|
+
'</div>';
|
|
642
|
+
|
|
643
|
+
function savePreviewSetting(key, value) {
|
|
644
|
+
_previewLoopSettings[key] = value;
|
|
645
|
+
}
|
|
646
|
+
|
|
647
|
+
var opts = {
|
|
648
|
+
models: s.currentModels || [],
|
|
649
|
+
currentModel: _previewLoopSettings.model || "",
|
|
650
|
+
currentMode: _previewLoopSettings.permissionMode || "default",
|
|
651
|
+
currentEffort: _previewLoopSettings.effort || "medium",
|
|
652
|
+
currentThinking: _previewLoopSettings.thinking || "adaptive",
|
|
653
|
+
currentThinkingBudget: _previewLoopSettings.thinkingBudget || 10000,
|
|
654
|
+
sendMsg: function (msgType, data) {
|
|
655
|
+
if (msgType === "rp_set_model") savePreviewSetting("model", data.model);
|
|
656
|
+
else if (msgType === "rp_set_mode") savePreviewSetting("permissionMode", data.mode);
|
|
657
|
+
else if (msgType === "rp_set_effort") savePreviewSetting("effort", data.effort);
|
|
658
|
+
else if (msgType === "set_thinking") {
|
|
659
|
+
savePreviewSetting("thinking", data.thinking);
|
|
660
|
+
if (data.budgetTokens) savePreviewSetting("thinkingBudget", data.budgetTokens);
|
|
661
|
+
}
|
|
662
|
+
},
|
|
663
|
+
modelMsgType: "rp_set_model",
|
|
664
|
+
modeMsgType: "rp_set_mode",
|
|
665
|
+
effortMsgType: "rp_set_effort",
|
|
666
|
+
};
|
|
667
|
+
|
|
668
|
+
renderModelList("rp", opts);
|
|
669
|
+
renderModeList("rp", opts);
|
|
670
|
+
renderEffortBar("rp", opts);
|
|
671
|
+
renderThinkingBar("rp", opts);
|
|
672
|
+
}
|
|
@@ -31,7 +31,8 @@ import { handleSkillInstalled, handleSkillUninstalled } from './skills.js';
|
|
|
31
31
|
import { showRewindModal, onRewindComplete, setRewindMode, onRewindError, clearPendingRewindUuid, addRewindButton } from './rewind.js';
|
|
32
32
|
import { checkAdminAccess } from './admin.js';
|
|
33
33
|
import { mateAvatarUrl } from './avatar.js';
|
|
34
|
-
import { showImageModal, sendExtensionCommand } from './app-misc.js';
|
|
34
|
+
import { showImageModal, sendExtensionCommand, handleMcpToolCallMessage } from './app-misc.js';
|
|
35
|
+
import { handleMcpServersState } from './mcp-ui.js';
|
|
35
36
|
import { handleLoopRegistryUpdated, handleScheduleRunStarted, handleScheduleRunFinished, handleLoopScheduled, isSchedulerOpen, enterCraftingMode, exitCraftingMode, handleLoopRegistryFiles } from './scheduler.js';
|
|
36
37
|
|
|
37
38
|
// --- App module imports ---
|
|
@@ -999,6 +1000,14 @@ export function processMessage(msg) {
|
|
|
999
1000
|
sendExtensionCommand(msg.command, msg.args, msg.requestId);
|
|
1000
1001
|
break;
|
|
1001
1002
|
|
|
1003
|
+
case "mcp_tool_call":
|
|
1004
|
+
handleMcpToolCallMessage(msg);
|
|
1005
|
+
break;
|
|
1006
|
+
|
|
1007
|
+
case "mcp_servers_state":
|
|
1008
|
+
handleMcpServersState(msg);
|
|
1009
|
+
break;
|
|
1010
|
+
|
|
1002
1011
|
case "term_created":
|
|
1003
1012
|
handleTermCreated(msg);
|
|
1004
1013
|
if (store.getState().pendingTermCommand) {
|
|
@@ -1467,6 +1476,7 @@ export function processMessage(msg) {
|
|
|
1467
1476
|
showLoopBanner(false);
|
|
1468
1477
|
updateLoopButton();
|
|
1469
1478
|
enableMainInput();
|
|
1479
|
+
updateLoopInputVisibility(null);
|
|
1470
1480
|
var loopLabel = _lfbn || "Loop";
|
|
1471
1481
|
var finishMsg = msg.reason === "pass"
|
|
1472
1482
|
? loopLabel + " completed successfully after " + msg.iterations + " iteration(s)."
|
|
@@ -5,6 +5,7 @@ import { refreshIcons, iconHtml } from './icons.js';
|
|
|
5
5
|
import { escapeHtml, copyToClipboard } from './utils.js';
|
|
6
6
|
import { getWs } from './ws-ref.js';
|
|
7
7
|
import { updateBrowserTabList } from './context-sources.js';
|
|
8
|
+
import { setExtensionConnected } from './mcp-ui.js';
|
|
8
9
|
|
|
9
10
|
// --- Module-owned state ---
|
|
10
11
|
var confirmCallback = null;
|
|
@@ -95,6 +96,7 @@ export function initMisc() {
|
|
|
95
96
|
var msg = event.data.payload;
|
|
96
97
|
|
|
97
98
|
if (msg.type === "clay_ext_tab_list") {
|
|
99
|
+
setExtensionConnected(true);
|
|
98
100
|
updateBrowserTabList(msg.tabs);
|
|
99
101
|
// Also inform server about tab list
|
|
100
102
|
var ws = getWs();
|
|
@@ -108,9 +110,111 @@ export function initMisc() {
|
|
|
108
110
|
if (msg.type === "clay_ext_result") {
|
|
109
111
|
handleExtensionResult(msg.requestId, msg.result);
|
|
110
112
|
}
|
|
113
|
+
if (msg.type === "clay_ext_disconnected") {
|
|
114
|
+
setExtensionConnected(false);
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
// MCP bridge: extension reports available MCP servers
|
|
118
|
+
if (msg.type === "mcp_servers_available") {
|
|
119
|
+
var ws2 = getWs();
|
|
120
|
+
if (ws2 && ws2.readyState === 1) {
|
|
121
|
+
ws2.send(JSON.stringify({
|
|
122
|
+
type: "mcp_servers_available",
|
|
123
|
+
servers: msg.servers,
|
|
124
|
+
hostConnected: msg.hostConnected
|
|
125
|
+
}));
|
|
126
|
+
}
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
// MCP bridge: tool result from extension
|
|
130
|
+
if (msg.type === "mcp_tool_result") {
|
|
131
|
+
var ws3 = getWs();
|
|
132
|
+
if (ws3 && ws3.readyState === 1) {
|
|
133
|
+
ws3.send(JSON.stringify({
|
|
134
|
+
type: msg.error ? "mcp_tool_error" : "mcp_tool_result",
|
|
135
|
+
callId: msg.callId,
|
|
136
|
+
result: msg.result || null,
|
|
137
|
+
error: msg.error || null
|
|
138
|
+
}));
|
|
139
|
+
}
|
|
140
|
+
}
|
|
111
141
|
});
|
|
112
142
|
}
|
|
113
143
|
|
|
144
|
+
// Forward an MCP tool call from the server to the Chrome extension
|
|
145
|
+
export function forwardMcpToolCall(msg) {
|
|
146
|
+
window.postMessage({
|
|
147
|
+
source: "clay-page",
|
|
148
|
+
payload: {
|
|
149
|
+
type: "clay_mcp_tool_call",
|
|
150
|
+
callId: msg.callId,
|
|
151
|
+
server: msg.server,
|
|
152
|
+
method: msg.method,
|
|
153
|
+
params: msg.params,
|
|
154
|
+
}
|
|
155
|
+
}, "*");
|
|
156
|
+
}
|
|
157
|
+
|
|
158
|
+
// Forward an MCP tool call directly via HTTP for HTTP-transport servers
|
|
159
|
+
var _httpMcpServers = {}; // name -> url
|
|
160
|
+
export function setHttpMcpServers(servers) {
|
|
161
|
+
_httpMcpServers = {};
|
|
162
|
+
for (var i = 0; i < servers.length; i++) {
|
|
163
|
+
if (servers[i].transport === "http" && servers[i].url) {
|
|
164
|
+
_httpMcpServers[servers[i].name] = servers[i].url;
|
|
165
|
+
}
|
|
166
|
+
}
|
|
167
|
+
}
|
|
168
|
+
|
|
169
|
+
export function handleMcpToolCallMessage(msg) {
|
|
170
|
+
var httpUrl = _httpMcpServers[msg.server];
|
|
171
|
+
if (httpUrl) {
|
|
172
|
+
// HTTP transport: call directly via fetch
|
|
173
|
+
fetch(httpUrl, {
|
|
174
|
+
method: "POST",
|
|
175
|
+
headers: { "Content-Type": "application/json" },
|
|
176
|
+
body: JSON.stringify({
|
|
177
|
+
jsonrpc: "2.0",
|
|
178
|
+
id: msg.callId,
|
|
179
|
+
method: msg.method,
|
|
180
|
+
params: msg.params,
|
|
181
|
+
}),
|
|
182
|
+
})
|
|
183
|
+
.then(function (resp) { return resp.json(); })
|
|
184
|
+
.then(function (data) {
|
|
185
|
+
var ws = getWs();
|
|
186
|
+
if (ws && ws.readyState === 1) {
|
|
187
|
+
if (data.error) {
|
|
188
|
+
ws.send(JSON.stringify({
|
|
189
|
+
type: "mcp_tool_error",
|
|
190
|
+
callId: msg.callId,
|
|
191
|
+
error: data.error.message || JSON.stringify(data.error),
|
|
192
|
+
}));
|
|
193
|
+
} else {
|
|
194
|
+
ws.send(JSON.stringify({
|
|
195
|
+
type: "mcp_tool_result",
|
|
196
|
+
callId: msg.callId,
|
|
197
|
+
result: data.result,
|
|
198
|
+
}));
|
|
199
|
+
}
|
|
200
|
+
}
|
|
201
|
+
})
|
|
202
|
+
.catch(function (err) {
|
|
203
|
+
var ws = getWs();
|
|
204
|
+
if (ws && ws.readyState === 1) {
|
|
205
|
+
ws.send(JSON.stringify({
|
|
206
|
+
type: "mcp_tool_error",
|
|
207
|
+
callId: msg.callId,
|
|
208
|
+
error: "HTTP MCP fetch failed: " + err.message,
|
|
209
|
+
}));
|
|
210
|
+
}
|
|
211
|
+
});
|
|
212
|
+
} else {
|
|
213
|
+
// stdio transport: forward to extension
|
|
214
|
+
forwardMcpToolCall(msg);
|
|
215
|
+
}
|
|
216
|
+
}
|
|
217
|
+
|
|
114
218
|
export function showImageModal(src) {
|
|
115
219
|
var modal = document.getElementById("image-modal");
|
|
116
220
|
var img = document.getElementById("image-modal-img");
|