From 81faa7e70731e82b4e6f19a0f9cf46b5b8346bf0 Mon Sep 17 00:00:00 2001 From: Jiawei Zhao Date: Fri, 11 Sep 2026 15:48:09 +0800 Subject: [PATCH] refactor(ui): remove dead rail unarchive Archived tasks are filtered before rail projection. The restore branch was unreachable, so the rail contract no longer exposes it. Closes #5189 Generated-by: OpenAI Codex Signed-off-by: Jiawei Zhao --- .../ui/session-navigation-provider.tsx | 3 --- apps/desktop/stories/app-shell.stories.tsx | 1 - .../stories/session-rail-multi-select.stories.tsx | 1 - apps/desktop/stories/subagent-sessions.stories.tsx | 1 - .../__tests__/session-history-multi-select.test.tsx | 1 - .../__tests__/session-history-row-actions.test.tsx | 1 - packages/ui/src/conversation-copy.ts | 7 +++---- packages/ui/src/session-history-list.tsx | 11 +++-------- packages/ui/stories/session-list-panel.stories.tsx | 1 - 9 files changed, 6 insertions(+), 21 deletions(-) diff --git a/apps/desktop/src/renderer/features/session-navigation/ui/session-navigation-provider.tsx b/apps/desktop/src/renderer/features/session-navigation/ui/session-navigation-provider.tsx index f9e0799b89..12cc39731d 100644 --- a/apps/desktop/src/renderer/features/session-navigation/ui/session-navigation-provider.tsx +++ b/apps/desktop/src/renderer/features/session-navigation/ui/session-navigation-provider.tsx @@ -107,9 +107,6 @@ export function SessionNavigationProvider(props: SessionNavigationProviderProps) onArchive: (sessionId) => { void controller.commands.archiveSession(sessionId); }, - onUnarchive: (sessionId) => { - void controller.commands.unarchiveSession(sessionId); - }, onRename: (sessionId, name) => { void controller.commands.renameSession(sessionId, name); }, diff --git a/apps/desktop/stories/app-shell.stories.tsx b/apps/desktop/stories/app-shell.stories.tsx index 16e4bd739a..75220377e3 100644 --- a/apps/desktop/stories/app-shell.stories.tsx +++ b/apps/desktop/stories/app-shell.stories.tsx @@ -170,7 +170,6 @@ const catalogProjects: ProjectRecord[] = [ const sidebarRowActions: NonNullable = { onToggleFlag: noop, onArchive: noop, - onUnarchive: noop, onRename: noop, }; const projectRowActions: NonNullable = { diff --git a/apps/desktop/stories/session-rail-multi-select.stories.tsx b/apps/desktop/stories/session-rail-multi-select.stories.tsx index ae3465ce2a..10658d4483 100644 --- a/apps/desktop/stories/session-rail-multi-select.stories.tsx +++ b/apps/desktop/stories/session-rail-multi-select.stories.tsx @@ -90,7 +90,6 @@ const OPEN_SESSION_ID = 'rail-a'; const ROW_ACTIONS = { onToggleFlag: noop, onArchive: noop, - onUnarchive: noop, onRename: noop, }; diff --git a/apps/desktop/stories/subagent-sessions.stories.tsx b/apps/desktop/stories/subagent-sessions.stories.tsx index 5c6009c7f8..9c93a40354 100644 --- a/apps/desktop/stories/subagent-sessions.stories.tsx +++ b/apps/desktop/stories/subagent-sessions.stories.tsx @@ -285,7 +285,6 @@ const shell: Record = { const NOOP_ROW_ACTIONS = { onToggleFlag() {}, onArchive() {}, - onUnarchive() {}, onRename() {}, onDelete() {}, }; diff --git a/packages/ui/src/__tests__/session-history-multi-select.test.tsx b/packages/ui/src/__tests__/session-history-multi-select.test.tsx index adba3a3bc1..c3d0b000f1 100644 --- a/packages/ui/src/__tests__/session-history-multi-select.test.tsx +++ b/packages/ui/src/__tests__/session-history-multi-select.test.tsx @@ -113,7 +113,6 @@ function summary(id: string, overrides: Partial = {}): SessionSu const ROW_ACTIONS = { onToggleFlag: () => undefined, onArchive: () => undefined, - onUnarchive: () => undefined, onRename: () => undefined, }; diff --git a/packages/ui/src/__tests__/session-history-row-actions.test.tsx b/packages/ui/src/__tests__/session-history-row-actions.test.tsx index 63b74314c0..ca6b364e1e 100644 --- a/packages/ui/src/__tests__/session-history-row-actions.test.tsx +++ b/packages/ui/src/__tests__/session-history-row-actions.test.tsx @@ -66,7 +66,6 @@ const session: SessionSummary = { const rowActions: SessionRowActions = { onToggleFlag: () => undefined, onArchive: () => undefined, - onUnarchive: () => undefined, onRename: () => undefined, }; diff --git a/packages/ui/src/conversation-copy.ts b/packages/ui/src/conversation-copy.ts index 1bf10a43b4..b1187b84f3 100644 --- a/packages/ui/src/conversation-copy.ts +++ b/packages/ui/src/conversation-copy.ts @@ -433,7 +433,6 @@ export interface ConversationCopy { unpin: string; rename: string; archive: string; - unarchive: string; delete: string; pinned: string; /** Time-sort unpinned section title (SideNavSection). */ @@ -626,7 +625,7 @@ const CONVERSATION_COPY = { sessions: { status: { active: '可继续', running: '进行中', waiting_for_user: '等你确认', blocked: '需要处理', aborted: '已中止' }, blockedReason: { NO_REAL_CONNECTION: '等待配置可用模型连接', auth: '需要重新登录', permission_required: '等待权限确认', tool_failed: '工具调用失败', unknown: '运行中断,可重试' }, - listAriaLabel: '任务列表', showMore: '显示更多', showMoreAriaLabel: (count) => `显示 ${count} 条更多任务`, renameAriaLabel: '重命名任务', renameProjectTitle: '重命名项目', renameSubmit: '保存', respondingAriaLabel: '正在响应', respondingTitle: '任务正在流式响应中', staleTitle: '此任务使用的模型连接已不可用,发送时会切换到默认连接', staleAriaLabel: '任务已过期', stale: '已过期', unreadAriaLabel: '未读消息', actionsAriaLabel: (name) => `${name} 任务操作`, pin: '置顶', unpin: '取消置顶', rename: '重命名', archive: '归档', unarchive: '取消归档', delete: '删除', pinned: '置顶', recent: '最近', projects: '项目', groupByTime: '按时间', groupByProject: '按项目', groupingAriaLabel: '任务分组方式', projectActionsAriaLabel: (name) => `${name} 项目操作`, projectNewTask: '新建任务', projectRename: '重命名', projectArchive: '归档', projectRestore: '恢复', projectRelink: '重新定位', projectUnavailable: '项目目录不可用', archivedProjects: '已归档项目', archivedProjectsAriaLabel: '展开已归档项目', worktreeAriaLabel: 'Git 工作树', promptRailAriaLabel: '按提问跳转', emptyPrompt: '(空提问)', jumpToPrompt: (preview) => `跳到提问:${preview}`, pickedAriaLabel: '已选中', pinCount: (count) => `置顶 ${count} 项`, unpinCount: (count) => `取消置顶 ${count} 项`, archiveCount: (count) => `归档 ${count} 项`, + listAriaLabel: '任务列表', showMore: '显示更多', showMoreAriaLabel: (count) => `显示 ${count} 条更多任务`, renameAriaLabel: '重命名任务', renameProjectTitle: '重命名项目', renameSubmit: '保存', respondingAriaLabel: '正在响应', respondingTitle: '任务正在流式响应中', staleTitle: '此任务使用的模型连接已不可用,发送时会切换到默认连接', staleAriaLabel: '任务已过期', stale: '已过期', unreadAriaLabel: '未读消息', actionsAriaLabel: (name) => `${name} 任务操作`, pin: '置顶', unpin: '取消置顶', rename: '重命名', archive: '归档', delete: '删除', pinned: '置顶', recent: '最近', projects: '项目', groupByTime: '按时间', groupByProject: '按项目', groupingAriaLabel: '任务分组方式', projectActionsAriaLabel: (name) => `${name} 项目操作`, projectNewTask: '新建任务', projectRename: '重命名', projectArchive: '归档', projectRestore: '恢复', projectRelink: '重新定位', projectUnavailable: '项目目录不可用', archivedProjects: '已归档项目', archivedProjectsAriaLabel: '展开已归档项目', worktreeAriaLabel: 'Git 工作树', promptRailAriaLabel: '按提问跳转', emptyPrompt: '(空提问)', jumpToPrompt: (preview) => `跳到提问:${preview}`, pickedAriaLabel: '已选中', pinCount: (count) => `置顶 ${count} 项`, unpinCount: (count) => `取消置顶 ${count} 项`, archiveCount: (count) => `归档 ${count} 项`, }, }, 'zh-TW': { @@ -789,7 +788,7 @@ const CONVERSATION_COPY = { sessions: { status: { active: '可繼續', running: '進行中', waiting_for_user: '等你確認', blocked: '需要處理', aborted: '已中止' }, blockedReason: { NO_REAL_CONNECTION: '等待設定可用模型連線', auth: '需要重新登入', permission_required: '等待權限確認', tool_failed: '工具呼叫失敗', unknown: '執行中斷,可重試' }, - listAriaLabel: '任務列表', showMore: '顯示更多', showMoreAriaLabel: (count) => `顯示 ${count} 條更多工`, renameAriaLabel: '重新命名任務', renameProjectTitle: '重新命名專案', renameSubmit: '儲存', respondingAriaLabel: '正在響應', respondingTitle: '任務正在流式響應中', staleTitle: '此任務使用的模型連線已不可用,傳送時會切換到預設連線', staleAriaLabel: '任務已過期', stale: '已過期', unreadAriaLabel: '未讀訊息', actionsAriaLabel: (name) => `${name} 任務操作`, pin: '置頂', unpin: '取消置頂', rename: '重新命名', archive: '歸檔', unarchive: '取消歸檔', delete: '刪除', pinned: '置頂', recent: '最近', projects: '專案', groupByTime: '按時間', groupByProject: '按專案', groupingAriaLabel: '任務分組方式', projectActionsAriaLabel: (name) => `${name} 專案操作`, projectNewTask: '建立任務', projectRename: '重新命名', projectArchive: '歸檔', projectRestore: '恢復', projectRelink: '重新定位', projectUnavailable: '專案目錄不可用', archivedProjects: '已歸檔專案', archivedProjectsAriaLabel: '展開已歸檔專案', worktreeAriaLabel: 'Git 工作樹', promptRailAriaLabel: '按提問跳轉', emptyPrompt: '(空提問)', jumpToPrompt: (preview) => `跳到提問:${preview}`, pickedAriaLabel: '已選取', pinCount: (count) => `置頂 ${count} 項`, unpinCount: (count) => `取消置頂 ${count} 項`, archiveCount: (count) => `歸檔 ${count} 項`, + listAriaLabel: '任務列表', showMore: '顯示更多', showMoreAriaLabel: (count) => `顯示 ${count} 條更多工`, renameAriaLabel: '重新命名任務', renameProjectTitle: '重新命名專案', renameSubmit: '儲存', respondingAriaLabel: '正在響應', respondingTitle: '任務正在流式響應中', staleTitle: '此任務使用的模型連線已不可用,傳送時會切換到預設連線', staleAriaLabel: '任務已過期', stale: '已過期', unreadAriaLabel: '未讀訊息', actionsAriaLabel: (name) => `${name} 任務操作`, pin: '置頂', unpin: '取消置頂', rename: '重新命名', archive: '歸檔', delete: '刪除', pinned: '置頂', recent: '最近', projects: '專案', groupByTime: '按時間', groupByProject: '按專案', groupingAriaLabel: '任務分組方式', projectActionsAriaLabel: (name) => `${name} 專案操作`, projectNewTask: '建立任務', projectRename: '重新命名', projectArchive: '歸檔', projectRestore: '恢復', projectRelink: '重新定位', projectUnavailable: '專案目錄不可用', archivedProjects: '已歸檔專案', archivedProjectsAriaLabel: '展開已歸檔專案', worktreeAriaLabel: 'Git 工作樹', promptRailAriaLabel: '按提問跳轉', emptyPrompt: '(空提問)', jumpToPrompt: (preview) => `跳到提問:${preview}`, pickedAriaLabel: '已選取', pinCount: (count) => `置頂 ${count} 項`, unpinCount: (count) => `取消置頂 ${count} 項`, archiveCount: (count) => `歸檔 ${count} 項`, }, }, en: { @@ -978,7 +977,7 @@ const CONVERSATION_COPY = { sessions: { status: { active: 'Ready', running: 'Running', waiting_for_user: 'Waiting for you', blocked: 'Needs attention', aborted: 'Stopped' }, blockedReason: { NO_REAL_CONNECTION: 'Waiting for an available model connection', auth: 'Sign in again', permission_required: 'Waiting for permission', tool_failed: 'Tool call failed', unknown: 'Run interrupted; retry available' }, - listAriaLabel: 'Task list', showMore: 'Show more', showMoreAriaLabel: (count) => `Show ${count} more tasks`, renameAriaLabel: 'Rename task', renameProjectTitle: 'Rename project', renameSubmit: 'Save', respondingAriaLabel: 'Responding', respondingTitle: 'This task is streaming a response', staleTitle: 'This task\'s model connection is unavailable; sending will switch to the default connection', staleAriaLabel: 'Stale task', stale: 'Stale', unreadAriaLabel: 'Unread messages', actionsAriaLabel: (name) => `${name} task actions`, pin: 'Pin', unpin: 'Unpin', rename: 'Rename', archive: 'Archive', unarchive: 'Unarchive', delete: 'Delete', pinned: 'Pinned', recent: 'Recent', projects: 'Projects', groupByTime: 'By time', groupByProject: 'By project', groupingAriaLabel: 'Task grouping', projectActionsAriaLabel: (name) => `${name} project actions`, projectNewTask: 'New task', projectRename: 'Rename', projectArchive: 'Archive', projectRestore: 'Restore', projectRelink: 'Relocate', projectUnavailable: 'Project directory unavailable', archivedProjects: 'Archived projects', archivedProjectsAriaLabel: 'Expand archived projects', worktreeAriaLabel: 'Git worktree', promptRailAriaLabel: 'Jump by prompt', emptyPrompt: '(empty prompt)', jumpToPrompt: (preview) => `Jump to prompt: ${preview}`, pickedAriaLabel: 'Selected', pinCount: (count) => `Pin ${count} tasks`, unpinCount: (count) => `Unpin ${count} tasks`, archiveCount: (count) => `Archive ${count} tasks`, + listAriaLabel: 'Task list', showMore: 'Show more', showMoreAriaLabel: (count) => `Show ${count} more tasks`, renameAriaLabel: 'Rename task', renameProjectTitle: 'Rename project', renameSubmit: 'Save', respondingAriaLabel: 'Responding', respondingTitle: 'This task is streaming a response', staleTitle: 'This task\'s model connection is unavailable; sending will switch to the default connection', staleAriaLabel: 'Stale task', stale: 'Stale', unreadAriaLabel: 'Unread messages', actionsAriaLabel: (name) => `${name} task actions`, pin: 'Pin', unpin: 'Unpin', rename: 'Rename', archive: 'Archive', delete: 'Delete', pinned: 'Pinned', recent: 'Recent', projects: 'Projects', groupByTime: 'By time', groupByProject: 'By project', groupingAriaLabel: 'Task grouping', projectActionsAriaLabel: (name) => `${name} project actions`, projectNewTask: 'New task', projectRename: 'Rename', projectArchive: 'Archive', projectRestore: 'Restore', projectRelink: 'Relocate', projectUnavailable: 'Project directory unavailable', archivedProjects: 'Archived projects', archivedProjectsAriaLabel: 'Expand archived projects', worktreeAriaLabel: 'Git worktree', promptRailAriaLabel: 'Jump by prompt', emptyPrompt: '(empty prompt)', jumpToPrompt: (preview) => `Jump to prompt: ${preview}`, pickedAriaLabel: 'Selected', pinCount: (count) => `Pin ${count} tasks`, unpinCount: (count) => `Unpin ${count} tasks`, archiveCount: (count) => `Archive ${count} tasks`, }, }, } satisfies UiCatalog; diff --git a/packages/ui/src/session-history-list.tsx b/packages/ui/src/session-history-list.tsx index b85529633f..e8189c774b 100644 --- a/packages/ui/src/session-history-list.tsx +++ b/packages/ui/src/session-history-list.tsx @@ -119,7 +119,6 @@ function useSidebarHoverCardTrigger( export interface SessionRowActions { onToggleFlag(sessionId: string, next: boolean): void | Promise; onArchive(sessionId: string): void | Promise; - onUnarchive(sessionId: string): void | Promise; onRename(sessionId: string, name: string): void | Promise; } @@ -1353,14 +1352,10 @@ function SessionItemActions(props: { // reachable only for a task already archived, which is the step // that makes the intent deliberate. { - label: props.session.isArchived ? copy.unarchive : copy.archive, - icon: props.session.isArchived ? ArchiveRestore : Archive, + label: copy.archive, + icon: Archive, onClick: () => - runRowAction('archive', () => - props.session.isArchived - ? actions.onUnarchive(props.session.id) - : actions.onArchive(props.session.id), - ), + runRowAction('archive', () => actions.onArchive(props.session.id)), }, ] } diff --git a/packages/ui/stories/session-list-panel.stories.tsx b/packages/ui/stories/session-list-panel.stories.tsx index 7ff2767752..60ab93a88e 100644 --- a/packages/ui/stories/session-list-panel.stories.tsx +++ b/packages/ui/stories/session-list-panel.stories.tsx @@ -85,7 +85,6 @@ function makeSession(input: { const rowActions: NonNullable = { onToggleFlag: noop, onArchive: noop, - onUnarchive: noop, onRename: noop, };