keygen标签在现代浏览器中根本不会工作,它已被所有主流浏览器彻底移除(Chrome 69+、Firefox 67+、Edge 79+),自HTML5.2起正式废弃,W3C和WHATWG均不再维护;哪怕语法正确,页面中的<keygen>也会被解析器直接忽略,不渲染、不生成密钥、不提交公钥;其唯一历史作用是辅助客户端证书注册,在表单提交前由浏览器生成RSA密钥对,私钥本地存储、公钥自动提交,但仅支持keytype="rsa"且无法指定密钥长度或算法;替代方案必须使用crypto.subtle.generateKey()手动实现密钥生命周期管理,并通过fetch等主动提交PEM格式公钥。

keygen 标签在现代浏览器中根本不会工作
它已被所有主流浏览器彻底移除(Chrome 69+、Firefox 67+、Edge 79+),keygen 元素自 HTML5.2 起正式废弃,W3C 和 WHATWG 均不再维护。哪怕你写对了语法,页面里放了 <keygen>,也只会渲染为空白或被忽略——不是样式问题,是解析器直接跳过。
为什么曾经用 keygen?它实际做了什么
keygen 的唯一作用是在表单提交前,由浏览器生成一对 RSA 密钥:私钥留在本地(不外传),公钥以 <input type="hidden"> 形式随表单一起提交。典型场景是客户端证书申请(如企业内网 CA 注册),而非通用加密。
- 它依赖浏览器内置的 PKI 模块,和操作系统证书存储深度绑定
- 不支持指定密钥长度以外的参数(如
keytype="rsa"是唯一有效值,ecdsa等从未被任何浏览器实现) -
challenge属性用于防重放,但服务端必须主动验证,否则形同虚设
替代方案不是“换一个标签”,而是换整套流程
现在必须用 JavaScript + Web Crypto API 手动完成密钥生成与签名,再通过 fetch 提交公钥。例如:
async function generateKeyPair() {
const keyPair = await crypto.subtle.generateKey({ name: "RSA_SPKI", hash: "SHA-256" }, true, ["sign", "verify"]);
const publicKey = await crypto.subtle.exportKey("spki", keyPair.publicKey);
const pem = btoa(String.fromCharCode(...new Uint8Array(publicKey)));
// 后续把 pem 发给后端
}
注意:crypto.subtle.generateKey 只能在安全上下文(HTTPS 或 localhost)运行;导出的公钥需 Base64 编码并拼接 PEM 头尾才能被 OpenSSL 或后端正确识别。
将调研报告、方案对比、数据分析、需求梳理、会议纪要、设计说明、代码评审、学习笔记等任务产物输出为可在浏览器直接打开的单文件 HTML,替代 Markdown 作为最终交付物。Markdown 在信息密度、视觉清晰度和可分享性上已跟不上 AI 产物的丰富度,HTML 能同时承载排版、表格、SVG 等。
立即学习“前端免费学习笔记(深入)”;
如果非要跑通旧代码(比如教学演示)
唯一可行方式是降级到已废弃的旧版浏览器(如 Firefox 60 ESR 或 Chrome 67),且必须配合本地 HTTP Server(不能直接双击打开 HTML 文件),因为 keygen 要求页面处于 secure context。
- 不要尝试 polyfill —— 没有 JS 能模拟浏览器原生密钥生成和证书存储逻辑
- 不要指望 Electron 或 WebView2 支持 —— 它们基于新版 Chromium/Edge,同样移除了
keygen - 教学时若展示旧代码,务必同步说明:这行代码在 2019 年后的任意真实环境中都无效
真正卡住人的从来不是怎么写 keygen,而是误以为它还能“运行”。历史技术细节值得了解,但别让它干扰对现代 Web 加密路径的理解。


















