refac
This commit is contained in:
@@ -362,7 +362,7 @@
|
||||
onClose={() => showControls.set(false)}
|
||||
/>
|
||||
{:else if activeTab === 'files' && $selectedTerminalId}
|
||||
<FileNav onAttach={handleTerminalAttach} />
|
||||
<FileNav onAttach={handleTerminalAttach} {chatId} />
|
||||
{:else if activeTab === 'files' && codeInterpreterEnabled}
|
||||
<PyodideFileNav />
|
||||
{:else}
|
||||
@@ -513,7 +513,7 @@
|
||||
onClose={() => showControls.set(false)}
|
||||
/>
|
||||
{:else if activeTab === 'files' && $selectedTerminalId}
|
||||
<FileNav onAttach={handleTerminalAttach} overlay={dragged} />
|
||||
<FileNav onAttach={handleTerminalAttach} overlay={dragged} {chatId} />
|
||||
{:else if activeTab === 'files' && codeInterpreterEnabled}
|
||||
<PyodideFileNav overlay={dragged} />
|
||||
{:else}
|
||||
|
||||
@@ -49,6 +49,7 @@
|
||||
|
||||
export let onAttach: ((blob: Blob, name: string, contentType: string) => void) | null = null;
|
||||
export let overlay = false;
|
||||
export let chatId: string | null = null;
|
||||
|
||||
// ── Terminal panel state ────────────────────────────────────────────
|
||||
let terminalExpanded = false;
|
||||
@@ -215,30 +216,48 @@
|
||||
return url ? { url, key } : null;
|
||||
};
|
||||
|
||||
// Detect terminal changes — the explicit store references ensure
|
||||
// Detect terminal or chat changes — the explicit store references ensure
|
||||
// Svelte re-runs this block when any of them update.
|
||||
// The `mounted` flag prevents the initial run from racing with onMount.
|
||||
let prevTerminalUrl = '';
|
||||
let prevChatId = chatId;
|
||||
let mounted = false;
|
||||
$: {
|
||||
($selectedTerminalId, $terminalServers, $settings);
|
||||
const terminal = getTerminal();
|
||||
selectedTerminal = terminal;
|
||||
|
||||
if (terminal && terminal.url !== prevTerminalUrl) {
|
||||
prevTerminalUrl = terminal.url;
|
||||
loading = true;
|
||||
error = null;
|
||||
entries = [];
|
||||
(async () => {
|
||||
// Discover server features (terminal enabled/disabled)
|
||||
const config = await getTerminalConfig(terminal.url, terminal.key);
|
||||
terminalEnabled = config?.features?.terminal !== false;
|
||||
const chatChanged = chatId !== prevChatId;
|
||||
const oldChatId = prevChatId;
|
||||
if (chatChanged) prevChatId = chatId;
|
||||
|
||||
const rawCwd = await getCwd(terminal.url, terminal.key);
|
||||
const cwd = rawCwd ? normalizePath(rawCwd) : null;
|
||||
const dir = cwd ? (cwd.endsWith('/') ? cwd : cwd + '/') : '/';
|
||||
savedPath = dir;
|
||||
loadDir(dir);
|
||||
})();
|
||||
const terminalChanged = terminal && terminal.url !== prevTerminalUrl;
|
||||
if (terminalChanged) prevTerminalUrl = terminal.url;
|
||||
|
||||
if (mounted && terminal) {
|
||||
if (chatChanged && chatId && !oldChatId) {
|
||||
// Chat just got created (null → real ID): persist the current
|
||||
// browsed path as the new session's cwd — don't re-fetch.
|
||||
setCwd(terminal.url, terminal.key, savedPath, chatId);
|
||||
} else if (terminalChanged || chatChanged) {
|
||||
// Terminal switched, new chat started, or switched between
|
||||
// existing chats — re-fetch the session cwd.
|
||||
loading = true;
|
||||
error = null;
|
||||
entries = [];
|
||||
(async () => {
|
||||
if (terminalChanged) {
|
||||
const config = await getTerminalConfig(terminal.url, terminal.key);
|
||||
terminalEnabled = config?.features?.terminal !== false;
|
||||
}
|
||||
|
||||
const rawCwd = await getCwd(terminal.url, terminal.key, chatId ?? undefined);
|
||||
const cwd = rawCwd ? normalizePath(rawCwd) : null;
|
||||
const dir = cwd ? (cwd.endsWith('/') ? cwd : cwd + '/') : '/';
|
||||
savedPath = dir;
|
||||
loadDir(dir);
|
||||
})();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -316,7 +335,7 @@
|
||||
loading = false;
|
||||
|
||||
// Set working directory on the terminal server (fire-and-forget)
|
||||
setCwd(terminal.url, terminal.key, path);
|
||||
setCwd(terminal.url, terminal.key, path, chatId ?? undefined);
|
||||
|
||||
if (result === null) {
|
||||
error =
|
||||
@@ -736,14 +755,22 @@
|
||||
|
||||
if (!handledDisplayFile) {
|
||||
loading = true;
|
||||
if (savedPath === '/') {
|
||||
const rawCwd = await getCwd(terminal.url, terminal.key);
|
||||
|
||||
// Discover server features on initial mount
|
||||
const config = await getTerminalConfig(terminal.url, terminal.key);
|
||||
terminalEnabled = config?.features?.terminal !== false;
|
||||
|
||||
if (chatId || savedPath === '/') {
|
||||
// Fetch session-specific cwd from the server (or global default for new chats)
|
||||
const rawCwd = await getCwd(terminal.url, terminal.key, chatId ?? undefined);
|
||||
const cwd = rawCwd ? normalizePath(rawCwd) : null;
|
||||
if (cwd) savedPath = cwd.endsWith('/') ? cwd : cwd + '/';
|
||||
}
|
||||
loadDir(savedPath);
|
||||
}
|
||||
|
||||
mounted = true;
|
||||
|
||||
const onKeyDown = (e: KeyboardEvent) => {
|
||||
if (e.key === 'Shift') shiftKey = true;
|
||||
};
|
||||
@@ -1368,6 +1395,7 @@
|
||||
overlay={overlay || isDraggingHandle}
|
||||
bind:connected={terminalConnected}
|
||||
bind:connecting={terminalConnecting}
|
||||
{chatId}
|
||||
/>
|
||||
</div>
|
||||
{/if}
|
||||
|
||||
@@ -12,6 +12,7 @@
|
||||
const i18n = getContext('i18n');
|
||||
|
||||
export let overlay = false;
|
||||
export let chatId: string | null = null;
|
||||
|
||||
let terminalEl: HTMLDivElement;
|
||||
let term: Terminal | null = null;
|
||||
@@ -67,9 +68,11 @@
|
||||
authToken = apiKey;
|
||||
|
||||
// Create session
|
||||
const createHeaders: Record<string, string> = { Authorization: `Bearer ${apiKey}` };
|
||||
if (chatId) createHeaders['X-Session-Id'] = chatId;
|
||||
const res = await fetch(`${base}/api/terminals`, {
|
||||
method: 'POST',
|
||||
headers: { Authorization: `Bearer ${apiKey}` }
|
||||
headers: createHeaders
|
||||
});
|
||||
if (!res.ok) throw new Error(`Failed to create session: ${res.status}`);
|
||||
const session = await res.json();
|
||||
@@ -83,9 +86,11 @@
|
||||
authToken = token;
|
||||
|
||||
// Create session via proxy
|
||||
const proxyHeaders: Record<string, string> = { Authorization: `Bearer ${token}` };
|
||||
if (chatId) proxyHeaders['X-Session-Id'] = chatId;
|
||||
const res = await fetch(`${base}/terminals/${info.serverId}/api/terminals`, {
|
||||
method: 'POST',
|
||||
headers: { Authorization: `Bearer ${token}` }
|
||||
headers: proxyHeaders
|
||||
});
|
||||
if (!res.ok) throw new Error(`Failed to create session: ${res.status}`);
|
||||
const session = await res.json();
|
||||
|
||||
Reference in New Issue
Block a user