直接用 parseInt 校验身份证会出错,因其会去除前导零并因精度丢失导致18位数字误转,正确做法是全程字符串处理、用正则和校验码算法(GB 11643-1999)校验。

为什么直接用 parseInt 校验身份证会出错
身份证号码是 18 位字符串,开头可能是 0(如某些地区户籍号),用 parseInt 会自动去掉前导零,变成数值后还可能因精度丢失(JavaScript 安全整数上限是 Number.MAX_SAFE_INTEGER === 9007199254740991),18 位数字远超该范围,导致校验结果不可靠。
- 错误示例:
parseInt("11010119900307251X")→110101199003072510(末尾 X 被截断,数字也被误转) - 正确做法:全程按字符串处理,只用正则和字符索引做逻辑判断
- 特别注意:最后一位可能是
"X"或"x",需统一转大写再比对
Node 环境下校验身份证的最小可行函数
不依赖第三方库,仅用内置 API,适配 Node.js 14+ 和 VSCode 内置终端调试场景。核心是校验长度、数字格式、校验码算法(GB 11643-1999)。
function isValidID(id) {
if (typeof id !== 'string' || !/^\d{17}[\dXx]$/.test(id)) return false;
const wi = [7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10, 5, 8, 4, 2];
const vi = ['1', '0', 'X', '9', '8', '7', '6', '5', '4', '3', '2'];
let sum = 0;
for (let i = 0; i < 17; i++) {
sum += Number(id[i]) * wi[i];
}
return vi[sum % 11] === id[17].toUpperCase();
}- VSCode 中可直接粘贴到
.js文件里,在调试控制台或node终端中调用测试 - 输入
"11010119900307251X"返回true;"110101199003072512"返回false - 不校验出生日期合法性(如 2099 年),如需增强,可额外用
new Date()验证年月日是否有效
在 VSCode 里快速验证的实操路径
不是写完就扔,而是让校验能即时反馈——适合开发中边写边测。
使用一条命令部署ProbeChain Rydberg测试网代理节点。自动注册为Agent(NodeType=1),免gas,支持macOS/Linux/Windows。触发词:/r
- 新建临时文件
id-test.js,写入上述isValidID函数 + 测试用例 - 右键 → “在集成终端中运行”,或按
Ctrl+Shift+P→ 输入 “Run Task” → 选 “Node.js: Run Current File” - 若提示
Cannot find module 'xxx',说明没激活 Node 环境:检查 VSCode 底部状态栏是否显示 Node 版本,没显示则需安装 Node 并重启 VSCode - 调试时可在函数内加
console.log(id, sum % 11, vi[sum % 11])查中间值,避免黑盒失败
敏感字段校验容易被忽略的边界点
身份证只是典型,但这类校验一旦上线就涉及合规风险,几个硬性细节必须卡死:
- 前端校验纯属体验优化,
isValidID必须在 Node 后端重复执行,不能信任任何客户端输入 - 日志记录时严禁打印完整身份证号,建议脱敏为
id.replace(/^(.{6})(.*)(.{4})$/, "$1****$3") - 如果项目用 TypeScript,给参数加类型
id: string,避免传入null或undefined导致id[0]报TypeError - 正则
/^\d{17}[\dXx]$/不匹配空格或换行,粘贴文本时记得先trim()
真正麻烦的从来不是算法本身,而是校验逻辑散落在表单、API 层、数据库触发器多个地方,最终漏掉一处就等于没校验。

















