@agent-link/server 0.1.54 → 0.1.56
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/package.json +1 -1
- package/web/app.js +28 -0
- package/web/modules/connection.js +2 -0
- package/web/modules/sidebar.js +49 -0
- package/web/style.css +71 -0
package/package.json
CHANGED
package/web/app.js
CHANGED
|
@@ -68,6 +68,10 @@ const App = {
|
|
|
68
68
|
const deleteConfirmOpen = ref(false);
|
|
69
69
|
const deleteConfirmTitle = ref('');
|
|
70
70
|
|
|
71
|
+
// Working directory history state
|
|
72
|
+
const workDirHistory = ref([]);
|
|
73
|
+
const workDirHistoryOpen = ref(false);
|
|
74
|
+
|
|
71
75
|
// File attachment state
|
|
72
76
|
const attachments = ref([]);
|
|
73
77
|
const fileInputRef = ref(null);
|
|
@@ -141,6 +145,7 @@ const App = {
|
|
|
141
145
|
folderPickerOpen, folderPickerPath, folderPickerEntries,
|
|
142
146
|
folderPickerLoading, folderPickerSelected, streaming,
|
|
143
147
|
deleteConfirmOpen, deleteConfirmTitle,
|
|
148
|
+
workDirHistory, workDirHistoryOpen,
|
|
144
149
|
});
|
|
145
150
|
|
|
146
151
|
const { connect, wsSend, closeWs } = createConnection({
|
|
@@ -278,6 +283,12 @@ const App = {
|
|
|
278
283
|
deleteSession: sidebar.deleteSession,
|
|
279
284
|
confirmDeleteSession: sidebar.confirmDeleteSession,
|
|
280
285
|
cancelDeleteSession: sidebar.cancelDeleteSession,
|
|
286
|
+
// Working directory history
|
|
287
|
+
workDirHistory, workDirHistoryOpen,
|
|
288
|
+
selectWorkDirHistory: sidebar.selectWorkDirHistory,
|
|
289
|
+
removeWorkDirHistory: sidebar.removeWorkDirHistory,
|
|
290
|
+
toggleWorkDirHistory: sidebar.toggleWorkDirHistory,
|
|
291
|
+
selectRecentDir: sidebar.selectRecentDir,
|
|
281
292
|
// File attachments
|
|
282
293
|
attachments, fileInputRef, dragOver,
|
|
283
294
|
triggerFileInput: fileAttach.triggerFileInput,
|
|
@@ -610,6 +621,23 @@ const App = {
|
|
|
610
621
|
</button>
|
|
611
622
|
<input class="folder-picker-path-input" type="text" v-model="folderPickerPath" @keydown.enter="folderPickerGoToPath" placeholder="Enter path..." spellcheck="false" />
|
|
612
623
|
</div>
|
|
624
|
+
<div v-if="workDirHistory.length > 0" class="folder-picker-recent">
|
|
625
|
+
<div class="folder-picker-recent-label">Recent</div>
|
|
626
|
+
<div
|
|
627
|
+
v-for="dir in workDirHistory" :key="dir"
|
|
628
|
+
:class="['folder-picker-recent-item', { active: dir === workDir }]"
|
|
629
|
+
@click="selectRecentDir(dir)"
|
|
630
|
+
:title="dir"
|
|
631
|
+
>
|
|
632
|
+
<svg viewBox="0 0 24 24" width="13" height="13"><path fill="currentColor" d="M13 3a9 9 0 0 0-9 9H1l3.89 3.89.07.14L9 12H6c0-3.87 3.13-7 7-7s7 3.13 7 7-3.13 7-7 7c-1.93 0-3.68-.79-4.94-2.06l-1.42 1.42A8.954 8.954 0 0 0 13 21a9 9 0 0 0 0-18zm-1 5v5l4.28 2.54.72-1.21-3.5-2.08V8H12z"/></svg>
|
|
633
|
+
<span class="folder-picker-recent-path">{{ dir }}</span>
|
|
634
|
+
<button
|
|
635
|
+
class="folder-picker-recent-remove"
|
|
636
|
+
@click.stop="removeWorkDirHistory(dir)"
|
|
637
|
+
title="Remove from history"
|
|
638
|
+
>×</button>
|
|
639
|
+
</div>
|
|
640
|
+
</div>
|
|
613
641
|
<div class="folder-picker-list">
|
|
614
642
|
<div v-if="folderPickerLoading" class="folder-picker-loading">
|
|
615
643
|
<div class="history-loading-spinner"></div>
|
|
@@ -145,6 +145,7 @@ export function createConnection(deps) {
|
|
|
145
145
|
hostname.value = msg.agent.hostname || '';
|
|
146
146
|
workDir.value = msg.agent.workDir;
|
|
147
147
|
agentVersion.value = msg.agent.version || '';
|
|
148
|
+
sidebar.addToWorkDirHistory(msg.agent.workDir);
|
|
148
149
|
const savedDir = localStorage.getItem('agentlink-workdir');
|
|
149
150
|
if (savedDir && savedDir !== msg.agent.workDir) {
|
|
150
151
|
wsSend({ type: 'change_workdir', workDir: savedDir });
|
|
@@ -341,6 +342,7 @@ export function createConnection(deps) {
|
|
|
341
342
|
} else if (msg.type === 'workdir_changed') {
|
|
342
343
|
workDir.value = msg.workDir;
|
|
343
344
|
localStorage.setItem('agentlink-workdir', msg.workDir);
|
|
345
|
+
sidebar.addToWorkDirHistory(msg.workDir);
|
|
344
346
|
messages.value = [];
|
|
345
347
|
toolMsgMap.clear();
|
|
346
348
|
visibleLimit.value = 50;
|
package/web/modules/sidebar.js
CHANGED
|
@@ -31,6 +31,53 @@ export function createSidebar(deps) {
|
|
|
31
31
|
folderPickerLoading, folderPickerSelected, streaming,
|
|
32
32
|
} = deps;
|
|
33
33
|
|
|
34
|
+
// ── Working directory history ──
|
|
35
|
+
|
|
36
|
+
const WORKDIR_HISTORY_KEY = 'agentlink-workdir-history';
|
|
37
|
+
const MAX_HISTORY = 10;
|
|
38
|
+
const workDirHistory = deps.workDirHistory;
|
|
39
|
+
const workDirHistoryOpen = deps.workDirHistoryOpen;
|
|
40
|
+
|
|
41
|
+
// Load from localStorage on init
|
|
42
|
+
try {
|
|
43
|
+
const saved = localStorage.getItem(WORKDIR_HISTORY_KEY);
|
|
44
|
+
if (saved) workDirHistory.value = JSON.parse(saved);
|
|
45
|
+
} catch { /* ignore */ }
|
|
46
|
+
|
|
47
|
+
function addToWorkDirHistory(dir) {
|
|
48
|
+
if (!dir) return;
|
|
49
|
+
const list = workDirHistory.value.filter(d => d !== dir);
|
|
50
|
+
list.unshift(dir);
|
|
51
|
+
if (list.length > MAX_HISTORY) list.length = MAX_HISTORY;
|
|
52
|
+
workDirHistory.value = list;
|
|
53
|
+
localStorage.setItem(WORKDIR_HISTORY_KEY, JSON.stringify(list));
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
function selectWorkDirHistory(dir) {
|
|
57
|
+
workDirHistoryOpen.value = false;
|
|
58
|
+
if (dir === workDir.value) return;
|
|
59
|
+
wsSend({ type: 'change_workdir', workDir: dir });
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
function selectRecentDir(dir) {
|
|
63
|
+
if (dir === workDir.value) {
|
|
64
|
+
folderPickerOpen.value = false;
|
|
65
|
+
return;
|
|
66
|
+
}
|
|
67
|
+
folderPickerOpen.value = false;
|
|
68
|
+
wsSend({ type: 'change_workdir', workDir: dir });
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
function removeWorkDirHistory(dir) {
|
|
72
|
+
const list = workDirHistory.value.filter(d => d !== dir);
|
|
73
|
+
workDirHistory.value = list;
|
|
74
|
+
localStorage.setItem(WORKDIR_HISTORY_KEY, JSON.stringify(list));
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
function toggleWorkDirHistory() {
|
|
78
|
+
workDirHistoryOpen.value = !workDirHistoryOpen.value;
|
|
79
|
+
}
|
|
80
|
+
|
|
34
81
|
// ── Session management ──
|
|
35
82
|
|
|
36
83
|
function requestSessionList() {
|
|
@@ -207,6 +254,8 @@ export function createSidebar(deps) {
|
|
|
207
254
|
return {
|
|
208
255
|
requestSessionList, resumeSession, newConversation, toggleSidebar,
|
|
209
256
|
deleteSession, confirmDeleteSession, cancelDeleteSession,
|
|
257
|
+
addToWorkDirHistory, selectWorkDirHistory, removeWorkDirHistory, toggleWorkDirHistory,
|
|
258
|
+
selectRecentDir,
|
|
210
259
|
openFolderPicker, folderPickerNavigateUp, folderPickerSelectItem,
|
|
211
260
|
folderPickerEnter, folderPickerGoToPath, confirmFolderPicker,
|
|
212
261
|
groupedSessions,
|
package/web/style.css
CHANGED
|
@@ -1747,6 +1747,77 @@ body {
|
|
|
1747
1747
|
cursor: not-allowed;
|
|
1748
1748
|
}
|
|
1749
1749
|
|
|
1750
|
+
/* ── Folder Picker: Recent directories ── */
|
|
1751
|
+
.folder-picker-recent {
|
|
1752
|
+
border-bottom: 1px solid var(--border);
|
|
1753
|
+
padding: 6px 0;
|
|
1754
|
+
}
|
|
1755
|
+
|
|
1756
|
+
.folder-picker-recent-label {
|
|
1757
|
+
padding: 4px 16px 2px;
|
|
1758
|
+
font-size: 0.7rem;
|
|
1759
|
+
font-weight: 600;
|
|
1760
|
+
text-transform: uppercase;
|
|
1761
|
+
letter-spacing: 0.04em;
|
|
1762
|
+
color: var(--text-secondary);
|
|
1763
|
+
}
|
|
1764
|
+
|
|
1765
|
+
.folder-picker-recent-item {
|
|
1766
|
+
display: flex;
|
|
1767
|
+
align-items: center;
|
|
1768
|
+
gap: 8px;
|
|
1769
|
+
padding: 5px 16px;
|
|
1770
|
+
font-size: 0.82rem;
|
|
1771
|
+
cursor: pointer;
|
|
1772
|
+
color: var(--text-primary);
|
|
1773
|
+
transition: background 0.1s;
|
|
1774
|
+
user-select: none;
|
|
1775
|
+
}
|
|
1776
|
+
|
|
1777
|
+
.folder-picker-recent-item:hover {
|
|
1778
|
+
background: var(--bg-tertiary);
|
|
1779
|
+
}
|
|
1780
|
+
|
|
1781
|
+
.folder-picker-recent-item.active {
|
|
1782
|
+
color: var(--accent);
|
|
1783
|
+
}
|
|
1784
|
+
|
|
1785
|
+
.folder-picker-recent-item svg {
|
|
1786
|
+
flex-shrink: 0;
|
|
1787
|
+
color: var(--text-secondary);
|
|
1788
|
+
}
|
|
1789
|
+
|
|
1790
|
+
.folder-picker-recent-item.active svg {
|
|
1791
|
+
color: var(--accent);
|
|
1792
|
+
}
|
|
1793
|
+
|
|
1794
|
+
.folder-picker-recent-path {
|
|
1795
|
+
flex: 1;
|
|
1796
|
+
overflow: hidden;
|
|
1797
|
+
text-overflow: ellipsis;
|
|
1798
|
+
white-space: nowrap;
|
|
1799
|
+
}
|
|
1800
|
+
|
|
1801
|
+
.folder-picker-recent-remove {
|
|
1802
|
+
background: none;
|
|
1803
|
+
border: none;
|
|
1804
|
+
color: var(--text-secondary);
|
|
1805
|
+
font-size: 1rem;
|
|
1806
|
+
cursor: pointer;
|
|
1807
|
+
padding: 0 4px;
|
|
1808
|
+
line-height: 1;
|
|
1809
|
+
opacity: 0;
|
|
1810
|
+
transition: opacity 0.15s, color 0.15s;
|
|
1811
|
+
}
|
|
1812
|
+
|
|
1813
|
+
.folder-picker-recent-item:hover .folder-picker-recent-remove {
|
|
1814
|
+
opacity: 1;
|
|
1815
|
+
}
|
|
1816
|
+
|
|
1817
|
+
.folder-picker-recent-remove:hover {
|
|
1818
|
+
color: var(--error);
|
|
1819
|
+
}
|
|
1820
|
+
|
|
1750
1821
|
/* ── File Upload: Attachment Bar ── */
|
|
1751
1822
|
.attachment-bar {
|
|
1752
1823
|
display: flex;
|