浏览器在HTML5输入类型为url时使用什么正则表达式?

6
我正在开发一个HTML5输入模式polyfill,尝试在JavaScript中像浏览器(Chrome)一样精确地验证input type=url。但是我找不到任何关于JavaScript或PERL兼容的正则表达式的文档。作为polyfill,如果它能够精确匹配所有URL(这是不可能的),那么我并不特别介意,而是希望它模仿浏览器的工作方式。
有没有人知道PERL语法中相同的模式?
谢谢

1
它可能取决于浏览器。 - SLaks
可能吧。关于输入类型为URL以及什么样的URL算作有效的规范,确实有些难以理解。我在原问题中提到了Chrome浏览器,所以有人对这个特定浏览器有什么想法吗? - Benjamin Solum
那个浏览器不是(部分?)基于开源的吗? - Maarten Bodewes
是的,说实话我还没有仔细查看源代码以确定,但Chrome是用C++、汇编、Python和JavaScript编写的,所以即使我知道要查找什么,也不能保证在PERL语法中找到它。如果我在其他地方找不到它,那么我可能不得不深入Chrome的源代码。 - Benjamin Solum
2个回答

6
在GitHub上搜索了几个HTML5 shivs,看看是否有其他人遇到过理想的表达式,我相信我找到了一个非常接近的东西,但它并不完全匹配。
Alexander Farkas (https://github.com/aFarkas/webshim/blob/master/src/shims/form-shim-extend.js#L285) 使用这种模式来测试URL:
/^([a-z]([a-z]|\d|\+|-|\.)*):(\/\/(((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:)*@)?((\[(|(v[\da-f]{1,}\.(([a-z]|\d|-|\.|_|~)|[!\$&'\(\)\*\+,;=]|:)+))\])|((\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5])\.(\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5])\.(\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5])\.(\d|[1-9]\d|1\d\d|2[0-4]\d|25[0-5]))|(([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=])*)(:\d*)?)(\/(([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)*)*|(\/((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)+(\/(([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)*)*)?)|((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)+(\/(([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)*)*)|((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)){0})(\?((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)|[\uE000-\uF8FF]|\/|\?)*)?(\#((([a-z]|\d|-|\.|_|~|[\u00A0-\uD7FF\uF900-\uFDCF\uFDF0-\uFFEF])|(%[\da-f]{2})|[!\$&'\(\)\*\+,;=]|:|@)|\/|\?)*)?$/i;

此外,如果有人通过Google偶然发现这篇文章,如果您不需要模式,只是想通过JavaScript检查某些内容是否有效(例如onChange),则可以使用formelement.checkValidity()方法。显然,这对于填充程序没有帮助(它假设没有本地HTML5验证支持),但仍然很有用。

4
请阅读关于规范的说明:http://www.w3.org/TR/html5/forms.html#url-state-(type=url)
您的polyfill应该从清理输入开始,即删除换行符并修剪字符串。句子“用户代理程序不得允许用户插入“LF”(U+000A)或“CR”(U+000D)字符”也可能很有趣。
结果应该是一个有效的绝对的 URL。所引用的RFC 39863987将描述URL验证,关于解析URLs的部分也可能很有趣。
您的polyfill不仅可以验证URI,还可以解析相对URI。至少,使用算法验证URI将比查找适当的regexp简单得多。然而,甚至RFC在附录B中提到了用于解析已验证的URI的regexp。

谢谢你的帮助和建议。这绝对是一个很好的起点。我曾经浏览过规范,但一直想着是否已经有人走过这条路了,如果是的话,我就使用现成的东西。看来我得稍微动手一下了。再次感谢你的建议! - Benjamin Solum
嘿@bergi!看起来这个答案中的W3C链接已经不可用了。你能否更新一下?谢谢! - Slava Fomin II

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接