如何测试字符串是否为URL编码?
以下哪种方法更好?
function is_urlEncoded($string){
$test_string = $string;
while(urldecode($test_string) != $test_string){
$test_string = urldecode($test_string);
}
return (urlencode($test_string) == $string)?True:False;
}
$t = "Hello World > how are you?";
if(is_urlEncoded($sreq)){
print "Was Encoded.\n";
}else{
print "Not Encoded.\n";
print "Should be ".urlencode($sreq)."\n";
}
上面的代码可以正常工作,但不是在字符串经过双重编码的情况下,如下例所示:
$t = "Hello%2BWorld%2B%253E%2Bhow%2Bare%2Byou%253F";
$t = "Hello+World%2B%253E%2Bhow%2Bare%2Byou%253F";
答案 0 :(得分:33)
你可以这样做以防止双重编码。 每次首先解码然后再次编码;
$string = urldecode($string);
然后再做一次
$string = urlencode($string);
以这种方式执行我们可以避免双重编码:)
答案 1 :(得分:11)
这是我刚刚放在一起的东西。
if ( urlencode(urldecode($data)) === $data){
echo 'string urlencoded';
} else {
echo 'string is NOT urlencoded';
}
答案 2 :(得分:10)
你永远不会确定字符串是否是URL编码的,或者它是否应该包含序列%2B
。相反,它可能取决于字符串的来源,即它是手工制作还是来自某些应用程序。
在字符串中搜索要编码的字符是否更好,哪些字符不存在,如果存在则不编码。
我认为这是一种更好的方法,因为它会处理以编程方式完成的事情(假设应用程序不会留下非编码字符)。
这里有一点令人困惑......从技术上讲,%
“应该被编码,如果它将出现在最终值中,因为它是一个特殊字符。您可能必须结合使用方法来查找应该编码的字符,以及验证字符串是否成功解码(如果没有找到)。
答案 3 :(得分:5)
我认为没有万无一失的方法可以做到这一点。例如,请考虑以下事项:
$t = "A+B";
这是一个URL编码为“A B”还是需要编码为“A%2BB”?
答案 4 :(得分:3)
$is_encoded = preg_match('~%[0-9A-F]{2}~i', $string);
答案 5 :(得分:3)
没有可靠的方法来做到这一点,因为有些字符串在编码过程中保持不变,即是否为“abc”编码?没有明确的答案。另外,正如您所遇到的,一些角色有多种编码......但是......
您的decode-check-encode-check方案失败,因为某些字符可能以多种方式编码。但是,稍微修改一下你的函数应该是相当可靠的,只需检查解码是否修改了字符串,如果是,则进行编码。
当然,它不是万无一失的,因为“10 + 20 = 30”将返回true(+转换为空格),但我们实际上只是在做算术。我想这是你计划试图反击的,我很遗憾地说我认为没有一个完美的解决方案。
HTH。
修改:
正如我在自己的评论中提到的那样(这里只是为了清楚起见),一个很好的折衷方案可能是检查你网址中的无效字符(例如空格),如果有一些字符没有编码。如果没有,请尝试解码并查看字符串是否更改。这仍然不能处理上面的算术(这是不可能的),但希望它足够了。
答案 6 :(得分:2)
怎么样:
if (urldecode(trim($url)) == trim($url)) { $url_form = 'decoded'; }
else { $url_form = 'encoded'; }
无法使用双重编码,但我认为这超出了范围?
答案 7 :(得分:2)
@ user187291代码可以工作,只有在+未编码时才会失败。
我知道这是很老的帖子。但这对我有用。
$is_encoded = preg_match('~%[0-9A-F]{2}~i', $string);
if($is_encoded) {
$string = urlencode(urldecode(str_replace(['+','='], ['%2B','%3D'], $string)));
} else {
$string = urlencode($string);
}
答案 8 :(得分:1)
发送一个变量,当你从网址获取数据时标记解码。
?path=folder/new%20file.txt&decode=1
答案 9 :(得分:0)
我正在使用以下测试来查看字符串是否已经过urlencoded:
if(urlencode($str) != str_replace(['%','+'], ['%25','%2B'], $str))
如果字符串已经被urlencoded,那么将通过双重编码改变的唯一字符是%(它启动所有编码的字符串)和+(替换空格。)更改它们,你应该有原始字符串。< / p>
请告诉我这是否适合您。
答案 10 :(得分:0)
我找到了。
网址为例如:https://example.com/xD?foo=bar&uri=https%3A%2F%2Fexample.com%2FxD
您需要找到$ _GET ['uri']是否已编码:
preg_match("/.*uri=(.*)&?.*/", $_SERVER['REQUEST_URI'], $r);
if (isset($_GET['uri']) && urldecode($r['1']) === $r['1']) {
// Code Here if url is not encoded
}
答案 11 :(得分:0)
在我的情况下,我想检查是否对完整的URL进行了编码,因此我已经知道URL必须包含字符串https://
,而我所做的就是检查字符串是否具有{ {1}}(https://
)中,如果没有,我就知道它没有被编码:
https%3A%2F%2F
理论上,只要您知道部分字符串(在此示例中为//make sure $completeUrl is encoded
if (strpos($completeUrl, urlencode('https://')) === false) {
// not encoded, need to encode it
$completeUrl = urlencode($completeUrl);
}
)将始终存在于您要检查的内容中,则该解决方案可以与除完整URL之外的任何其他字符串一起使用。
答案 12 :(得分:-1)
private static boolean isEncodedText(String val,String ... encoding)throws UnsupportedEncodingException { String decodingText = URLDecoder.decode(val,TransformFetchConstants.DEFAULT_CHARSET);
if(encoding != null && encoding.length > 0){
decodedText = URLDecoder.decode(val, encoding[0]);
}
String encodedText = URLEncoder.encode(decodedText);
return encodedText.equalsIgnoreCase(val) || !decodedText.equalsIgnoreCase(val);
}