我有一个输入字段,可以输入常规文本和sprintf标记.
例: some text here. %1$s done %2$d times
我如何验证sprintf部件,以便它们不可能出错%$1s
?文本是utf-8,据我所知,正则表达式只匹配latin-1字符.
www.regular-expressions.info没有列出/u
任何地方,我认为这用于告诉字符串是unicode.
是搜索整个输入字段字符串的最佳方法,%
或者$
如果找到,则应用正则表达式来验证sprintf部分?
我认为正则表达式将是: /%\d\$(s|d|u|f)/u
我最初使用Gumbo的正则表达式来解析sprintf指令,但在尝试解析像%1.2f这样的东西时我立即遇到了问题.我最终回到PHP的sprintf手册并根据其规则编写了正则表达式.到目前为止,我不是一个正则表达式专家,所以我不确定这是否是最干净的写作方式:
/%(?:\d+\$)?[+-]?(?:[ 0]|'.{1})?-?\d*(?:\.\d+)?[bcdeEufFgGosxX]/
Run Code Online (Sandbox Code Playgroud)
这就是我最终得到的结果,并且它正在发挥作用。
// Always use server validation even if you have JS validation
if (!isset($_POST['input']) || empty($_POST['input'])) {
// Do stuff
} else {
$matches = explode(' ',$_POST['input']);
$validInput = true;
foreach ($matches as $m) {
// Check if a slice contains %$[number] as it indicates a sprintf format
if (preg_match('/[%\d\$]+/',$m) > 0) {
// Match found. Now check if its a valid sprintf format
if ($validInput === false || preg_match('/^%(?:\d+\$)?[dfsu]$/u',$m)===0) { // no match found
$validInput = false;
break; // Invalid sprintf format found. Abort
}
}
}
if ($validInput === false) {
// Do stuff when input is NOT valid
}
}
Run Code Online (Sandbox Code Playgroud)
感谢 Gumbo 提供的正则表达式模式,它可以匹配有订单标记和没有订单标记的情况。
编辑:我意识到搜索 % 是错误的,因为如果忘记/省略,则不会检查任何内容。以上是新代码。
“$validInput === false ||” 可以在最后一个 if 语句中省略,但为了完整性我将其包含在内。