使用方法
这个高强度密码生成器只有一个必填项:长度。下面五步走完,你会同时拿到一条密码和它的强度数字。
- 「密码长度」默认填 24(示例值),允许 8~64 的整数。长度是唯一能持续拉高强度的变量,其余参数都是微调。
- 「字符池」四类默认全勾:小写 26 + 大写 26 + 数字 10 + 符号 32 = 94 个可打印字符(ASCII 33~126,去掉空格)。
- 点「生成并量化」,结果区出现一条 24 位密码;下方四张统计卡同时给出它的熵、取值空间、离线与在线两档破解耗时。
- 取消任何一类字符,统计卡会立刻按新的池重算。想对比「去掉符号会损失多少」,勾选状态改一下就行,不必反复生成。
- 「复制这条密码」只复制密码本身,不含任何标签或说明文字;「复制对照表」把正文里两张表按 Tab 分隔复制走,可以直接粘进 Excel 或评审文档。
这个高强度密码生成器能解决什么问题
一是把「够不够强」从感觉换成数字。很多页面给的是「弱 / 中 / 强」三档色条,实际只统计用了哪几类字符,同一档里 8 位和 32 位看起来一样。本页给出的是可以直接引用的量:H = 长度 × log2(字符池),以及按明确速率假设算出的破解耗时。
二是给安全评审提供可复核的口径。写检查报告时同事会问「你这 157.3 bit 怎么来的」——本页把速率假设(离线 1010 次/秒、在线 104 次/秒)和平均尝试次数(2H−1)都写在页面上,任何人可以拿计算器复现。
三是纠正「必须大小写加符号混合」的旧习惯。NIST SP 800-63B 明确不再建议强制组成规则,因为用户会把「Aa1!」这类固定套路搬到每个站点,反而更容易被掩码攻击命中。本页仍然允许你勾选各类字符,但统计卡会告诉你:把长度从 12 加到 24 得到的增量,远大于补几个符号。
四是估算一次性凭据的有效期。给接口签名、设备配对码这类短期凭据定长度时,可以直接查对照表:若攻击者只能走在线限速通道(每秒 1 万次),12 位全池口令的期望破解时间已经远超这枚凭据的存活时间,再长就是浪费。
本页不做这些事:不保管密码、不评估你已有的口令、不查询泄露库、不把结果写进任何浏览器存储。要评估一条现成密码的强弱,请用页面底部的「密码力量检测」;想知道某个字符串的字符池是怎么反推出来的,用「密码熵值计算器」对照。
量化原理:熵、字符池与拒绝采样
这个高强度密码生成器只用了两个公式。第一个是单字符信息量:若字符池大小为 |A|,均匀随机取一个字符带来的信息量是 log2(|A|) 比特。四类字符全勾时 log2(94) ≈ 6.5546;只勾数字时 log2(10) ≈ 3.3219,差了近一倍。
第二个是整条口令的熵:各字符独立均匀,所以 H = L × log2(|A|),代码里就是一行 L * Math.log2(pool)。这里用的是 Math.log2 而不是 Math.log(x) / Math.log(2)——后者在 IEEE 754 双精度下中间结果会被拆成两次舍入,Math.log2(8) 这类应当整除的值可能得到 2.9999999999999996,而 Math.log2 在 ECMAScript 规范里被要求对 2 的整数次幂返回精确整数。熵与取值空间是同一件事的两种写法:取值空间 = 2H = |A|L。
随机数只取自 crypto.getRandomValues(new Uint32Array(1))。它是 W3C Web Cryptography API 定义的加密随机数接口,由操作系统熵池供数,不是 Math.random() 那种为了速度牺牲不可预测性的 PRNG。取到 32 位无符号整数后不能直接 n % 94——因为 232 = 4294967296 不能被 94 整除,余数 0~41 会比 42~93 多出现一次。工具实际先算接受上限 Math.floor(4294967296 / 94) × 94 = 4294967254,随机数落在 4294967254~4294967295 这 42 个取值上就丢弃重抽;拒绝率约 9.8×10−7%,代价可以忽略,换来的是严格均匀。
破解耗时怎么算。假设攻击者已知字符池与长度、只做穷举,平均要试到空间的一半,即 2H−1 次。本页给两档速率:离线 1010 次/秒对应拿到口令哈希后在本机用多张显卡跑快速哈希或直接猜明文;在线 104 次/秒对应对着登录接口撞库,受网络往返和服务端限速约束。两档差了 100 万倍,所以「在线很安全」和「离线很安全」是两回事。
NIST SP 800-63B 的现代建议。该规范对口令的下限要求是 8 位,并要求验证方允许至少 64 位的口令;它不建议强制「必须含大小写、数字、符号」的组成规则,也不建议强制定期更换;真正被推荐的两条是「足够长」和「与已知泄露口令库比对」。本页把组成规则保留成可选项,是为了兼容那些仍在校验组成的老系统,而不是说组成规则本身能提升强度。
完整示例:默认档 24 位是怎么算成 157.3 bit 的
示例条件与页面打开时的默认值完全一致:长度 24 位、四类字符全勾(池 94)。逐步代入上面的公式:
- 单字符信息量
log2(94) = 6.5546bit; - 整条熵
H = 24 × 6.5546 = 157.3 bit; - 取值空间
9424 ≈ 2.27×1047种,和2157.3是同一个数; - 平均尝试
2156.3 ≈ 1.14×1047次,按离线 1010 次/秒≈ 3.6×1029 年,约是宇宙年龄(1.38×1010 年)的 2.6×1019 倍; - 同一串放到在线限速 104 次/秒,期望耗时升到 3.6×1035 年;
- 长度每再加 1 位,熵固定增加
log2(94) = 6.55bit。
下面这条是默认条件下的固定演示串(写在 HTML 里,不是随机生成的),只用来告诉你输出长什么样。点一次「生成并量化」会得到完全不同的内容:
K7#vQz2@Lm9!Rt4$Wp6*Yd8X
长度、字符池与破解耗时对照表
表一是池固定 94 位、只改长度。每加 1 位,熵严格加 6.55 bit,破解耗时则翻 94 倍——所以这张表的耗时列增长得非常快。
| 密码长度 | 熵 H | 取值空间 94L | 离线 1010/秒 | 在线 104/秒 |
|---|---|---|---|---|
| 8 位 | 52.4 bit | 6.10×1015 | 3.5 天 | 9658 年 |
| 12 位 | 78.7 bit | 4.76×1023 | 75.4 万年 | 7540.5 亿年 |
| 16 位 | 104.9 bit | 3.72×1031 | 5.9×1013 年 | 5.9×1019 年 |
| 20 位 | 131.1 bit | 2.90×1039 | 4.6×1021 年 | 4.6×1027 年 |
| 24 位(默认) | 157.3 bit | 2.27×1047 | 3.6×1029 年 | 3.6×1035 年 |
| 32 位 | 209.7 bit | 1.38×1063 | 2.2×1045 年 | 2.2×1051 年 |
表二反过来:长度固定 12 位,只改勾选的字符类别。它回答的是那个被问烂的问题——「多勾几类到底值不值」。
| 字符池(长度固定 12 位) | 池大小 | 熵 H | 离线 1010/秒 | 在线 104/秒 |
|---|---|---|---|---|
| 只勾数字 | 10 | 39.9 bit | 50.0 秒 | 2 年 |
| 只勾小写 | 26 | 56.4 bit | 55.2 天 | 15.1 万年 |
| 大小写 | 52 | 68.4 bit | 619 年 | 6.2 亿年 |
| 大小写 + 数字 | 62 | 71.5 bit | 5112 年 | 51.1 亿年 |
| 四类全勾(默认池) | 94 | 78.7 bit | 75.4 万年 | 7540.5 亿年 |
两张表对着看:把池从 62 补到 94(多 32 个符号)只多 7.2 bit,折算成长度大约是 1.2 位;而长度从 12 加到 24,多出来的是 78.6 bit。结论很直白——加长度永远比加字符类别划算。
输入范围、边界与精度说明
- 长度 8~64 的整数。下限 8 直接来自 NIST SP 800-63B 的最低要求;上限 64 是因为让验证方接受更长口令并不是普遍现象,很多表单
maxlength就是 64,而 bcrypt 这类算法在 72 字节之后会直接截断——超过上限再长的部分在部分系统里根本不参与比对,写长了只会让人误以为更安全。 - 字符池上限 94。可打印 ASCII 共 95 个(含空格),本页去掉空格:许多表单会对口令做首尾 trim,空格进了池却在提交时被吃掉,实际字符池会缩水,算出来的熵就是在骗自己。
- 每类字符不是强制出现的。本页按纯均匀抽取生成,某一条 24 位口令里恰好没有数字是完全可能的,概率约
(84/94)24 ≈ 6.7%。这符合熵的定义;如果你的目标系统硬性校验组成,请改用同族的「密码生成器」,它会先给每一类各抽一个再补齐。 - 熵是上界,不是保证。公式假设攻击者对你一无所知。真实攻击会先用字典、掩码和规则把空间裁掉一大块:生日、姓名拼音、键盘走位、站点名加年份,这些模式都不在
|A|L里体现。熵高只能说明「纯穷举打不动」,挡不住钓鱼、键盘记录和跨站复用。 - 本页不做泄露库比对。NIST 建议的那一步需要一份真实的已泄露口令数据集,属服务端能力,本页没有也不会上传任何内容去查。
- 结果区首屏那条是固定演示文本,写在 HTML 源码里,和随机数无关。点一次按钮之后显示的才是
crypto.getRandomValues的产物。 - 统计卡里的耗时是期望值,按平均尝试
2H−1次计算。若按最坏情况(试完整空间)算,数字再乘 2;这个差别在 157 bit 这个量级上没有任何实际意义。
记住这些边界之后,这个高强度密码生成器只会给出它有把握给出的结论:长度、字符池、熵和两档耗时。至于这条口令在你的实际环境里安不安全,还要看你把它用在哪里、有没有复用。
常见问题
为什么默认是 24 位,而不是常见的 12 位或 16 位?
因为要留出安全边际与人工输入成本之间的平衡点。16 位全池已经是 104.9 bit,在很多系统里够用;24 位把它推到 157.3 bit,代价只是多按 8 次键盘。只有当目标系统把口令字段卡在 64 位以下、或者必须手输到手机等设备上时,才建议退回 16 位并接受略低的熵。
为什么不再强制「大小写 + 数字 + 符号」混合?
NIST SP 800-63B 不再建议这类组成规则。原因是它会诱发可预测的套路:人们习惯把大写放开头、把数字和符号放结尾,攻击者的掩码字典正好按这个模式命中。组成规则把一个本应均匀的空间压成了少数几个高概率形状,实际收益常常是负的。长度没有这个副作用。
加长度和加字符类别,到底哪个更划算?
加长度。以 12 位为例,池从 62 补到 94(多 32 个符号)只增加 7.2 bit,约等于 1.2 位长度;而长度从 12 加到 13 本身就有 5.95 bit(池 62 时)。更关键的是,长口令对人更友好——换成一句长口令短语,记忆负担可能还更低。
157.3 bit 是不是意味着绝对安全?
不是。它只说明在「攻击者做纯穷举且只知道池和长度」这个模型下打不动。现实中的突破口几乎都在模型之外:你在别的站点复用了同一条口令、口令被钓鱼页面收走、设备被装了键盘记录器、或者口令被写在一张便签上。熵解决的是数学问题,不是全部安全问题。
必须把口令抄到纸上时怎么办?
先把符号去掉、只用大小写加数字(池 62),牺牲 5.95 bit 换抄写准确率;再把长度从 24 提到 32 补回来,净熵反而更高。这就是本页把「勾选类别」做成可选项的意义:强度是可以按场景重新分配的。
工具会把生成的密码发到服务器或存进浏览器吗?
都不会。随机数来自浏览器内置接口,拼接和计算全部在页面里完成,没有任何网络请求,也没有 localStorage、sessionStorage 或 Cookie 写入。想自己验证,打开开发者工具的 Network 面板点几次按钮,看不到任何新请求。
离线 1010 次/秒、在线 104 次/秒这两个数是怎么定的?
它们是两个量级代表值而非实测值:离线档对应拿到哈希后在本机用多张消费级显卡跑快速哈希(或直接针对明文空间猜测)的吞吐;在线档对应通过网络不断尝试登录接口,受往返延迟与服务端限速双重约束。两者相差 100 万倍,所以同一个长度在两个模型下的结论可能完全相反。实际速率取决于哈希算法(bcrypt/Argon2 比 MD5 慢好几个数量级)和对手的预算,本页给的是可以自行替换的量级锚点。
为什么本页不检查密码是否出现在泄露库里?
因为那需要一份真实的已泄露口令数据集,而且要做到「查了不泄露你要查的内容」,必须走 k-匿名之类的前缀查询协议,属于服务端能力。本页是纯本地工具,没有任何后端,所以不做这件事。NIST 建议验证方在设置口令时做这一步——那应当由你注册的站点来做,而不是由一个本地生成器代劳。
相关工具
- 口令短语生成器:用若干个常见单词拼成长口令,熵不低而记忆负担更小,适合需要长期背诵的账号。
- 随机字符串生成器:生成不带强度含义的随机串,用于接口 token、签名盐值、临时文件名。
- UUID生成器:生成全局唯一标识符,注意 UUID v4 只有 122 bit 随机位,不要当口令用。
- PIN码代码生成器:生成纯数字短码,本页对照表里「只勾数字」那一行就是它的强度上限。
- 虚拟密码生成器:为测试数据和演示环境造一批占位口令,不带真实安全语义。
- 密码力量检测:评估一条已有口令,会一并考虑常见词、重复模式和键盘走位,正好补上本页纯穷举模型的盲区。
- 密码熵值计算器:从一条给定字符串反推字符池与信息量,可用来核对本页算出的 157.3 bit。
- 生成器:查看全部生成器工具。