fix: 修复 markdown 编辑保存后内容丢失的问题

- 在 saveContent 中缓存 unsavedContent,避免 async 期间的竞态条件
- 在 useMarkdownLogic 中添加 lastContentRef 跟踪内容变化,防止不必要的编辑器更新
This commit is contained in:
2026-03-13 18:38:38 +08:00
parent cd1b541427
commit 371d4ce327
2 changed files with 15 additions and 5 deletions

View File

@@ -85,6 +85,8 @@ export const useMarkdownLogic = ({
const readOnlyRef = useRef(readOnly) const readOnlyRef = useRef(readOnly)
const ctxRef = useRef<Ctx | null>(null) const ctxRef = useRef<Ctx | null>(null)
const lastContentRef = useRef<string>('')
useEffect(() => { useEffect(() => {
onChangeRef.current = onChange onChangeRef.current = onChange
}, []) }, [])
@@ -117,23 +119,28 @@ export const useMarkdownLogic = ({
} }
}, [readOnly]) }, [readOnly])
// 在只读模式下动态更新内容 // 在只读模式下动态更新内容(仅当 content 真正变化时)
useEffect(() => { useEffect(() => {
if (!ctxRef.current || !readOnly) return if (!ctxRef.current || !readOnly) return
// 只有当 content 真正变化时才更新编辑器
if (content === lastContentRef.current) return
lastContentRef.current = content
try { try {
const view = ctxRef.current.get(editorViewCtx) const view = ctxRef.current.get(editorViewCtx)
const parser = ctxRef.current.get(parserCtx) const parser = ctxRef.current.get(parserCtx)
const doc = parser(content) const doc = parser(content)
if (!doc) return if (!doc) return
const state = view.state view.dispatch(view.state.tr.replaceWith(0, view.state.doc.content.size, doc))
view.dispatch(state.tr.replaceWith(0, state.doc.content.size, doc))
} catch { } catch {
// 编辑器可能尚未就绪 // 编辑器可能尚未就绪
} }
}, [content, readOnly]) }, [content, readOnly])
return useEditor((root) => { return useEditor((root) => {
lastContentRef.current = content
return Editor.make() return Editor.make()
.config((ctx) => { .config((ctx) => {
ctxRef.current = ctx ctxRef.current = ctx

View File

@@ -331,7 +331,9 @@ export const useTabStore = create<TabStore>((set, get) => {
const isAsyncImportProcessing = isAsyncImportProcessingContent(tab.content) const isAsyncImportProcessing = isAsyncImportProcessingContent(tab.content)
if (isAsyncImportProcessing) return if (isAsyncImportProcessing) return
await saveFileContent(filePath, tab.unsavedContent) const contentToSave = tab.unsavedContent
await saveFileContent(filePath, contentToSave)
set((state) => { set((state) => {
const newTabs = new Map(state.tabs) const newTabs = new Map(state.tabs)
@@ -339,7 +341,8 @@ export const useTabStore = create<TabStore>((set, get) => {
if (currentTab) { if (currentTab) {
newTabs.set(filePath, { newTabs.set(filePath, {
...currentTab, ...currentTab,
content: currentTab.unsavedContent, content: contentToSave,
unsavedContent: contentToSave,
isEditing: false, isEditing: false,
}) })
} }