45-崩溃后草稿损坏-用临时文件和恢复账本保护输入
第45篇崩溃后草稿损坏用临时文件和恢复账本保护输入摘要编辑页草稿最怕“写了一半崩溃再打开内容坏了”。如果每次输入都直接覆盖正式草稿崩溃、磁盘异常或序列化失败都会把可恢复内容一起毁掉。更稳的做法是写临时文件和恢复账本完整写入后再原子替换重启时按账本恢复或隔离损坏草稿。有个长文编辑页用户写到一半切后台应用被系统回收。重进后草稿还在但正文少了后半段图片列表也乱了。原代码在每次输入后直接覆盖draft.json中途写入失败就留下了半截 JSON。草稿保存不能只追求实时要保证任何一次崩溃都不会破坏上一份完整内容。这篇文章解决四个实际问题草稿写入先落临时文件成功后再替换正式文件。恢复账本记录最后一次完整版本和待恢复版本。重启时先校验 JSON 和版本不直接打开损坏草稿。保存频率用防抖和显式保存结合避免每个字符都落盘。先确认损坏的是内容还是索引草稿损坏不一定是文件消失。可能是 JSON 半截、图片附件缺失、版本不匹配或者页面读取了旧索引。位置现象风险处理方向正文少半截直接覆盖正式文件崩溃留下半写入临时文件加替换图片错位附件和正文不同步索引先更新了快照统一保存重启空白解析失败被当成空草稿损坏隔离频繁卡顿每字符写文件防抖保存这一步的价值是先把问题放回运行链路。只要能确认问题停在哪个位置后面就不用靠猜测改页面。编辑状态和持久草稿要隔一层快照页面里的输入状态变化很频繁持久化层需要的是完整快照。不要让每个输入框都直接写草稿文件。模块应该负责不应该负责EditorPage当前输入、保存中提示文件路径DraftSnapshotBuilder把页面状态转成快照磁盘写入DraftStore临时文件和替换UI 布局DraftJournal版本、路径、恢复状态输入事件RecoveryPage恢复或丢弃选择序列化细节边界定清后代码就不会在页面、服务和回调之间来回复制同一段判断。后续新增场景也能先判断应该落在哪一层。草稿快照要有版本和校验字段exportinterfaceDraftSnapshot{draftId:stringversion:numbertitle:stringbody:stringattachmentIds:string[]savedAt:number}exportinterfaceDraftJournalEntry{draftId:stringstableVersion:numberpendingVersion:numberrecovering:booleanupdatedAt:number}exportfunctionisValidDraft(snapshot:DraftSnapshot):boolean{returnsnapshot.draftId.length0snapshot.version0snapshot.savedAt0}版本号和账本让重启恢复有依据。页面不能把解析失败的草稿直接当成空内容否则用户会以为内容被正常清掉了。这类模型最好放在models或common中页面、Service 和仓储都使用同一份类型避免各层用字符串互相猜。写入走临时文件再替换正式文件exportclassDraftStore{constructor(privatereadonlyfileWriter:DraftFileWriter){}asyncsave(snapshot:DraftSnapshot):Promisevoid{consttempPathdraftTempPath(snapshot.draftId,snapshot.version)conststablePathdraftStablePath(snapshot.draftId)awaitthis.fileWriter.writeText(tempPath,JSON.stringify(snapshot))constloadedJSON.parse(awaitthis.fileWriter.readText(tempPath))asDraftSnapshotif(!isValidDraft(loaded)){thrownewError(invalid draft snapshot)}awaitthis.fileWriter.replace(tempPath,stablePath)}}先写 temp再读回校验最后替换正式文件。即使写 temp 过程中崩溃上一份 stable 草稿仍然存在。Service 的目标不是把所有逻辑都塞进去而是把跨页面、跨生命周期或需要持久化的判断集中起来。页面只表达用户动作。页面用防抖保存完整快照Componentstruct ArticleEditorPage{Statetitle:stringStatebody:stringStatesaving:booleanfalseprivateautosave:DraftAutosaveServicecreateDraftAutosaveService()onInputChanged():void{constsnapshotthis.buildSnapshot()this.autosave.schedule(snapshot)}privatebuildSnapshot():DraftSnapshot{return{draftId:currentDraftId(),version:Date.now(),title:this.title,body:this.body,attachmentIds:readAttachmentIds(),savedAt:Date.now()}}}页面只负责生成完整快照不直接写文件。附件 id 和正文一起进入快照避免正文恢复了、附件索引没恢复。页面层要控制展示和交互节奏但不应该拥有底层事实。这样页面重建、横竖屏变化或返回前台时都能重新从 Service 拿到可信结果。恢复时先隔离损坏版本exportclassDraftRecoveryService{constructor(privatereadonlystore:DraftStore,privatereadonlyjournal:DraftJournal){}asyncrecover(draftId:string):PromiseDraftSnapshot|null{conststableawaitthis.store.loadStable(draftId).catch(()null)if(stable!nullisValidDraft(stable)){awaitthis.journal.markRecovered(draftId,stable.version)returnstable}awaitthis.journal.markCorrupted(draftId)returnnull}}恢复服务不把坏文件吞掉。能恢复就标记已恢复不能恢复就标记损坏让页面给出恢复失败说明而不是直接显示空白编辑器。实际项目里很多问题不是第一次进入页面暴露而是在冷启动、返回前台、页面重建或回调晚到时暴露。把这段生命周期补上修复才算闭环。恢复提示要给用户选择情况页面表现工程处理找到稳定草稿提示恢复上次编辑用户确认后进入编辑页只有损坏草稿隔离坏文件提示无法恢复并保留日志附件缺失恢复正文并标记附件失败不要丢正文保存中崩溃使用上一个 stabletemp 不覆盖正式草稿兜底路径不是可有可无。用户遇到异常时页面至少要给出当前状态、可执行动作和可排查线索。排查时找直接覆盖草稿的代码rg-ndraft.json|writeText|replace|autosave|DraftSnapshotentry features common rg-nJSON.parse|JSON.stringify|attachmentIds|DraftJournalentry features common rg-nonTextChange|onInput|schedule\(|debounceentry features common第一组命令找旧路径第二组命令找新边界第三组命令看生命周期或回调位置。命中后不要只看字段名要判断它是否仍在直接改页面状态。验证清单验证项预期结果输入后立刻杀进程重启恢复到上一份完整草稿写 temp 失败stable 草稿不损坏JSON 半截进入损坏隔离不显示空白假象附件缺失正文仍可恢复连续输入不会每字符同步写文件卡顿这些验证最好在真机或模拟器里按顺序走一遍。只看源码很难发现冷启动、重启和回调晚到这类问题。常见问题和处理方式现象常见原因处理方式草稿半截直接覆盖正式文件temp 加替换打开变空白解析失败当空草稿损坏隔离并提示附件乱了正文和附件分开保存统一 DraftSnapshot输入卡顿保存频率太高防抖保存如果现象没有出现在表里仍然建议按“输入来源 - 中间状态 - 持久化或页面展示 - 失败兜底”的顺序排查。小结草稿保存先保护上一份完整内容草稿不是普通缓存它承载用户输入。写入时先生成完整快照落临时文件校验后替换正式版本重启时按恢复账本加载稳定版本坏文件隔离。这样即使崩溃发生在写入中间用户也不会丢掉上一份可用内容。| 保存频率太高 | 防抖保存 |如果现象没有出现在表里仍然建议按“输入来源 - 中间状态 - 持久化或页面展示 - 失败兜底”的顺序排查。小结草稿保存先保护上一份完整内容草稿不是普通缓存它承载用户输入。写入时先生成完整快照落临时文件校验后替换正式版本重启时按恢复账本加载稳定版本坏文件隔离。这样即使崩溃发生在写入中间用户也不会丢掉上一份可用内容。

相关新闻

TMS320F2838x CMSYSCTL_REGS:系统控制、低功耗与复位管理详解

TMS320F2838x CMSYSCTL_REGS:系统控制、低功耗与复位管理详解

1. 深入理解CMSYSCTL_REGS:TMS320F2838x系统控制的基石在嵌入式系统开发,尤其是工业控制和汽车电子这类对实时性、可靠性和功耗有严苛要求的领域,微控制器的系统控制单元扮演着“中枢神经系统”的角色。它不像外设驱动那样直接处理数据收发&a…

2026/10/14 18:59:21 阅读更多 →
diff2html深度解析:Git差异可视化与代码审查的专业解决方案

diff2html深度解析:Git差异可视化与代码审查的专业解决方案

diff2html深度解析:Git差异可视化与代码审查的专业解决方案 【免费下载链接】diff2html Pretty diff to html javascript library (diff2html) 项目地址: https://gitcode.com/gh_mirrors/di/diff2html diff2html是一个功能强大的JavaScript库,专…

2026/10/8 22:06:05 阅读更多 →
5个步骤彻底解决Windows风扇噪音:FanControl实战指南

5个步骤彻底解决Windows风扇噪音:FanControl实战指南

5个步骤彻底解决Windows风扇噪音:FanControl实战指南 【免费下载链接】FanControl.Releases This is the release repository for Fan Control, a highly customizable fan controlling software for Windows. 项目地址: https://gitcode.com/GitHub_Trending/fa/…

2026/10/8 3:47:38 阅读更多 →

最新新闻

深入解析 docker-ce 中 google.golang.org/genproto:Go 生成的 Protobuf 与 gRPC API 包

深入解析 docker-ce 中 google.golang.org/genproto:Go 生成的 Protobuf 与 gRPC API 包

容器运行时云原生 【免费下载链接】docker-ce :warning: This repository is deprecated and will be archived (Docker CE itself is NOT deprecated) see the https://github.com/docker/docker-ce/blob/master/README.md :warning: 项目地址: https://gitcode.co…

2026/10/14 21:40:34 阅读更多 →
Windows第三方应用程序漏洞全解析:从DLL劫持到权限提升的排查与修复

Windows第三方应用程序漏洞全解析:从DLL劫持到权限提升的排查与修复

先说一件我亲身处理过的事。凌晨两点,某单位的IT值班人员发现一台开发终端CPU占用异常,进程列表里多了一个名字很像系统服务的进程,路径却指向用户临时目录。顺着进程链一层层追下去,最后定位到一个很不起眼的第三方小工具——某款…

2026/10/14 21:40:34 阅读更多 →
动物运动会系统:用策略+工厂+观察者模式实践开闭原则

动物运动会系统:用策略+工厂+观察者模式实践开闭原则

简介:本资源是一套基于Java实现的《动物运动会》综合教学系统,面向软件工程专业学生、设计模式初学者及Java进阶开发者,旨在通过真实业务场景深度理解并实践31种经典设计模式。系统以动物参赛、大厅交互、赛事执行等完整流程为载体&#xff0…

2026/10/14 21:40:34 阅读更多 →
基于Node.js的药膳食堂点餐系统全栈设计与实现经验详解

基于Node.js的药膳食堂点餐系统全栈设计与实现经验详解

1. 项目概述与核心需求解析1.1 药膳点餐系统到底在解决什么问题去年我参与了一个餐饮类的全栈项目,名字就叫“基于Node.js药膳食堂点餐系统的设计与实现”。刚拿到这个需求的时候,我第一反应是这不就是个普通的外卖点餐系统套了个“药膳”的壳吗&#xf…

2026/10/14 21:40:34 阅读更多 →
Java构建AI漫画推文系统:多端部署与源码实战解析

Java构建AI漫画推文系统:多端部署与源码实战解析

1. 项目概述与价值拆解漫画推文这两年是真的火,说白了就是那种短视频平台上常见的“动态漫画配音解说剧情字幕”内容形态,画面是AI生成的漫画,旁白是TTS语音合成,再加个背景音乐和转场,一条看起来像模像样的推文视频就…

2026/10/14 21:40:34 阅读更多 →
业务驱动挖金融SRC:从逻辑漏洞到越权的高价值挖掘思路

业务驱动挖金融SRC:从逻辑漏洞到越权的高价值挖掘思路

做金融SRC这五六年,我最大的体会是:漏洞挖掘的瓶颈往往不在工具,而在你对业务的理解深度。同样一批人,手里工具差不多,漏洞库也差不多,但产出高价值漏洞的能力可以差出好几倍。通用扫描器擅长发现组件版本漏…

2026/10/14 21:39:33 阅读更多 →

日新闻

AnyPS5通用适配层设计:兼容性与性能的工程取舍

AnyPS5通用适配层设计:兼容性与性能的工程取舍

1. 从"AnyPS5"这个名字说起:它到底想解决什么问题第一次看到"AnyPS5"这个标题,我脑子里冒出来的第一个念头是:这大概率是一个围绕"跨平台运行"或者"通用适配"做文章的项目。名字里的"Any"…

2026/10/14 0:00:41 阅读更多 →
Flutter跨平台开发实战:二手交易应用与HarmonyOS适配

Flutter跨平台开发实战:二手交易应用与HarmonyOS适配

1. 项目概述:Flutter跨平台二手交易应用开发作为一名长期从事移动应用开发的工程师,我最近完成了一个基于Flutter框架的二手物品交易平台项目。这个项目最吸引我的地方在于它完美结合了Flutter的跨平台优势与HarmonyOS的生态特性,实现了"…

2026/10/14 0:00:41 阅读更多 →
DFS算法解决飞机降落调度问题实战

DFS算法解决飞机降落调度问题实战

1. 项目背景与核心思路飞机降落问题是一个经典的调度优化场景,也是算法竞赛和面试中的高频题目。这个题目要求我们合理安排多架飞机的降落顺序和时间,确保所有飞机都能安全着陆而不发生冲突。在实际航空管制中,这类问题直接关系到飞行安全和机…

2026/10/14 0:00:41 阅读更多 →

周新闻

流感时间序列预测实战:ARIMA/LSTM全流程拆解与避坑指南

流感时间序列预测实战:ARIMA/LSTM全流程拆解与避坑指南

简介:基于 ARIMA、LSTM、Transformer 等模型的流感时间序列预测 Python 源码,面向计算机相关专业课程设计与期末大作业学生,以及项目实战学习者。内容覆盖预处理、平稳性检验、定阶、残差分析、多模型对比预测的完整时序建模流程,…

2026/10/14 3:30:28 阅读更多 →
影刀RPA新手教程:键盘模拟输入实战——输入文本与模拟按键的区别

影刀RPA新手教程:键盘模拟输入实战——输入文本与模拟按键的区别

影刀RPA新手教程:键盘模拟输入实战——输入文本与模拟按键的区别 做影刀RPA自动化,十个新手有八个栽在"往输入框里填东西"这件事上:要么填不进去,要么填了一半,要么直接把原来内容追加在后面。这背后的根因&…

2026/10/14 16:30:29 阅读更多 →
影刀RPA新手教程:阅文起点小说数据采集实战——书籍信息与章节内容

影刀RPA新手教程:阅文起点小说数据采集实战——书籍信息与章节内容

影刀RPA新手教程:阅文起点小说数据采集实战——书籍信息与章节内容 1. 认识影刀:什么场景该用RPA采小说数据 起点中文网的页面结构相对稳定——分类榜单、书籍详情、章节内容三块独立页面,跳转链路清晰。这种场景非常适合影刀自动化&#x…

2026/10/14 3:29:58 阅读更多 →

月新闻

我发现了一个新思路:用 Remotion + Claude Code 像写代码一样自动化生成短视频

我发现了一个新思路:用 Remotion + Claude Code 像写代码一样自动化生成短视频

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/13 22:01:27 阅读更多 →
Windows下 Codex 中 Chrome 和 Computer Use 插件不可用问题排查及解决参考方式:TaoToken 统一 Key 配置与验证

Windows下 Codex 中 Chrome 和 Computer Use 插件不可用问题排查及解决参考方式:TaoToken 统一 Key 配置与验证

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/13 14:57:39 阅读更多 →
黑夜航拍船只数据集训练YOLOV5模型全流程解析

黑夜航拍船只数据集训练YOLOV5模型全流程解析

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/14 7:53:34 阅读更多 →