Недавно я столкнулся со странной проблемой с urlencode: у меня был знак "+" в частях URL-адреса как pathinfo, так и querystring.
Например:
http://example.com/A + B?s=C + D
Я использую tamperdata в firefox и могу убедиться, что firefox закодировал URL-адрес следующим образом:
http://example.com/A%20+%20B?s=C%20+%20D
На стороне сервера у меня включена перезапись URL-адреса apache с помощью следующей инструкции:
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_URI} !=/favicon.ico
RewriteRule ^(.*)$ index.php?q=$1 [L,QSA]
Затем на php я получил следующее:
$_REQUEST['q'] = 'A B';
$_REQUEST['s'] = 'C D';
$_SERVER['QUERY_STRING'] = 'q=A + B&s=C%20+%20D';
Как мы знаем, php автоматически использует urldecode для преобразования строки запроса в суперпеременную $ _REQUEST, что объясняет, почему 'A + B' превратилось в 'AB', а 'C + D' превратилось в 'C D'. Затем я использую этот apache Перезапись URL-адреса должна декодировать все символы, чтобы выполнить преобразование перезаписи. ФЛАГ B поможет повторно преобразовать их после сопоставления. Таким образом, правила перезаписи стали соблюдаться с применением B FLAG.
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_URI} !=/favicon.ico
RewriteRule ^(.*)$ index.php?q=$1 [B,L,QSA]
Затем результат стал:
$_REQUEST['q'] = 'A + B';
$_REQUEST['s'] = 'C D';
$_SERVER['QUERY_STRING'] = 'q=A+%2B+B&s=C%20+%20D';
Я ожидал следующего:
$_SERVER['QUERY_STRING'] = 'q=A%20+%20B&s=C%20+%20D';
Затем я мог бы использовать rawurldecode, чтобы вручную проанализировать строку запроса следующим образом, также как изначально firefox
$_REQUEST['q'] = 'A + B';
$_REQUEST['s'] = 'C + D';
Но вместо этого apache mod-rewrite B glag make q превратился в 'A +% 2B + B', что отличается от исходной кодировки Firefox 'A% 20 +% 20B'. Конечно, кодировка apache совместима с функцией urlencode php.
Возникает вопрос, почему firefox и apache ведут себя так по-разному? Почему firefox не кодирует «A + B» в «A +% 2B + B» как обычное использование, а «A% 20 +% 20», что приводит к тому, что многие из них несовместимы с PHP. а на стороне сервера?