Skip to content

Development and Release

zhangxh edited this page Aug 16, 2026 · 5 revisions

开发与发布

本页说明 TeXLeaf 0.7.2 的源码结构、验证门禁、跨平台验收和 Marketplace/GitHub Release 流程。贡献代码前请同时阅读 片段与模板文献与 ZoteroMath Preview致谢与联合开发,避免破坏已经明确的产品边界。

环境要求

  • Node.js 20 或兼容当前 VS Code Extension Host 的版本;
  • pnpm;
  • VS Code 1.98+ 桌面版;
  • Git;
  • 进行 Zotero 集成验收时需要 Zotero 桌面端,推荐 Better BibTeX;
  • 进行 GitHub 发布时可使用 GitHub CLI gh,也可通过网页创建 Release。

Windows、macOS 和 Linux 都是运行时支持平台。核心 TypeScript、Node Worker、VS Code API 和 Workspace FS 没有把扩展运行时绑定到 Windows 路径;平台特定内容主要位于测试启动器和人工视觉自动化。

获取源码

git clone https://github.com/zhangxh-math/texleaf.git
cd texleaf
pnpm install

仓库路径可以包含空格或非 ASCII 字符,但脚本和 CI 中必须把路径作为独立参数传递,不要用未引用的字符串拼接 shell 命令。

常用脚本

命令 作用
pnpm run check tsc -p tsconfig.json --noEmit 主源码静态检查
pnpm run test:compile 编译测试 TypeScript 到 .test-dist
pnpm test 运行不启动 VS Code 的核心、Snippet、模板、citation、Zotero、Math Preview 单元/集成测试
pnpm run compile 用 esbuild 生成 dist/extension.jsdist/mathPreviewWorker.js
pnpm run test:bundle 检查扩展 bundle 自包含加载和 Math Preview Worker
pnpm run test:extension-host 构建后在隔离 VS Code Profile 运行 Extension Host 回归
pnpm run verify check + tests + compile + bundle smoke
pnpm run release:verify verify + Extension Host 回归
pnpm run package 先过 release:verify,再用 vsce 创建 VSIX
pnpm run watch 开发时持续构建 extension/worker bundle

发布前必须至少运行:

pnpm run release:verify
pnpm run package

不要直接调用 vsce package 绕过测试门禁后就发布。

架构概览

入口与配置

  • src/extension.ts:激活、命令、控制器和生命周期;
  • src/config.ts:38 个设置的读取、兼容值和安全规范化;
  • package.json:三组 Settings、命令、键位、工作区信任和 language defaults。

片段与模板

  • src/core/latexScanner.ts:共享的 TeX 文本/数学/环境扫描器;
  • src/defaultLibrary.tssrc/defaultSnippets.ts:工厂规则;
  • src/snippetRuntime.ts:匹配和 replacement 规划;
  • src/editorController.ts:输入事件、自动展开、分数、Tabout、矩阵快捷键;
  • src/snippetRepository.ts:Profile 内部 JSONC、迁移、CAS、备份和原子替换;
  • src/snippetSync.ts:Settings Sync envelope、lineage 和冲突处理;
  • src/snippetEditorPanel.tssrc/snippetManagerWebview.ts:结构化管理器 host/Webview;
  • src/templateLibrary.tssrc/templateManager.ts:内部模板目录、验证和运行时展开;
  • templates/*.tex:四个出厂模板种子,不是用户运行时可编辑外部依赖。

文献

  • src/core/citation.ts:citation 上下文、逗号分段、BibTeX 解析和范围;
  • src/referenceMatcher.ts:标题/作者/年份/key 搜索和文献身份;
  • src/citationRepository.ts:安全解析 bibliography URI 和 VS Code 文档模型;
  • src/zoteroClient.ts:固定回环 Better BibTeX JSON-RPC 与 Zotero Local API;
  • src/citationController.ts:原生 Suggest、后台缓存、接受和原子导入。

TeXLeaf citation item 左侧是标题+来源,detail 保持空,右侧 Markdown 分字段显示作者、出版物、年份、Citation key、来源和操作状态。改变 UI 时必须同时覆盖:左侧无 key、右侧保留 key、顶部无重复 metadata summary、key 仍可搜索并作为 insertText。

Math Preview

  • src/core/mathPreview.ts:公式快照、宏解析、光标安全边界;
  • src/mathPreviewController.ts:防抖、缓存、Worker、Hover、decoration 和过时结果丢弃;
  • src/mathPreviewWorker.ts:MathJax SVG 渲染与消毒;
  • src/mathPreviewLayout.ts:inline/block 锚点和上下方规划;
  • src/mathPreviewCard.tsmathPreviewAppearance.tsmathPreviewDataUri.ts:卡片几何、主题和安全数据 URI。

Worker 与 extension 分别 bundle;VSIX 中不包含 src/test/ 或 node_modules 散目录。

F5 调试

  1. 用 VS Code 打开仓库根目录;
  2. 运行 pnpm run watch
  3. F5 启动 Extension Development Host;
  4. 在宿主中新建并先保存 .tex
  5. 分别验证 lmdm\thm、管理器、\cite{} 和公式预览;
  6. 修改源码后重新启动调试宿主。

建议使用独立 Profile/临时工作区,避免开发版本迁移真实个人 Snippet 库。

自动化测试层次

纯测试

覆盖:

  • TeX 扫描、数学上下文、标签抑制;
  • trigger 匹配、priority、正则、v1/v2 占位符;
  • 默认 212 条 Snippet 与四个模板;
  • 管理器生成 HTML、CSP、ready 握手、表单和批量替换;
  • citation 分段、BibTeX 解析、查询、去重;
  • Zotero JSON-RPC/Local API、library、导出与错误映射;
  • Math Preview 扫描、宏、光标、SVG、主题和布局。

测试数量会随版本增加,不应在 Wiki 固定为永久不变的数字;0.7.2 发布候选应以当次 pnpm test 的全绿结果为准。

Bundle smoke

test/bundle-smoke.cjs 检查生产 extension bundle 在没有开发源码/散依赖时可以加载;test/math-preview-worker.cjs 直接与 Worker 通信,覆盖 SVG、安全、Unicode、宏隔离、并发和错误恢复。

Extension Host

test/run-extension-host.cjs 创建唯一临时目录、隔离 user-data/extensions、双根 workspace,并禁用其他扩展后运行 test/extensionHost.cjs。覆盖真实 VS Code API 行为:

  • 激活与命令/设置清单;
  • 片段、模板、键位、迁移、备份、Sync;
  • 管理器相关入口;
  • 原生 citation label/detail/documentation/range/filter;
  • Math Preview Hover、安全 SVG 和主题;
  • .tex/.bib/Untitled/多根作用域。

临时目录删除前会验证它确实是由本次 mkdtemp 创建的目标,避免递归删除错误路径。

Math Preview 视觉验收

仓库提供固定场景:

  • inline
  • multiline-inline
  • display
  • nested-display
  • tall-display

Windows 开发机可运行:

node .\test\run-math-preview-visual-host.cjs --scenario multiline-inline --placement auto --theme dark
node .\test\run-math-preview-visual-host.cjs --scenario nested-display --placement auto --theme light --debug-port 9339
node .\test\math-preview-cdp-check.cjs --port 9339 --scenario nested-display

CDP 只绑定 127.0.0.1,检查真实 Monaco ::before 几何而不修改用户窗口。nested-display 要求卡片与 opening delimiter 误差不超过 3 px;tall-display 要求高度未被错误压缩并保持上方尾部策略。

这些视觉辅助脚本当前以 Windows 的 Code.exe/窗口环境作为主要、经过验证的自动化入口;虽然部分 runner 可通过环境变量指向其他可执行文件,但不能把它当作已完成的 macOS GUI 自动化。test/ 和这些脚本由 .vscodeignore 排除,不会进入 VSIX,因此不影响 macOS/Linux 运行时兼容性。

macOS 实机发布验收

每个 Release 至少应在真实 macOS VS Code 做一次人工检查:

  1. 从最终 VSIX 安装,而不是源码 F5;
  2. 在 Apple Silicon(可用时也抽查 Intel)打开已保存 .tex
  3. 验证 Cmd+Alt+L、Tab、Enter、Shift+Enter、Escape;
  4. 展开 lmdm\thm 和四个模板;
  5. 在本机 Zotero/BBT 中测试已有与未导入条目、多 key citation;
  6. 深色/浅色、Retina 和系统推荐缩放下检查行内活动行对齐、行间 opening 对齐、鲜艳光标和不透明卡片;
  7. 检查 Hover fallback、超宽裁切与超高尾部;
  8. 确认没有调用 Windows 路径、PowerShell、Code.exe 或测试脚本。

Linux 也应至少在一个常见发行版/桌面会话做安装、片段、引用回环和预览冒烟,特别注意 Snap/Flatpak 沙箱与 Wayland 分数缩放。

管理器手工验收

  • 全新 Profile 打开管理器,加载 212 条 Snippet 和四个模板;
  • 搜索、分类/状态筛选、添加、复制、删除;
  • 修改 trigger/replacement/options/category/description/priority/flags/syntaxVersion/enabled;
  • 表单同行输入框顶部对齐,说明文字位于字段下方;
  • 模板名称/trigger/说明/正文可编辑;
  • 查找替换字段范围、大小写、regex、预览、应用、撤销;
  • Ctrl+S/Cmd+S 后新 trigger 立即生效;
  • 另一个窗口修改后,旧草稿保存必须报 revision 冲突;
  • 超长字段/总量在进入永久 busy 前被拒绝;
  • 恢复默认会保护 dirty Webview 和高级 JSONC。

Citation 手工验收

准备:

  • 两条 bibliography 现有文献;
  • 两条 Zotero 未导入文献;
  • 标题、作者、年份和 key 可区分。

检查:

  1. \cite{} 自动打开原生 Suggest;
  2. bibliography 条目排序在 Zotero 条目前;
  3. 左侧 TeXLeaf 行只有标题和来源,无 key、无 metadata detail;
  4. 右侧标题下没有重复“作者 · 期刊 · 年份”summary;
  5. 右侧分字段含作者、期刊/出版物、年份、Citation key、来源和状态;
  6. 标题、作者、年份和 key 查询都能筛选;
  7. 输入查询、退格清空、再次输入仍自动重开;
  8. \cite{keepA, query, keepB} 只替换 query;
  9. BibTeX/BibLaTeX、自定义路径、群组库、dirty .bib、Undo;
  10. Zotero 关闭、端口错误、库错误、超时和 Local API fallback;
  11. 未信任工作区不访问端口、不写入文件;
  12. 安装 LaTeX Workshop 时确认第三方候选无法由 TeXLeaf 选择性删除,并验证文档中推荐的 label 配置行为。

安全与许可检查

发布前确认:

  • Snippet JSONC 仍是纯数据,不引入 eval/Function;
  • Zotero endpoint 仍固定 127.0.0.1,路径设置仍限制在 workspace 内;
  • Webview 有 nonce CSP,不用 innerHTML 注入用户数据;
  • MathJax Worker 输入长度/宏/队列/超时仍有限制;
  • 输出 SVG 仍拒绝脚本、事件属性、外部 URL 和 foreignObject;
  • 并发保存、恢复、Sync 与 bibliography 写入仍有 revision/版本校验;
  • THIRD_PARTY_NOTICES.mdlicenses/Apache-2.0.txt 与 bundle 依赖一致;
  • README、Wiki 致谢与 THIRD_PARTY_NOTICES.md 能准确区分产品灵感、实际发行依赖和相应许可证;
  • LICENSE、第三方 notice 和模板隐私清理完整。

Release 检查清单

  1. 更新 package.json 版本为 0.7.2,同步 README/CHANGELOG;
  2. 确认 README 只按片段、文献、预览三部分描述;
  3. 检查出厂 article 模板使用 \bibliographystyle{alpha}
  4. 运行 pnpm install --frozen-lockfile(CI/干净环境);
  5. 运行 pnpm run release:verify
  6. 完成 Windows、macOS、Linux 对应的自动/人工验收;
  7. 运行 pnpm run package 生成 texleaf-0.7.2.vsix
  8. vsce ls --no-dependencies 或解包检查 VSIX 清单;
  9. 确认不包含 src/test/.git/、node_modules 散目录、旧 VSIX、日志或用户数据;
  10. 在全新隔离 Profile 安装最终 VSIX再做一次管理器、citation 和 Math Preview 冒烟;
  11. 记录文件大小和 SHA-256;
  12. 提交可审阅的源码变更,创建签名/普通 tag v0.7.2
  13. 推送源码分支和 tag;
  14. 创建 GitHub Release,把 VSIX 作为 Release asset 上传;
  15. 下载 Release 资产复核哈希和安装。

二进制只放 GitHub Release

源码仓库的 .gitignore 排除:

dist/
out/
.test-dist/
*.vsix
*.tgz

正确发布模型:

  • Git commit:TypeScript、package/lockfile、模板、测试、README、许可证;
  • Git tag:对应可复现版本;
  • GitHub Release:texleaf-0.7.2.vsix、release notes,可选哈希;
  • 不把 VSIX 通过 Git LFS 或普通 Git 放进源码历史;
  • 不把本地 dist/ 当作源码提交。

示例(确认仓库、tag 和权限后执行):

git tag v0.7.2
git push origin main
git push origin v0.7.2
gh release create v0.7.2 texleaf-0.7.2.vsix \
  --title "TeXLeaf 0.7.2" \
  --notes-file RELEASE_NOTES.md

不要自动覆盖已经存在的 Release 或 tag;发现同名对象时先核对其 commit 和资产。

Wiki 发布

GitHub Wiki 是独立 Git 仓库,地址通常为:

https://github.com/zhangxh-math/texleaf.wiki.git

本项目先在源码工作区的 .wiki-publish/ 准备页面;该目录由 .gitignore 排除,不进入源码 commit。发布时将这些 Markdown 复制/提交到独立 wiki 仓库:

git clone https://github.com/zhangxh-math/texleaf.wiki.git texleaf.wiki
# 将 .wiki-publish/*.md 放入 texleaf.wiki/
cd texleaf.wiki
git add Home.md _Sidebar.md *.md
git commit -m "Document TeXLeaf 0.7.2"
git push origin master

实际默认分支可能是 master 或其他名称,以 git branch -r 为准。推送前检查:

  • Home.md 存在;
  • _Sidebar.md 链接到全部页面;
  • Wiki 链接目标与文件 basename 一致;
  • 页面没有源码工作区绝对路径、个人信息或临时资产;
  • Wiki 仓库不包含 VSIX;二进制仍只属于 Release。

贡献准则

  • 一次提交聚焦一个可审阅目标;
  • 不覆盖用户工作树中的无关修改;
  • 改行为必须同步测试和用户文档;
  • 诊断问题与实现修复分开描述;
  • 对 VS Code 未公开 API 的兼容层明确写出限制和降级;
  • 外部项目只能借鉴公开产品行为,复制代码/资源必须满足许可并记录来源;
  • 网络、本机端口、文件写入、Webview 和递归删除必须有明确边界。

相关页面

Clone this wiki locally