0%

魅族云便签导出到本地 Markdown:605 条实录

笔记散在好几个地方,魅族便签是攒得最多的一处。这轮的打算是把它们收敛到本地一个目录,来龙去脉写在锤子便签那篇里。脚本在 GitHub 上:phone-cloud-data-export/flyme-notes。

魅族云便签的网页版在 notes.flyme.cn。我账号里 605 条笔记,时间从 2014 年排到 2022 年,多数是当年在地铁上用手机随手记的。

这套导出也分两步:先在已经登录的页面里跑脚本抓原始 JSON,再在本地转成带 frontmatter 的 Markdown。Cookie 不出本机。

1. 接口

页面是 React 单页应用,接口都是 POST,同源带 Cookie,请求头带 X-Requested-With: XMLHttpRequest。

用到三个:

  • 分类(标签)列表:/c/browser/note/gettags
  • 某个分类下的笔记:/c/browser/note/getnotegroups,参数 start、length、groupUuid,-1 表示「全部」
  • 按内容搜索:/c/browser/note/getnotebycontent,参数 content、start、limit

返回结构是 {returnCode, returnMessage, returnValue},returnCode 为 200 才算成功。登录态过期会返回 302 加一个登录跳转地址,脚本据此判断要不要重新登录。

笔记对象的字段:uuid、title、body、groupStatus(分类 id)、createDate(毫秒时间戳)、updateDate、topdate(置顶)、remind(提醒)、fontSize、status(D 表示回收站)、files(附件的文件名到地址)。

和锤子那份不同,这里创建时间是有的,frontmatter 里 created 和 updated 都有值。

2. 抓取

脚本按「全部」和每个分类各翻一遍页,每页 200 条,按 uuid 去重打包成一个 JSON。

跑完会自报完整性:把抓到的条数和云端各分类条数之和对比,另外打印正文为空的条数。这次的账是:正常 557 条、回收站 47 条、加密占位 1 条,去重后正好 605 条。

关于为什么用浏览器控制台而不是复制 Cookie,理由和锤子那篇一样,这里不重复。

3. 正文是块数组

body 是个 JSON 字符串,里面是按顺序排的块数组。每个块有自己的 state:

  • 0:段落
  • 1 / 2:待办,未完成和已完成
  • 3 / 4 / 5:图片、录音、附件
  • 50 / 51 / 53:有序列表、无序列表、列表项
  • 60:标题,级别在 level 里

文字样式单独放在 span 字段里,长这样:[{span: 样式码, start, end, param}],start 和 end 是字符下标。

样式码对照:

  • 1 加粗
  • 6 下划线
  • 7 斜体
  • 16 字号
  • 17 链接,param 是 URL
  • 18 删除线
  • 19 高亮

转换脚本按这些码还原 Markdown。列表能带嵌套,标题能到六级。

云端 583 条笔记本身没有标题,文件名取正文第一行代替,frontmatter 里的 title 保持云端空值,不编一个出来。

4. 换行

428 条笔记带换行,单换行 5579 处,空行另有 5710 处。

这次用的是行尾两个空格,也就是 Markdown 的硬换行标记。Obsidian 里观感不变,VS Code 预览和 GitHub 上也认。转换后逐条核对过,标记位置和原始换行一一对应。

正文里如果混了 \r\n,会先统一成 \n,否则残留的 \r 会把行切坏。这个坑在短信那篇里踩过。

风格可以换,加 --line-break= 重跑,取值和锤子那篇一致:space、br、blank、keep。

5. 附件

39 个图片和附件还在云端,地址在 cloud.flyme.cn/c/browser/download/...,同样要登录态。要一起落到本地就再跑一次下载脚本,下完把 md 里的云端地址换成本地路径。

6. 核对

node verify.js flyme-notes-raw.json notes 逐条比对 md 和原始 JSON 的创建时间、修改时间、时间戳、标题、分类、正文,并检查有没有漏导。

结果 558/558,缺失 0,字段全部一致。

7. 结果

605 条原始笔记写出 558 个 md,回收站那 47 条默认跳过,加 --include-deleted 可以一起导。

按分类分目录:未分类 496、JAVA 55、study 5、plan 1、生活 1。时间跨度 2014-07-18 至 2022-03-26。文件名是「创建日期 标题.md」。

frontmatter 字段:title、uuid、category、category_id、created、updated、created_ts、updated_ts、status、pinned、remind、font_size、attachments。

这 558 个 md 和锤子便签那批放进同一个库,搜索一次能搜全。Markdown 不绑定工具,Obsidian 和 VS Code 都能直接读,uuid 留着以后跟云端对账。

8. 脚本

抓取、下载附件、转换、校验四个脚本,都用 node 直接跑,没有第三方依赖。

GitHub 仓库:phone-cloud-data-export/flyme-notes