pattern 只在表单提交或手动调用 checkvalidity()/reportvalidity() 时触发校验,不监听实时事件;title 属性决定错误提示文案,缺失则提示不可读;正则需避免首尾斜杠、正确处理字符类与转义,实时反馈必须依赖 js 补位。

pattern 什么时候才真正开始校验?
它只在表单提交或手动调用 checkValidity() / reportValidity() 时触发,不会监听 input、blur 或任何实时事件。用户输错内容后,输入框不会变红、不弹提示、也不阻止非法字符输入——直到点提交按钮或按 Enter 键。
常见静默失效场景:
- 没加
required:空字符串默认通过所有pattern,哪怕正则写成.+也拦不住空值 - type 不是文本类:用
type="number"或type="date"时,pattern完全被浏览器忽略 - 没调用验证方法:不点提交、也不手动执行
form.reportValidity(),就永远没反馈
为什么写了 pattern 却没提示?title 是刚需不是可选
title 属性决定错误文案是否可读。没写 title,Chrome 显示“请与所要求的格式匹配”,Safari 可能根本不显示气泡,用户完全不知道哪里错了。
实操建议:
- 文案要具体,比如
title="请输入11位手机号,不要加空格或括号",别写“格式错误” - 移动端 Safari 对
title支持弱,iOS 用户可能看不到提示,必须用 JS 补充setCustomValidity()气泡 - 错误提示文案来自
input.validationMessage,调试时可在控制台执行document.querySelector("input").checkValidity()查看实际内容
pattern 正则怎么写才不被浏览器静默忽略?
浏览器把 pattern 当作裸字符串解析,内部自动加 ^ 和 $ 做全串匹配。写错一个符号就失效,且毫无报错提示。
关键避坑点:
- 绝对不要加首尾斜杠:
pattern="/[0-9]{6}/"→ 浏览器真去匹配字面的/,必然失败 - 字符类
[]中短横-必须放开头或结尾:[a-z_-]✅,[a-z-_]❌(会被当成非法 Unicode 范围) - 中文用
[u4e00-u9fa5],不是\u4e00-\u9fa5(单u会被 HTML 解析器吞掉) - 点号
.在属性中需双写反斜杠 → 实际写成\.;.*开头或结尾会失去约束力,慎用
想实时标红或动态反馈?pattern 自身做不到
pattern 天然不支持实时反馈。所谓“输错立刻标红”,必须靠 JS 补位:
- 监听
input事件,每次输入后调用input.checkValidity()判断状态 - 匹配失败时用
input.setCustomValidity("自定义提示"),成功时清空:input.setCustomValidity("") - 状态残留很常见:用户改完内容再提交仍报旧错,因为
input.validity.valid不自动刷新,必须手动清理 - 复杂逻辑如密码强度(大小写+数字+特殊字符),
pattern依赖的环视(?=.*[a-z])在旧版 Safari 中静默失效,必须用 JS 分项验证
最易被忽略的是:pattern 的校验结果不会自动同步到 CSS 伪类 :valid/:invalid 的视觉更新——你得在 JS 中手动触发重绘,或者靠 class 切换控制样式。











