新闻详情

新闻详情

首页 / 资讯中心 / 详情

SVG-edit 代码重构演进史:从巨型单体 JS 到模块化 SVG Canvas 架构

发布时间:2026/9/27 6:59:27来源:尧图网络
SVG-edit 代码重构演进史:从巨型单体 JS 到模块化 SVG Canvas 架构
前端图形学【免费下载链接】svgeditPowerful SVG-Editor for your browser项目地址https://gitcode.com/gh_mirrors/sv/svgedit点击查看免费下载SVG-edit 曾经把整个编辑器塞进svg-editor.js界面与svgcanvas.js其余一切两个文件到 2010 年 10 月后者已膨胀至约 11600 行 JavaScript。这篇技术文章以项目早期官方 Wiki 文档 CodeRefactoring.md 为骨架还原这场拆巨文件重构的动机、方法、里程碑与遗留 TODO并结合当前仓库源码展示其终局形态svgedit/svgcanvas已按职责拆分为三十余个核心模块。读完你将理解为什么巨型单文件会扼杀开源项目的协作活力掌握渐进式模块拆分 单元测试 构建期合并Closure Compiler / Vite这套可复制的重构方法论并能在当前代码库中按图索骥找到当年重构设想的落地证据。重构的动机为什么 11600 行的单文件必须被拆开SVG-edit 起步时极小整个项目只包含两个 JS 文件svg-editor.js——本质上承载编辑器 UIsvgcanvas.js——承载其余一切绘图、选择、路径、图层、撤销等全部逻辑。随着功能持续叠加扩展机制虽然把部分特性从主代码库中分离出去但到 2010 年 10 月svgcanvas.js依然达到了约 11600 行 JavaScript。作者 Jeff Schiller 在文中给出了两个核心担忧对新人开发者极不友好一个巨型文件无论注释多详尽、组织多规整都难以吸引新贡献者——想搞懂项目如何工作本身就构成巨大门槛。对依赖零散业余贡献者的开源项目而言这是致命问题。作者本人即是亲历者2010 年初暂停重度贡献、年末回归时发现自己已迷失在这个大文件里。测试手段只能靠手点当时验证任何新改动的唯一现实途径是打开编辑器手动试功能。这种方式只能证明新功能能用却完全无法捕捉是否破坏了既有功能。只依赖人工测试的代码库长期必然进展缓慢。历史背景2009 年的分文件提议与 2010 年的正式启动其实早在 2009 年NarendraNarendra Sisodiya就曾提议把 JS 功能拆分到独立文件——他自己离开项目又回归时也遇到了同样的迷路问题并已贡献了独立的本地化脚本locale.js作为示范。但当时作者对 Web 应用如何做模块化尚无头绪他不愿为每个script标签发起独立 GET 请求也觉得locale.js这种做法略让人在意加上当时正处在功能高速迭代期拆分计划被搁置。等到作者自己站到 Narendra 当年的位置、代码量又增长了一个数量级之后才真正意识到这件事的重要性。于是从版本 r1817 开始他着手逐步拆解代码。重构的核心原则是做增量、谨慎的拆分绝不引入新 bug。作者坦言并未完全做到零回归但至少没有酿成重大事故。重构方法命名空间收编 按功能拆模块 脚本按序加载重构后被拆出的代码统一收编到svgedit全局命名空间之下。当时的最终目标是一切代码都归入该命名空间但仍有svgEditor、svgCanvas等部分暂未迁入。以browser.js为例它导出了一批浏览器探测函数svgedit.browser.isOpera() svgedit.browser.isWebkit() svgedit.browser.isGecko() svgedit.browser.supportsSelectors() svgedit.browser.supportsPathReplaceItem() ...当时重构后的整体格局可以概括为四点开发版 SVG-edit 使用多个script标签按序加载全部 JS 模块模块间依赖关系当时仍靠人工维护JS 文件必须按正确顺序加载每个新 JS 模块在test/下都有对应的测试文件Makefile已更新使用Closure Compiler将所有 JS 模块编译合并为单个文件把发布版的 GET 请求数重新降回合理水平。文中特别注明这是一项持续中的工程当时svgcanvas.js仍约有 8800 行并偶有增长作者的搞怪基准是希望每个文件都能在 Google Code 上顺畅浏览——当时直接打开svgcanvas.js会让浏览器卡死。单元测试拆一个模块补一组测试作者在重构的每一个模块/函数/类上都补写了单元测试。截至文中记录文中写 Jan 2010按其上下文应为 2011 年前后项目已有接近 500 个单元测试全部通过test/all_tests.html统一运行。这一点在当前仓库中得到了完整继承与大幅强化tests/unit/下按模块一一对应测试文件例如 draw.test.js、history.test.js、path.test.js、select.test.js、sanitize.test.js 等测试统一由 Vitest 驱动见 package.json 中test: vitest run --coverage node scripts/run-e2e.mjs并配合 Playwright 跑端到端用例。当年每个模块配一个测试文件的设想如今已固化为tests/unit目录的真实组织结构。当时的进行中任务与 TODO 清单文中记录的进行中任务Drawing 抽象作者引入Drawing概念来封装单个打开 SVG 文档的状态。编辑器持有一个当前 drawing 的句柄用它代替直接访问 SVG DOM 元素图层、当前编辑上下文、文档历史等代码最终都应迁入draw.js但当时大部分仍在svgcanvas.js。pathActions 迁移正把svgcanvas.js中一大块名为pathActions的代码迁移到独立模块path.js。这块代码依赖很多只能逐块搬移当时约迁移了一半且大部分公共 API仍留在svgcanvas.js。TODO 清单完成将图层功能移入 Drawing 类将current_group与上下文功能移入 Drawing将setSvgString()与importSvgString()移入独立模块将pathActions移入独立模块重新生成 API 文档想办法让 Closure Compiler 把svgedit.browser.isOpera()编译成svgedit$browser$isOpera()以便进一步优化缩小编译产物并降低运行时开销。文末还列了两个拟调研方向改用 jscode 风格的文档适度引入 Closure 的goog.require/provide但顾虑是 Closure 与 jQuery 功能重叠显著需避免拉入不需要的代码。从当年蓝图看当前仓库重构如何真正落地距离该文档写下十余年后的今天这份蓝图的几乎每一项都已在代码库中兑现。当前项目已演化为 npm workspace 结构见根目录 package.json 的workspaces字段核心绘图引擎独立成包 packages/svgcanvas/package.jsonsvgedit/svgcanvas当前版本 7.4.2彻底摆脱了两个巨型 JS 文件的旧格局。svgedit命名空间与 browser 模块的现代化当年的svgedit.browser.isWebkit()等函数式 API如今演化为 packages/svgcanvas/common/browser.js 中的BrowserDetector类与单例导出isWebkit()、isGecko()、isChrome()、isMac()、supportsGoodTextCharPos()仍以函数形式导出以保持兼容同时内部采用现代特性检测 惰性求值 Map 结果缓存#cachedResults并暴露browser.isWebkit等 getter。该模块被多处真实调用如 select.js 用isWebkitselected-elem.js 用isGeckosvg-exec.js 同时用到三者text-actions.js 用supportsGoodTextCharPosEditor.js 用isMacMainMenu.js 用isChrome。命名空间化的思路在 ES Modules 时代以更彻底的形态延续了下来。Drawing 类当年设想的完全体当年引入 Drawing 封装单文档状态的设想如今完整实现在 packages/svgcanvas/core/draw.js 的Drawing类中它封装svgElem_被编辑的 SVG DOM 元素、obj_num计数、idPrefix、可复用的releasedNums栈、按 z 序排列的all_layers图层数组、layer_map名称索引与current_layer当前图层并通过se:nonce机制支持跨文档随机化元素 ID。getNextId()/releaseId()实现了 ID 的生成与回收复用。在 svgcanvas.js 的构造器中可以看到this.current_drawing_ new draw.Drawing(this.svgContent, this.idprefix)以及clear()时重建Drawing、创建空首层、重置撤销栈的完整闭环——当年 TODO 里完成图层功能移入 Drawing 类已由 layer.js 与Drawing共同完成。pathActions从半途迁移到独立path模块当年pathActions 约迁移一半的工程如今由 packages/svgcanvas/core/path.js 完整承接它向下聚合了路径段数据表segData覆盖 MOVETO/LINETO/CURVETO/ARC 等各类绝对路径段、控制点链接开关linkControlPts再引入 path-method.js 的Path类与 path-actions.js 的pathActions方法集。而 svgcanvas.js 顶部通过import * as pathModule from ./core/path.js取用pathActions构造器中this.pathActions pathActions; pathModule.init(this)——公共 API 留在 svgcanvas.js的过渡态已被清晰的门面导入取代。setSvgString / importSvgString 与 API 文档的归宿当年 TODO 要求把setSvgString()、importSvgString()移入独立模块。在 svgcanvas.js 第 1232 行的注释this BEFORE callingsvgCanvas.setSvgString中仍能看到该方法作为SvgCanvas公共 API 的痕迹而底层序列化/反序列化逻辑已分别沉淀到 json.jsJSON ↔ SVG 元素转换与 sanitize.jsSVG 清洗等模块中。至于重新生成 API 文档当前仓库的 package.json 提供了build-docs基于 JSDoc 与 jsdoc-config.js与open-docs等脚本文档工作已完全脚本化。构建与发布从 Closure Compiler 到 Vite 打包文档时代通过 Makefile Closure Compiler 把所有模块合并回一个文件以减少 GET 请求当前仓库则升级为 Vite 构建链build: vite build packages/svgcanvas vite build packages/react-test vite buildsvgcanvas 包自身的构建脚本为vite build见 packages/svgcanvas/package.json。模块化 构建期合并的核心理念一脉相承只是工具链从 Closure 换成了 Vite且每个子包都产出可独立发布的产物与类型声明svgcanvas.d.ts。当前模块地图重构终局的直观证据packages/svgcanvas/core/目录完整呈现了当年拆分构想的终局——按职责划分的三十余个核心模块每个都对应文档中拆模块 配测试的规划文档状态draw.js、layer.js、dataStorage.js历史/撤销history.js、historyrecording.js、undo.js路径与绘制path.js、path-actions.js、path-method.js、svg-exec.js选择与文本select.js、selection.js、selected-elem.js、text-actions.js坐标与几何coords.js、math.js、recalculate.js、units.js基础能力namespaces.js、sanitize.js、paint.js、clipboard.js、paste-elem.js、copy-elem.js、clear.js、event.js、blur-event.js、touch.js、svgroot.js、elem-get-set.js、json.js、utilities.js。与此同时src/editor/侧承载 UI 层Editor.js、MainMenu.js、panels、components 等src/editor/extensions 继续扮演文档中提到的扩展机制角色把特色功能从主代码库中分离出去——这正是当初促使svgcanvas.js不至于无限膨胀的那道防线。结语一次重构留下的可迁移方法论回看这篇写于项目早期的重构文档它最宝贵的遗产并非某个具体拆分而是一套任何中型前端项目都可复用的方法论模块化不只关乎代码组织更关乎社区活力——巨型单文件会把潜在贡献者挡在门外这在依赖志愿协作的开源项目中尤为致命以可浏览、可测试为基准——每拆出一个模块就配套单元测试当时近 500 个如今tests/unit数十个测试文件用测试网兜住人工验证的盲区开发期多文件、发布期合并——通过构建工具当年 Closure Compiler如今 Vite在发布时把模块重新折叠平衡开发可读性与运行时请求数这对矛盾渐进式迁移而非大爆炸重写——对依赖复杂的代码块如pathActions逐块搬移、保持公共 API 兼容是降低回归风险的关键。如今你可以在 packages/svgcanvas/core 目录中逐文件验证这份十余年前的蓝图——每一个当年 TODO 的落点都能在当前源码里找到对应模块、对应测试与对应构建脚本。赞分享前端图形学【免费下载链接】svgeditPowerful SVG-Editor for your browser项目地址https://gitcode.com/gh_mirrors/sv/svgedit点击查看免费下载相关推荐78 个免费公共 Tracker 清单两步接入 qBittorrent让 BT 下载提速78 个免费公共 Tracker 清单两步接入 qBittorrent让 BT 下载提速 trackerslist 帮你维护一份免费公共 Tracker 服Hound白名单策略实战如何用 --files 让AI代码审计聚焦关键文件、告别Token洪流Hound白名单策略实战如何用 files 让AI代码审计聚焦关键文件、告别Token洪流 用Hound做AI代码审计时你是不是也遇到过这样的场景一个中KICS安全扫描引擎核心算法深度解析KICS安全扫描引擎核心算法深度解析 KICSKeeping Infrastructure as Code Secure是Checkmarx推出的一款强大的数据库低代码后端前端上一篇跨浏览器兼容性挑战easytimer.js 如何优雅支持IE9到现代浏览器下一篇DECAF终极动态二进制分析框架 - 让恶意软件无所遁形创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
网站建设高端定制企业官网
RELATED

相关资讯

更多精彩内容,欢迎继续阅读

较早相关资讯

最新相关资讯

阿里云网站空间申请避坑指南:新手必知的5个注意事项 2026/9/27 7:44:28

阿里云网站空间申请避坑指南:新手必知的5个注意事项

阿里云网站空间申请避坑指南:新手必知的5个注意事项 找建站公司报价时,你是否也曾被“高端定制”的词汇唬住,生怕自己不懂行被宰?别慌,其实大多数中小企业官网并不需要昂贵的全定制开发。今天咱们不聊虚的,直接拆解 阿里云网站空间申请…

阅读更多 →
电视直播网站建设避坑:报价不透明?改需求拖一周? 2026/9/27 7:44:16

电视直播网站建设避坑:报价不透明?改需求拖一周?

电视直播网站建设避坑:报价不透明?改需求拖一周? 改个需求建站公司拖一周,这种憋屈事儿干过互联网的都懂。你急得跳脚催进度,对方还在走流程,最后交出来的东西还跟预期差十万八千里。更让人头疼的是 建站报价…

阅读更多 →
Amazon SDE Coding Interview:常见题型、解题思路与面试准备 2026/9/27 7:44:16

Amazon SDE Coding Interview:常见题型、解题思路与面试准备

准备 Amazon SDE面试时,Coding Interview 是非常重要的一部分。很多候选人会直接开始刷 LeetCode,但真正进入面试后会发现,面试官考察的不只是“能不能写出代码”,还包括问题分析、算法选择、复杂度分析、Edge Cases 以及 Follow-…

阅读更多 →
3步搞定德国著名的外贸公司地址展示,拒绝模板丑站 2026/9/27 7:44:09

3步搞定德国著名的外贸公司地址展示,拒绝模板丑站

3步搞定德国著名的外贸公司地址展示,拒绝模板丑站 还在用那种一眼假的模板网站?后台改个颜色都卡半天,客户一看觉得你们公司不靠谱。 做外贸最怕什么?怕客户进不来,更怕客户进来觉得“这公司是不是皮包公司”。 今天不聊虚的,直接拆解 最佳实践…

阅读更多 →
cryptography 中的 Poly1305:一次性密钥消息认证码(MAC)完整使用指南 2026/9/27 7:44:03

cryptography 中的 Poly1305:一次性密钥消息认证码(MAC)完整使用指南

密码学 【免费下载链接】cryptography cryptography is a package designed to expose cryptographic primitives and recipes to Python developers. 项目地址: https://gitcode.com/gh_mirrors/cr/cryptography 点击查看 免费下载 本篇技术指南以 cryptography 项…

阅读更多 →
Ajenti 安全加固实战:基于 Fail2ban 的暴力破解防护配置指南 2026/9/27 7:43:50

Ajenti 安全加固实战:基于 Fail2ban 的暴力破解防护配置指南

后端运维 【免费下载链接】ajenti Ajenti Core and stock plugins 项目地址: https://gitcode.com/gh_mirrors/aj/ajenti 点击查看 免费下载 Ajenti 是一个基于 Python 的轻量级 Web 管理平台,包含 Ajenti Core(平台本身,含 HTTP…

阅读更多 →

今日资讯

本周资讯

本月资讯

看完文章仍有疑问?

联系尧图顾问,获取一对一建站咨询

立即免费咨询 📞 400-888-8888
📞 ✉