Open edX 平台 TinyMCE 升级、CodeMirror 插件集成与 tinymce.full.min.js 构建指南
2026/9/16 15:35:08 网站建设 项目流程

Open edX 平台 TinyMCE 升级、CodeMirror 插件集成与 tinymce.full.min.js 构建指南

【免费下载链接】openedx-platformThe Open edX LMS & Studio, powering education sites around the world!项目地址: https://gitcode.com/GitHub_Trending/ed/openedx-platform

TinyMCE 是 Open edX Studio(CMS)中 HTML 组件、富文本编辑的核心依赖,而本文所对应的 BUILD_README.md 正是维护这一 vendored 依赖的官方操作手册。本文将完整继承该文档的升级流程、CodeMirror 插件集成步骤与tinymce.full.min.js打包方法,并结合当前仓库中实际存在的 EDX 定制源码与加载配置,深入剖析每一步背后的实现细节,帮助你安全、可复现地完成 TinyMCE 的版本升级与自定义构建。

一、TinyMCE 在 Open edX 中的角色与本文适用范围

在 Open edX 仓库中,TinyMCE 并非通过 npm 运行时安装,而是以“vendored 静态文件”的形式直接存放在common/static/js/vendor/tinymce/目录下。从源码结构可以确认它的三个关键使用点:

  • 编辑器加载入口:xmodule/js/src/html/edit.js 中通过tinyMCE.baseURLtinyMCE.suffix等配置定位 TinyMCE,并以script_url: baseUrl + "js/vendor/tinymce/js/tinymce/tinymce.full.min.js"的方式加载打包后的单文件版本;
  • AMD/RequireJS 模块映射:cms/static/cms/js/require-config.js 将tinymce映射到js/vendor/tinymce/js/tinymce/tinymce.full.min,将jquery.tinymce映射到jquery.tinymce.min
  • 皮肤资源注册:cms/envs/common.py 中注册了js/vendor/tinymce/js/tinymce/skins/ui/studio-tmce5/content.min.cssskin.min.css,即仓库中定制的studio-tmce5皮肤。

因此,任何 TinyMCE 版本升级都必须同时保证“源码目录结构”、“tinymce.full.min.js打包内容”、“CodeMirror 源码编辑插件”三者保持一致,这正是本文操作流程存在的意义。

二、升级 TinyMCE 的整体流程(五步总览)

BUILD_README 给出了升级的宏观路径,可概括为以下五步,后文将逐一展开:

  1. 下载目标版本:从 TinyMCE 官方标签页获取所需版本的发行包;
  2. 主版本升级迁移:若属于主版本(major)升级,先阅读官方迁移文档并修改平台调用代码;
  3. 重新配置 codemirror-plugin:按下文第三节的步骤重建源码编辑插件;
  4. 识别并合并 EDX 定制:在 vendor 目录中搜索字符串EDX,找出全部本地定制点并应用到新版本;
  5. 重新生成tinymce.full.min.js:按下文第四节的命令重新打包。

注意:以上“下载地址”“官方迁移文档”“插件仓库”均为原文档给出的外部来源,本文不展开外部链接,实际操作时请以对应版本的官方发布物为准。

三、详细操作:配置 codemirror-plugin

CodeMirror 插件为 TinyMCE 提供“HTML 源码编辑”能力(工具栏上的HTML按钮),它是 Open edX 定制最深的一个插件。BUILD_README 的配置步骤如下:

  1. 下载插件:从tinymce-codemirror插件仓库下载源码;
  2. 安装并生成压缩文件:在插件目录打开终端执行:
    npm install npm run prepublish

    prepublish会在插件目录中生成压缩后的plugin.min.js

  3. 删除旧版 CodeMirror:移除tinymce-codemirror/plugins/codemirror/codemirror-4.8目录(插件自带的 4.8 版 CodeMirror 不适用于 Open edX 的托管方式);
  4. 移动 plugins 目录:将tinymce-codemirror/plugins目录整体移动到common/static/js/vendor/tinymce/js/plugins/
  5. 应用 EDX 定制:把上一轮版本中累积的 EDX 改动重新应用到新的plugin.jssource.html
  6. 安装 uglify-js 并生成plugin.min.js
    cd common/static/js/vendor/tinymce/js/plugins/codemirror/ uglify plugin.js -m -o plugin.min.js

IMPORTANT NOTE(原文强调):每次重新生成codemirror插件的plugin.min.js后,都必须同步重新生成tinymce.full.min.js聚合包,否则新改动不会进入编辑器实际加载的 bundle。

3.1 从源码看插件的工作机制与 EDX 改动清单

当前仓库中插件代码位于 common/static/js/vendor/tinymce/js/tinymce/plugins/codemirror/plugin.js 与 source.html,其中所有 EDX 定制均以// EDX:注释明确标注(可用grep -r "EDX" common/static/js/vendor/tinymce/复核)。主要定制点包括:

  • 基于 iframe 与 postMessage 的跨窗口通信:TinyMCE 5 中windowManager.openUrl返回的是 dialog API 而非 window 对象,因此 EDX 改用win.sendMessage/window.addEventListener("message", ...)实现编辑器与源码弹窗之间的双向消息传递,并校验codeEditorOriginevent.origin防止跨源消息注入(plugin.js);
  • onClose清理监听器:弹窗关闭时移除message监听器,避免内存泄漏(plugin.js);
  • onAction消息化改造:TinyMCE 5 下“Ok/Cancel”按钮通过postToCodeEditor({type: "save"})/{type: "cancel"}通知弹窗,而不是直接引用窗口对象(plugin.js);
  • 光标占位符清理 Bug 修复:修复CmCaReT光标占位 span 在<style>标签内残留的问题(plugin.js);
  • 工具栏按钮文案定制:TinyMCE 5 下按钮显示为 “HTML”,tooltip 为 “Edit HTML”(plugin.js);
  • 单文件加载 CodeMirror:将原本的多个 CodeMirror 依赖文件(codemirror.js、各 addon、edx_markdown.js等)注释掉,统一改为加载codemirror-compressed.js单文件,减少请求数(source.html);
  • 通过 query 参数传递运行时路径CodeMirrorPathParentOrigin通过 URL 查询串传入source.html,因为页面渲染时 JS/CSS 必须同步注入<head>,无法依赖 postMessage 时序(source.html)。

3.2 插件可配置项(从源码推导)

showSourceEditor()中读取的editor.settings.codemirror配置项如下,可在初始化 TinyMCE 时传入:

配置项默认值说明
path必填CodeMirror 静态资源的 base 路径,用于拼装source.htmlCodeMirrorPath参数
width800源码编辑弹窗宽度(像素)
height550源码编辑弹窗高度(像素)
fullscreenfalse是否以全屏方式打开(TinyMCE 5 下该逻辑被注释,见源码说明)
saveCursorPositiontrue打开源码视图前是否在编辑器内容中插入CmCaReT光标占位以恢复光标位置

插件本身还携带多语言包(plugins/codemirror/langs/下含cs_CZdeenes_ESfr_FRnlpt_BRpt_PTruukzh_TW等),通过tinymce.PluginManager.requireLangPack('codemirror')注册。

四、详细操作:创建 js/tinymce.full.min.js

BUILD_README 以5.5.1版本为例给出打包流程,升级其他版本时只需替换文件名中的版本号。核心思路是:利用 TinyMCE 官方构建产物,把核心库 + 所有插件 + 表情符号数据按固定顺序拼接到一个单文件中。

  1. 解压官方发行包
    unzip tinymce-5.5.1.zip
  2. 进入解压目录
    cd tinymce-5.5.1
  3. 使用 Yarn 构建(会在dist目录生成多个 zip 包):
    yarn && yarn build
  4. 解压 dev bundle 到 edx-platform 的 vendor 目录
    unzip dist/tinymce_5.5.1_dev.zip -d /path/to/edx-platform/common/static/js/vendor/

    注意解压后应形成common/static/js/vendor/tinymce/目录结构,与 当前仓库目录 保持一致;

  5. 清理多余文件:删除common/static/js/vendor/tinymcepackage.jsonyarn.lock等构建与包管理文件(这些文件不属于运行时资源);
  6. 生成聚合 bundle
    cd common/static/js/vendor/tinymce/js/tinymce LC_ALL=C cat tinymce.min.js */*/*.min.js plugins/emoticons/js/emojis.min.js > tinymce.full.min.js

4.1 拼接命令的要点解读

  • LC_ALL=C:强制使用 C 语言环境,避免cat在拼接二进制/非 UTF-8 内容时因 locale 差异产生不一致行为,保证打包可复现;
  • 通配符*/*/*.min.js:覆盖themes/silver/theme.min.jsplugins/*/plugin.min.js等两级子目录下的所有压缩文件。这与当前仓库的目录结构吻合——themes/plugins/均为“类别/插件名/plugin.min.js”的二级布局;
  • plugins/emoticons/js/emojis.min.js:emoticons 插件的表情符号数据位于三级目录下,需单独追加,否则该插件的 emoji 面板会缺失数据;
  • 拼接顺序:核心库(tinymce.min.js)在前,主题与插件随后,emoji 数据最后,确保文件加载依赖顺序正确。

4.2 当前仓库的产物形态

对照 common/static/js/vendor/tinymce/js/tinymce/ 目录,可以看到:tinymce.full.min.js已存在且是实际被加载的文件(见 require-config.js 与 edit.js);同时保留了tinymce.js/tinymce.min.js原始核心文件、jquery.tinymce.min.js集成文件、tinymce.d.ts类型声明,以及skins/ui/studio-tmce5/定制皮肤(含content.csscontent.inline.cssskin.css、移动端皮肤及tinymce-mobile.woff字体)。这些文件正是构建流程各步骤的直接产物,可作为升级后自检的对照基准。

五、升级时的 EDX 定制合并方法(实操要点)

BUILD_README 指出,升级的核心风险点在于本地定制。合并流程如下:

  1. 当前正在使用的 TinyMCE 版本的 vendor 目录中搜索字符串EDX,定位全部本地改动:
    grep -rn "EDX" common/static/js/vendor/tinymce/

    从当前仓库看,命中文件集中在js/tinymce/plugins/codemirror/plugin.jssource.html(另有本 README 自身);

  2. 逐条比对改动内容,将每一处// EDX:标注的修改迁移到新下载版本对应的同名文件中(插件配置、消息通信、Bug 修复、文案定制等,详见 3.1 节清单);
  3. 合并完成后,必须重新执行“第三节的plugin.min.js生成”与“第四节的tinymce.full.min.js拼接”两步,确保定制真正进入运行时 bundle。

六、升级完成后的验证清单

基于仓库现有证据,升级完成后建议按以下顺序验证:

  1. 目录完整性common/static/js/vendor/tinymce/js/tinymce/下应同时存在tinymce.min.jstinymce.full.min.jsthemes/(含silvermobile)、plugins/(含codemirror及官方全部插件)、skins/ui/studio-tmce5/langs/icons/default/
  2. bundle 内容:确认tinymce.full.min.js中同时包含核心库、codemirror插件(搜索"codemirror")、emojis.min.js数据(搜索 emoji 关键字);
  3. 加载链路:检查 require-config.js 中tinymce模块映射路径未变,edit.js 中script_url指向的tinymce.full.min.js存在;
  4. 皮肤资源:确认 cms/envs/common.py 引用的studio-tmce5皮肤 CSS 与字体文件均存在;
  5. 功能冒烟:在 Studio 中打开 HTML 组件编辑器,验证工具栏HTML按钮能打开 CodeMirror 源码视图,保存后光标位置、格式化内容正确,且不存在CmCaReT残留。

七、常见问题与注意事项

  • 主版本升级不可跳过迁移:TinyMCE 4→5 的 API 差异巨大(如windowManager.openopenUrl、按钮注册方式变化),仓库中的plugin.js已为双版本分支逻辑做了兼容(通过tinymce.majorVersion < 5判断),升级主版本时务必核对这一分支是否仍然成立;
  • plugin.min.js与 bundle 必须同步:只重新生成插件压缩文件而忘记重建tinymce.full.min.js,会导致编辑器加载到旧逻辑——这是 BUILD_README 专门用 IMPORTANT NOTE 强调的坑;
  • 不要提交构建产物之外的冗余文件:解压 dev bundle 后需清理package.jsonyarn.lock等文件,保持 vendor 目录只包含运行时所需资源;
  • 皮肤与版本匹配studio-tmce5皮肤与 TinyMCE 5.x 的 Silver 主题配套,若升级到 6.x 主版本,皮肤结构可能变化,需要同步评估定制皮肤是否可复用。

通过以上流程,你可以在不依赖包管理器的情况下,以完全可控、可审计的方式维护 Open edX 平台内嵌的 TinyMCE 编辑器:既保留官方插件的完整能力,又可持续叠加 Open edX 的本地化定制,最终产出稳定、可复现的tinymce.full.min.js构建产物。

【免费下载链接】openedx-platformThe Open edX LMS & Studio, powering education sites around the world!项目地址: https://gitcode.com/GitHub_Trending/ed/openedx-platform

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询