diff --git a/packages/app/src/components/prompt-input.tsx b/packages/app/src/components/prompt-input.tsx index d591b22c716b..310b2db27ca1 100644 --- a/packages/app/src/components/prompt-input.tsx +++ b/packages/app/src/components/prompt-input.tsx @@ -792,6 +792,8 @@ export const PromptInput: Component = (props) => { }, setMode: (mode) => setStore("mode", mode), setPopover: (popover) => setStore("popover", popover), + editingID: () => prompt.editingID(), + setEditingID: (id) => prompt.setEditingID(id), newSessionWorktree: () => props.newSessionWorktree, onNewSessionWorktreeReset: props.onNewSessionWorktreeReset, onSubmit: props.onSubmit, diff --git a/packages/app/src/components/prompt-input/submit.test.ts b/packages/app/src/components/prompt-input/submit.test.ts index 475a0e20f291..074be7265689 100644 --- a/packages/app/src/components/prompt-input/submit.test.ts +++ b/packages/app/src/components/prompt-input/submit.test.ts @@ -156,6 +156,8 @@ describe("prompt submit worktree selection", () => { resetHistoryNavigation: () => undefined, setMode: () => undefined, setPopover: () => undefined, + editingID: () => undefined, + setEditingID: () => undefined, newSessionWorktree: () => selected, onNewSessionWorktreeReset: () => undefined, onSubmit: () => undefined, diff --git a/packages/app/src/components/prompt-input/submit.ts b/packages/app/src/components/prompt-input/submit.ts index 49d75a95ecc7..09a62666dfd4 100644 --- a/packages/app/src/components/prompt-input/submit.ts +++ b/packages/app/src/components/prompt-input/submit.ts @@ -37,6 +37,8 @@ type PromptSubmitInput = { resetHistoryNavigation: () => void setMode: (mode: "normal" | "shell") => void setPopover: (popover: "at" | "slash" | null) => void + editingID: Accessor + setEditingID: (id: string | undefined) => void newSessionWorktree?: Accessor onNewSessionWorktreeReset?: () => void onSubmit?: () => void @@ -132,6 +134,17 @@ export function createPromptSubmit(input: PromptSubmitInput) { return } + const editingID = input.editingID() + const sessionID = params.id + + if (editingID && sessionID) { + if (input.working()) { + await sdk.client.session.abort({ sessionID }).catch(() => {}) + } + await sdk.client.session.revert({ sessionID, messageID: editingID }) + input.setEditingID(undefined) + } + input.addToHistory(currentPrompt, mode) input.resetHistoryNavigation() diff --git a/packages/app/src/components/session-context-usage.tsx b/packages/app/src/components/session-context-usage.tsx index 8b77edf3aa83..de5ed2467d18 100644 --- a/packages/app/src/components/session-context-usage.tsx +++ b/packages/app/src/components/session-context-usage.tsx @@ -35,7 +35,12 @@ export function SessionContextUsage(props: SessionContextUsageProps) { const sessionKey = createMemo(() => `${params.dir}${params.id ? "/" + params.id : ""}`) const tabs = createMemo(() => layout.tabs(sessionKey)) const view = createMemo(() => layout.view(sessionKey)) - const messages = createMemo(() => (params.id ? (sync.data.message[params.id] ?? []) : [])) + const messages = createMemo(() => { + const all = params.id ? (sync.data.message[params.id] ?? []) : [] + const revert = sync.session.get(params.id ?? "")?.revert?.messageID + if (!revert) return all + return all.filter((m) => m.id < revert) + }) const usd = createMemo( () => diff --git a/packages/app/src/context/prompt.tsx b/packages/app/src/context/prompt.tsx index 064892105184..9ca1e5a56871 100644 --- a/packages/app/src/context/prompt.tsx +++ b/packages/app/src/context/prompt.tsx @@ -160,12 +160,14 @@ function createPromptSession(dir: string, id: string | undefined) { createStore<{ prompt: Prompt cursor?: number + editingID?: string context: { items: (ContextItem & { key: string })[] } }>({ prompt: clonePrompt(DEFAULT_PROMPT), cursor: undefined, + editingID: undefined, context: { items: [], }, @@ -178,6 +180,7 @@ function createPromptSession(dir: string, id: string | undefined) { ready, current: createMemo(() => store.prompt), cursor: createMemo(() => store.cursor), + editingID: createMemo(() => store.editingID), dirty: createMemo(() => !isPromptEqual(store.prompt, DEFAULT_PROMPT)), context: { items: createMemo(() => store.context.items), @@ -190,6 +193,9 @@ function createPromptSession(dir: string, id: string | undefined) { setStore("context", "items", (items) => items.filter((x) => x.key !== key)) }, }, + setEditingID(id: string | undefined) { + setStore("editingID", id) + }, set: actions.set, reset: actions.reset, } @@ -246,14 +252,19 @@ export const { use: usePrompt, provider: PromptProvider } = createSimpleContext( ready: () => session().ready(), current: () => session().current(), cursor: () => session().cursor(), + editingID: () => session().editingID(), dirty: () => session().dirty(), context: { items: () => session().context.items(), add: (item: ContextItem) => session().context.add(item), remove: (key: string) => session().context.remove(key), }, + setEditingID: (id: string | undefined) => session().setEditingID(id), set: (prompt: Prompt, cursorPosition?: number) => session().set(prompt, cursorPosition), - reset: () => session().reset(), + reset: () => { + session().setEditingID(undefined) + session().reset() + }, } }, }) diff --git a/packages/app/src/i18n/ar.ts b/packages/app/src/i18n/ar.ts index e3792a3c3cc3..ca9b925cfa05 100644 --- a/packages/app/src/i18n/ar.ts +++ b/packages/app/src/i18n/ar.ts @@ -496,6 +496,7 @@ export const dict = { "common.delete": "حذف", "common.close": "إغلاق", "common.edit": "تحرير", + "ui.common.edit.message": "Editing message", "common.loadMore": "تحميل المزيد", "common.key.esc": "ESC", "sidebar.menu.toggle": "تبديل القائمة", diff --git a/packages/app/src/i18n/br.ts b/packages/app/src/i18n/br.ts index 07d6ce467aeb..5ed0fd6ac3c6 100644 --- a/packages/app/src/i18n/br.ts +++ b/packages/app/src/i18n/br.ts @@ -502,6 +502,7 @@ export const dict = { "common.delete": "Excluir", "common.close": "Fechar", "common.edit": "Editar", + "ui.common.edit.message": "Editing message", "common.loadMore": "Carregar mais", "common.key.esc": "ESC", "sidebar.menu.toggle": "Alternar menu", diff --git a/packages/app/src/i18n/bs.ts b/packages/app/src/i18n/bs.ts index 7d10da6ed875..a2caad18d1e8 100644 --- a/packages/app/src/i18n/bs.ts +++ b/packages/app/src/i18n/bs.ts @@ -562,6 +562,7 @@ export const dict = { "common.delete": "Izbriši", "common.close": "Zatvori", "common.edit": "Uredi", + "ui.common.edit.message": "Editing message", "common.loadMore": "Učitaj još", "common.key.esc": "ESC", diff --git a/packages/app/src/i18n/da.ts b/packages/app/src/i18n/da.ts index ac5c4d494b12..6328a818bbbd 100644 --- a/packages/app/src/i18n/da.ts +++ b/packages/app/src/i18n/da.ts @@ -558,6 +558,7 @@ export const dict = { "common.delete": "Slet", "common.close": "Luk", "common.edit": "Rediger", + "ui.common.edit.message": "Editing message", "common.loadMore": "Indlæs flere", "common.key.esc": "ESC", diff --git a/packages/app/src/i18n/de.ts b/packages/app/src/i18n/de.ts index 99a950631074..0e13629b3a20 100644 --- a/packages/app/src/i18n/de.ts +++ b/packages/app/src/i18n/de.ts @@ -510,6 +510,7 @@ export const dict = { "common.delete": "Löschen", "common.close": "Schließen", "common.edit": "Bearbeiten", + "ui.common.edit.message": "Editing message", "common.loadMore": "Mehr laden", "common.key.esc": "ESC", "sidebar.menu.toggle": "Menü umschalten", diff --git a/packages/app/src/i18n/en.ts b/packages/app/src/i18n/en.ts index c138c7b61456..46b271c842ea 100644 --- a/packages/app/src/i18n/en.ts +++ b/packages/app/src/i18n/en.ts @@ -562,6 +562,7 @@ export const dict = { "common.delete": "Delete", "common.close": "Close", "common.edit": "Edit", + "ui.common.edit.message": "Editing message", "common.loadMore": "Load more", "common.key.esc": "ESC", diff --git a/packages/app/src/i18n/es.ts b/packages/app/src/i18n/es.ts index 7a6c4974e091..419a5f3238f8 100644 --- a/packages/app/src/i18n/es.ts +++ b/packages/app/src/i18n/es.ts @@ -565,6 +565,7 @@ export const dict = { "common.delete": "Eliminar", "common.close": "Cerrar", "common.edit": "Editar", + "ui.common.edit.message": "Editing message", "common.loadMore": "Cargar más", "common.key.esc": "ESC", diff --git a/packages/app/src/i18n/fr.ts b/packages/app/src/i18n/fr.ts index fc3bf2667943..e3914ab6ccd5 100644 --- a/packages/app/src/i18n/fr.ts +++ b/packages/app/src/i18n/fr.ts @@ -508,6 +508,7 @@ export const dict = { "common.delete": "Supprimer", "common.close": "Fermer", "common.edit": "Modifier", + "ui.common.edit.message": "Editing message", "common.loadMore": "Charger plus", "common.key.esc": "ESC", "sidebar.menu.toggle": "Basculer le menu", diff --git a/packages/app/src/i18n/ja.ts b/packages/app/src/i18n/ja.ts index b597db02a586..5fad4e9e274a 100644 --- a/packages/app/src/i18n/ja.ts +++ b/packages/app/src/i18n/ja.ts @@ -500,6 +500,7 @@ export const dict = { "common.delete": "削除", "common.close": "閉じる", "common.edit": "編集", + "ui.common.edit.message": "Editing message", "common.loadMore": "さらに読み込む", "common.key.esc": "ESC", "sidebar.menu.toggle": "メニューを切り替え", diff --git a/packages/app/src/i18n/ko.ts b/packages/app/src/i18n/ko.ts index 525bd035651f..0aab23e68ffd 100644 --- a/packages/app/src/i18n/ko.ts +++ b/packages/app/src/i18n/ko.ts @@ -501,6 +501,7 @@ export const dict = { "common.delete": "삭제", "common.close": "닫기", "common.edit": "편집", + "ui.common.edit.message": "Editing message", "common.loadMore": "더 불러오기", "common.key.esc": "ESC", "sidebar.menu.toggle": "메뉴 토글", diff --git a/packages/app/src/i18n/no.ts b/packages/app/src/i18n/no.ts index 98e79e1896af..ff26d8be2048 100644 --- a/packages/app/src/i18n/no.ts +++ b/packages/app/src/i18n/no.ts @@ -565,6 +565,7 @@ export const dict = { "common.delete": "Slett", "common.close": "Lukk", "common.edit": "Rediger", + "ui.common.edit.message": "Editing message", "common.loadMore": "Last flere", "common.key.esc": "ESC", diff --git a/packages/app/src/i18n/pl.ts b/packages/app/src/i18n/pl.ts index 983c9c14ac1b..cefccdab0f83 100644 --- a/packages/app/src/i18n/pl.ts +++ b/packages/app/src/i18n/pl.ts @@ -501,6 +501,7 @@ export const dict = { "common.delete": "Usuń", "common.close": "Zamknij", "common.edit": "Edytuj", + "ui.common.edit.message": "Editing message", "common.loadMore": "Załaduj więcej", "common.key.esc": "ESC", "sidebar.menu.toggle": "Przełącz menu", diff --git a/packages/app/src/i18n/ru.ts b/packages/app/src/i18n/ru.ts index f2c87fe0f1ed..b906a7874273 100644 --- a/packages/app/src/i18n/ru.ts +++ b/packages/app/src/i18n/ru.ts @@ -563,6 +563,7 @@ export const dict = { "common.delete": "Удалить", "common.close": "Закрыть", "common.edit": "Редактировать", + "ui.common.edit.message": "Editing message", "common.loadMore": "Загрузить ещё", "common.key.esc": "ESC", diff --git a/packages/app/src/i18n/th.ts b/packages/app/src/i18n/th.ts index 689e82118968..4ceaab434538 100644 --- a/packages/app/src/i18n/th.ts +++ b/packages/app/src/i18n/th.ts @@ -557,6 +557,7 @@ export const dict = { "common.delete": "ลบ", "common.close": "ปิด", "common.edit": "แก้ไข", + "ui.common.edit.message": "Editing message", "common.loadMore": "โหลดเพิ่มเติม", "common.key.esc": "ESC", diff --git a/packages/app/src/i18n/zh.ts b/packages/app/src/i18n/zh.ts index 1b40013b60de..3544b5788829 100644 --- a/packages/app/src/i18n/zh.ts +++ b/packages/app/src/i18n/zh.ts @@ -555,6 +555,7 @@ export const dict = { "common.delete": "删除", "common.close": "关闭", "common.edit": "编辑", + "ui.common.edit.message": "Editing message", "common.loadMore": "加载更多", "common.key.esc": "ESC", diff --git a/packages/app/src/i18n/zht.ts b/packages/app/src/i18n/zht.ts index 34aec01b9cb1..c769666f5051 100644 --- a/packages/app/src/i18n/zht.ts +++ b/packages/app/src/i18n/zht.ts @@ -553,6 +553,7 @@ export const dict = { "common.delete": "刪除", "common.close": "關閉", "common.edit": "編輯", + "ui.common.edit.message": "Editing message", "common.loadMore": "載入更多", "common.key.esc": "ESC", diff --git a/packages/app/src/pages/session.tsx b/packages/app/src/pages/session.tsx index edcc660a0f5b..3ac0adb6b970 100644 --- a/packages/app/src/pages/session.tsx +++ b/packages/app/src/pages/session.tsx @@ -40,6 +40,7 @@ import { showToast } from "@opencode-ai/ui/toast" import { SessionHeader, SessionContextTab, SortableTab, FileVisual, NewSessionView } from "@/components/session" import { navMark, navParams } from "@/utils/perf" import { same } from "@/utils/same" +import { extractPromptFromParts } from "@/utils/prompt" import { createOpenReviewFile, focusTerminalById, getTabReorderIndex } from "@/pages/session/helpers" import { createScrollSpy } from "@/pages/session/scroll-spy" import { createFileTabListSync } from "@/pages/session/file-tab-scroll" @@ -306,6 +307,12 @@ export default function Page() { const hasReview = createMemo(() => reviewCount() > 0) const revertMessageID = createMemo(() => info()?.revert?.messageID) const messages = createMemo(() => (params.id ? (sync.data.message[params.id] ?? []) : [])) + const visibleMessages = createMemo(() => { + const all = messages() + const revert = revertMessageID() + if (!revert) return all + return all.filter((m) => m.id < revert) + }) const messagesReady = createMemo(() => { const id = params.id if (!id) return true @@ -1650,6 +1657,15 @@ export default function Page() { lastUserMessageID={lastUserMessage()?.id} expanded={store.expanded} onToggleExpanded={(id) => setStore("expanded", id, (open: boolean | undefined) => !open)} + onEdit={async (messageID) => { + const parts = sync.data.part[messageID] + if (parts) { + const restored = extractPromptFromParts(parts, { directory: sdk.directory }) + prompt.set(restored) + prompt.setEditingID(messageID) + focusInput() + } + }} /> @@ -1729,7 +1745,7 @@ export default function Page() { showAllFiles={showAllFiles} reviewPanel={reviewPanel} vm={{ - messages, + messages: visibleMessages, visibleUserMessages, view, info, diff --git a/packages/app/src/pages/session/message-timeline.tsx b/packages/app/src/pages/session/message-timeline.tsx index d5f04ccf91c4..9c161688fa9d 100644 --- a/packages/app/src/pages/session/message-timeline.tsx +++ b/packages/app/src/pages/session/message-timeline.tsx @@ -90,6 +90,7 @@ export function MessageTimeline(props: { lastUserMessageID?: string expanded: Record onToggleExpanded: (id: string) => void + onEdit?: (messageID: string) => void }) { let touchGesture: number | undefined @@ -318,6 +319,7 @@ export function MessageTimeline(props: { lastUserMessageID={props.lastUserMessageID} stepsExpanded={props.expanded[message.id] ?? false} onStepsExpandedToggle={() => props.onToggleExpanded(message.id)} + onEdit={props.onEdit} classes={{ root: "min-w-0 w-full relative", content: "flex flex-col justify-between !overflow-visible", diff --git a/packages/app/src/pages/session/session-prompt-dock.tsx b/packages/app/src/pages/session/session-prompt-dock.tsx index 8ec4f3b9f8c5..e01ae5049093 100644 --- a/packages/app/src/pages/session/session-prompt-dock.tsx +++ b/packages/app/src/pages/session/session-prompt-dock.tsx @@ -2,9 +2,11 @@ import { For, Show } from "solid-js" import type { QuestionRequest } from "@opencode-ai/sdk/v2" import { Button } from "@opencode-ai/ui/button" import { BasicTool } from "@opencode-ai/ui/basic-tool" +import { Icon } from "@opencode-ai/ui/icon" import { PromptInput } from "@/components/prompt-input" import { QuestionDock } from "@/components/question-dock" import { questionSubtitle } from "@/pages/session/session-prompt-helpers" +import { usePrompt } from "@/context/prompt" export function SessionPromptDock(props: { centered: boolean @@ -22,6 +24,8 @@ export function SessionPromptDock(props: { onSubmit: () => void setPromptDockRef: (el: HTMLDivElement) => void }) { + const prompt = usePrompt() + return (
} > + +
+
+ + {props.t("ui.common.edit.message")} +
+ +
+
`, copy: ``, check: ``, + undo: ``, photo: ``, share: ``, download: ``, diff --git a/packages/ui/src/components/message-part.tsx b/packages/ui/src/components/message-part.tsx index 3f61b3186d30..b0a0190d9894 100644 --- a/packages/ui/src/components/message-part.tsx +++ b/packages/ui/src/components/message-part.tsx @@ -92,6 +92,7 @@ function DiagnosticsDisplay(props: { diagnostics: Diagnostic[] }): JSX.Element { export interface MessageProps { message: MessageType parts: PartType[] + onEdit?: (messageID: string) => void } export interface MessagePartProps { @@ -277,7 +278,9 @@ export function Message(props: MessageProps) { return ( - {(userMessage) => } + {(userMessage) => ( + + )} {(assistantMessage) => ( @@ -301,7 +304,11 @@ export function AssistantMessageDisplay(props: { message: AssistantMessage; part return {(part) => } } -export function UserMessageDisplay(props: { message: UserMessage; parts: PartType[] }) { +export function UserMessageDisplay(props: { + message: UserMessage + parts: PartType[] + onEdit?: (messageID: string) => void +}) { const dialog = useDialog() const i18n = useI18n() const [copied, setCopied] = createSignal(false) @@ -417,7 +424,19 @@ export function UserMessageDisplay(props: { message: UserMessage; parts: PartTyp > -
+
+ + { + event.stopPropagation() + props.onEdit?.(props.message.id) + }} + aria-label={i18n.t("ui.message.undo")} + /> + void + onEdit?: (messageID: string) => void onUserInteracted?: () => void classes?: { root?: string @@ -626,13 +627,13 @@ export function SessionTurn( 0}>
- +
{/* User Message */}
- +
{/* Trigger (sticky) */} diff --git a/packages/ui/src/i18n/ar.ts b/packages/ui/src/i18n/ar.ts index 7ee17e2e0102..f71efb24d497 100644 --- a/packages/ui/src/i18n/ar.ts +++ b/packages/ui/src/i18n/ar.ts @@ -90,6 +90,7 @@ export const dict = { "ui.message.collapse": "طي الرسالة", "ui.message.copy": "نسخ", "ui.message.copied": "تم النسخ!", + "ui.message.undo": "Undo", "ui.message.attachment.alt": "مرفق", "ui.patch.action.deleted": "محذوف", diff --git a/packages/ui/src/i18n/br.ts b/packages/ui/src/i18n/br.ts index 6d7449d8457d..9743710b1f58 100644 --- a/packages/ui/src/i18n/br.ts +++ b/packages/ui/src/i18n/br.ts @@ -90,6 +90,7 @@ export const dict = { "ui.message.collapse": "Recolher mensagem", "ui.message.copy": "Copiar", "ui.message.copied": "Copiado!", + "ui.message.undo": "Undo", "ui.message.attachment.alt": "anexo", "ui.patch.action.deleted": "Excluído", diff --git a/packages/ui/src/i18n/bs.ts b/packages/ui/src/i18n/bs.ts index 24e4c12068ee..825b96f890e4 100644 --- a/packages/ui/src/i18n/bs.ts +++ b/packages/ui/src/i18n/bs.ts @@ -94,6 +94,7 @@ export const dict = { "ui.message.collapse": "Sažmi poruku", "ui.message.copy": "Kopiraj", "ui.message.copied": "Kopirano!", + "ui.message.undo": "Undo", "ui.message.attachment.alt": "prilog", "ui.patch.action.deleted": "Obrisano", diff --git a/packages/ui/src/i18n/da.ts b/packages/ui/src/i18n/da.ts index 218f3b26a494..92dfd51244ee 100644 --- a/packages/ui/src/i18n/da.ts +++ b/packages/ui/src/i18n/da.ts @@ -89,6 +89,7 @@ export const dict = { "ui.message.collapse": "Skjul besked", "ui.message.copy": "Kopier", "ui.message.copied": "Kopieret!", + "ui.message.undo": "Undo", "ui.message.attachment.alt": "vedhæftning", "ui.patch.action.deleted": "Slettet", diff --git a/packages/ui/src/i18n/de.ts b/packages/ui/src/i18n/de.ts index 921a12c99675..a422a70a1108 100644 --- a/packages/ui/src/i18n/de.ts +++ b/packages/ui/src/i18n/de.ts @@ -93,6 +93,7 @@ export const dict = { "ui.message.collapse": "Nachricht reduzieren", "ui.message.copy": "Kopieren", "ui.message.copied": "Kopiert!", + "ui.message.undo": "Undo", "ui.message.attachment.alt": "Anhang", "ui.patch.action.deleted": "Gelöscht", diff --git a/packages/ui/src/i18n/en.ts b/packages/ui/src/i18n/en.ts index 631bc660a65d..ce2b731f7323 100644 --- a/packages/ui/src/i18n/en.ts +++ b/packages/ui/src/i18n/en.ts @@ -90,6 +90,7 @@ export const dict = { "ui.message.collapse": "Collapse message", "ui.message.copy": "Copy", "ui.message.copied": "Copied!", + "ui.message.undo": "Undo", "ui.message.attachment.alt": "attachment", "ui.patch.action.deleted": "Deleted", diff --git a/packages/ui/src/i18n/es.ts b/packages/ui/src/i18n/es.ts index 4fd921b606b1..c095088351a8 100644 --- a/packages/ui/src/i18n/es.ts +++ b/packages/ui/src/i18n/es.ts @@ -90,6 +90,7 @@ export const dict = { "ui.message.collapse": "Colapsar mensaje", "ui.message.copy": "Copiar", "ui.message.copied": "¡Copiado!", + "ui.message.undo": "Undo", "ui.message.attachment.alt": "adjunto", "ui.patch.action.deleted": "Eliminado", diff --git a/packages/ui/src/i18n/fr.ts b/packages/ui/src/i18n/fr.ts index 537d01bba941..af380461131e 100644 --- a/packages/ui/src/i18n/fr.ts +++ b/packages/ui/src/i18n/fr.ts @@ -90,6 +90,7 @@ export const dict = { "ui.message.collapse": "Réduire le message", "ui.message.copy": "Copier", "ui.message.copied": "Copié !", + "ui.message.undo": "Undo", "ui.message.attachment.alt": "pièce jointe", "ui.patch.action.deleted": "Supprimé", diff --git a/packages/ui/src/i18n/ja.ts b/packages/ui/src/i18n/ja.ts index 6086070bdb2c..f57d1c51d3fa 100644 --- a/packages/ui/src/i18n/ja.ts +++ b/packages/ui/src/i18n/ja.ts @@ -89,6 +89,7 @@ export const dict = { "ui.message.collapse": "メッセージを折りたたむ", "ui.message.copy": "コピー", "ui.message.copied": "コピーしました!", + "ui.message.undo": "Undo", "ui.message.attachment.alt": "添付ファイル", "ui.patch.action.deleted": "削除済み", diff --git a/packages/ui/src/i18n/ko.ts b/packages/ui/src/i18n/ko.ts index fd394dbb7b52..a172b9397778 100644 --- a/packages/ui/src/i18n/ko.ts +++ b/packages/ui/src/i18n/ko.ts @@ -90,6 +90,7 @@ export const dict = { "ui.message.collapse": "메시지 접기", "ui.message.copy": "복사", "ui.message.copied": "복사됨!", + "ui.message.undo": "Undo", "ui.message.attachment.alt": "첨부 파일", "ui.patch.action.deleted": "삭제됨", diff --git a/packages/ui/src/i18n/no.ts b/packages/ui/src/i18n/no.ts index dcb353614d30..b5ac179ca1b9 100644 --- a/packages/ui/src/i18n/no.ts +++ b/packages/ui/src/i18n/no.ts @@ -93,6 +93,7 @@ export const dict: Record = { "ui.message.collapse": "Skjul melding", "ui.message.copy": "Kopier", "ui.message.copied": "Kopiert!", + "ui.message.undo": "Undo", "ui.message.attachment.alt": "vedlegg", "ui.patch.action.deleted": "Slettet", diff --git a/packages/ui/src/i18n/pl.ts b/packages/ui/src/i18n/pl.ts index fb10debbb92d..e55d18d0d0cb 100644 --- a/packages/ui/src/i18n/pl.ts +++ b/packages/ui/src/i18n/pl.ts @@ -89,6 +89,7 @@ export const dict = { "ui.message.collapse": "Zwiń wiadomość", "ui.message.copy": "Kopiuj", "ui.message.copied": "Skopiowano!", + "ui.message.undo": "Undo", "ui.message.attachment.alt": "załącznik", "ui.patch.action.deleted": "Usunięto", diff --git a/packages/ui/src/i18n/ru.ts b/packages/ui/src/i18n/ru.ts index 417fe0ce8bfe..9bb0aa7dbd06 100644 --- a/packages/ui/src/i18n/ru.ts +++ b/packages/ui/src/i18n/ru.ts @@ -89,6 +89,7 @@ export const dict = { "ui.message.collapse": "Свернуть сообщение", "ui.message.copy": "Копировать", "ui.message.copied": "Скопировано!", + "ui.message.undo": "Undo", "ui.message.attachment.alt": "вложение", "ui.patch.action.deleted": "Удалено", diff --git a/packages/ui/src/i18n/th.ts b/packages/ui/src/i18n/th.ts index 68bb0d733d99..adf2233fe8a9 100644 --- a/packages/ui/src/i18n/th.ts +++ b/packages/ui/src/i18n/th.ts @@ -90,6 +90,7 @@ export const dict = { "ui.message.collapse": "ย่อข้อความ", "ui.message.copy": "คัดลอก", "ui.message.copied": "คัดลอกแล้ว!", + "ui.message.undo": "Undo", "ui.message.attachment.alt": "ไฟล์แนบ", "ui.patch.action.deleted": "ลบ", diff --git a/packages/ui/src/i18n/zh.ts b/packages/ui/src/i18n/zh.ts index 53beeb1e4f0f..16f17c97d87d 100644 --- a/packages/ui/src/i18n/zh.ts +++ b/packages/ui/src/i18n/zh.ts @@ -94,6 +94,7 @@ export const dict = { "ui.message.collapse": "收起消息", "ui.message.copy": "复制", "ui.message.copied": "已复制!", + "ui.message.undo": "Undo", "ui.message.attachment.alt": "附件", "ui.patch.action.deleted": "已删除", diff --git a/packages/ui/src/i18n/zht.ts b/packages/ui/src/i18n/zht.ts index 1449b0530ac1..9e6184042d02 100644 --- a/packages/ui/src/i18n/zht.ts +++ b/packages/ui/src/i18n/zht.ts @@ -94,6 +94,7 @@ export const dict = { "ui.message.collapse": "收合訊息", "ui.message.copy": "複製", "ui.message.copied": "已複製!", + "ui.message.undo": "Undo", "ui.message.attachment.alt": "附件", "ui.patch.action.deleted": "已刪除",