首页
/ MkDocs Material 内置 offline 插件:构建无需服务器、可离线分发的文档站点

MkDocs Material 内置 offline 插件:构建无需服务器、可离线分发的文档站点

2026-09-10 10:58:29作者:宣海椒Queenly

Material for MkDocs 是为数不多能够构建"离线可读"文档的静态站点框架之一——生成的文档无需 Web 服务器,用户解压后直接双击 index.html 即可浏览。本文围绕内置的 offline 插件,讲解其工作原理(如何让搜索在 file:// 协议下继续工作)、mkdocs.yml 中的最小配置与 enabled 参数、与隐私/优化插件的配合方式,以及启用离线构建时必须注意的功能限制,帮助你产出可直接以 .zip 形式分发的离线文档包。

Objective:为什么需要 offline 插件

工作原理:从 file:// 到可用交互

MkDocs 构建出的 site 目录本质上是一组纯静态的 HTML、CSS、JS 与资源文件。按照 构建站点 的流程完成 mkdocs build 后,切换到 site 目录并双击 index.html,文档即可在本地文件系统中直接打开,浏览器地址栏会显示 file:// 前缀。

但问题随之而来:Material for MkDocs 的许多交互功能依赖 Fetch API 发起网络请求,而现代浏览器出于安全考虑,禁止从 file:// 页面发起跨源请求,通常会抛出类似如下错误:

Cross origin requests are only supported for protocol schemes: http, [...]

站点搜索正是受影响最明显的功能——搜索索引 search/search_index.json 需要通过 Fetch API 获取,一旦走 file:// 协议便会失败,搜索框形同虚设。

offline 插件正是为解决这一问题而生的。它在构建阶段做了两件事:

  1. 把搜索索引内联为 JavaScript 文件:在 on_post_build 钩子中,读取 site_dir/search/search_index.json 的内容,生成同目录下的 search_index.js,其内容形如 var __index = {...},让搜索数据不再依赖网络请求。
  2. 追加 iframe-worker 垫片(shim):通过 @squidfunk/iframe-worker 项目,用隐藏 iframe 模拟 Web Worker 的异步能力,使 Lunr.js 搜索逻辑在 file:// 协议下也能正常执行。

此外,插件在 on_config 钩子中自动关闭 use_directory_urls。目录式 URL(如 foo/bar/)依赖服务器重写才能正确解析,而本地文件系统没有这一能力;关闭后链接会退化为 foo/bar.html 形式,保证从本地直接打开时所有链接都能正确解析。这两项改动由 src/plugins/offline/plugin.pyOfflinePluginon_configon_post_build 两个钩子完成,其中 on_post_build 被标注为 @event_priority(-100),确保其在构建流程的末尾、其他插件处理完成之后才执行。

何时使用

插件的定位非常明确:只在为离线分发构建站点时才启用它。也就是说,如果你正计划把整个 site 目录打包成 .zip 发给用户,offline 插件就是关键一环;而如果站点始终托管在服务器上,则没有必要启用。

离线场景下,offline 插件还与其他内置插件配合默契,能组合出更完整的离线体验:

  • 内置 privacy 插件:离线构建时外部资源(字体、CDN 脚本等)无法访问,privacy 插件会在构建时自动把外部资源下载并内联进产物,让你的文档在完全断网的环境下也能正常渲染。
  • 内置 optimize 插件:自动识别并压缩、转换站点引用的所有媒体文件,减小产物体积,让最终分发的 .zip 更小、下载更快。

有人可能会问:为什么不让 offline 插件顺带实现外部资源下载?这是因为该能力已在 privacy 插件中完整实现,并成为其存在的核心理由。Material for MkDocs 的插件体系遵循模块化设计——各插件各司其职又相互增强,几个简单的配置即可解决复杂问题。

Configuration:在 mkdocs.yml 中启用

与所有 内置插件 一样,offline 插件的启用极其简单。在 mkdocs.yml 中添加如下配置即可:

plugins:
  - offline

offline 插件随 Material for MkDocs 内置分发,无需单独安装。从源码结构看,它由 src/plugins/offline/config.py 定义配置项、src/plugins/offline/plugin.py 实现具体逻辑,二者对应发布在 material/plugins/offline/ 目录下。

General:enabled 参数

插件目前唯一的配置项是 enabled

参数 类型 默认值 说明
enabled 布尔 true 是否在构建站点时启用离线处理

默认值为 true,即一旦在 plugins 中声明 offline,离线构建能力即生效。若希望一套配置同时产出在线与离线两种产物,可借助 环境变量 控制开关——例如默认关闭、仅当设置 OFFLINE 环境变量时才启用:

plugins:
  - offline:
      enabled: !ENV [OFFLINE, false]

使用该方式时,普通构建(mkdocs build)生成的是常规在线站点;而在设置 OFFLINE=true 的环境下构建,则得到可离线分发的产物。从 config.pyOfflineConfig 可以看到,enabled 通过 Type(bool, default = True) 定义,plugin 的两个钩子也都以 if not self.config.enabled: return 作为守卫,关闭时不会产生任何副作用。

Limitations:必须关闭的功能

浏览器的安全限制决定了并非所有交互功能都能在 file:// 下工作。启用 offline 插件后,以下依赖 Fetch API 的功能需要显式关闭,否则在本地打开时相关请求会报错:

这些功能的具体开关方式可分别查阅上文链接的 setup 章节。关闭它们之后,你的离线文档将保留绝大部分核心交互——尤其是站点搜索——同时不会在本地打开时冒出红字报错。

源码视角:离线搜索的两条关键链路

深入源码可以看到,offline 插件与搜索模块的配合构成了完整的离线搜索链路:

索引加载的分流逻辑位于 src/templates/assets/javascripts/bundle.tsfetchSearchIndex 函数:当 location.protocol === "file:" 时,通过 watchScript 动态加载插件生成的 search/search_index.js,并把全局变量 __index 作为索引数据;否则走常规路径,用 Fetch API 请求 search/search_index.json。这正是"移动搜索索引到 JavaScript 文件"这一设计的落点。

搜索 worker 的 iframe 垫片:搜索本身在 Web Worker 中执行以保持 UI 流畅,而 Web Worker 从 file:// 页面创建同样受限。搜索模块的 worker/_/index.ts 注释明确指出:借助一个轻量的、基于 iframe 的 Web Worker 垫片,搜索在 file:// 协议下也能得到支持。插件在 on_config 中向 config.extra["polyfills"] 追加的 https://unpkg.com/iframe-worker/shim(见 plugin.py)正是这个垫片。

此外,worker 内的多语言支持在 iframe 环境中需要修正脚本加载路径:worker/main/index.ts 通过检测 parent 上是否存在 IFrameWorker 来识别垫片环境,并依据首个带 srcscript 元素重新推导 lunr 语言包的基础路径。

至此,离线站点保留的最重要交互——搜索——从索引内联、worker 垫片到链接重写,形成了一条完整且可验证的链路,这也是 offline 插件价值的核心所在。

登录后查看全文
热门项目推荐
相关项目推荐

项目优选

收起
kernelkernel
deepin linux kernel
C
33
18
docsdocs
暂无描述
Markdown
900
5.83 K
ops-transformerops-transformer
本项目是CANN提供的transformer类大模型算子库,实现网络在NPU上加速计算。
C++
1.14 K
2.75 K
pytorchpytorch
作为 Ascend for PyTorch 社区的核心组件,TorchNPU 是昇腾专为 PyTorch 打造的深度学习适配插件,使 PyTorch 框架能够直接调用昇腾 NPU,为开发者提供昇腾 AI 处理器的超强算力。
Python
860
1.35 K
ops-nnops-nn
本项目是CANN提供的神经网络类计算算子库,实现网络在NPU上加速计算。
C++
927
1.85 K
jiuwenswarmjiuwenswarm
JiuwenSwarm 是一款基于openJiuwen开发的智能AI Agent,它能够将大语言模型的强大能力,通过你日常使用的各类通讯应用,直接延伸至你的指尖。
Python
3.84 K
1.02 K
kernelkernel
openEuler内核是openEuler操作系统的核心,既是系统性能与稳定性的基石,也是连接处理器、设备与服务的桥梁。
C
533
603
ops-mathops-math
本项目是CANN提供的数学类基础计算算子库,实现网络在NPU上加速计算。
C++
1.37 K
1.46 K
AscendNPU-IRAscendNPU-IR
AscendNPU-IR是基于MLIR(Multi-Level Intermediate Representation)构建的,面向昇腾亲和算子编译时使用的中间表示,提供昇腾完备表达能力,通过编译优化提升昇腾AI处理器计算效率,支持通过生态框架使能昇腾AI处理器与深度调优
C++
548
397
cann-learning-hubcann-learning-hub
CANN 学习中心仓,支持在线互动运行、边学边练,提供教程、示例与优化方案,一站式助力昇腾开发者快速上手。
Jupyter Notebook
1.04 K
525