对要发送到web服务器的查询字符串进行编码时-何时使用escape(),何时使用encodeURI()或encodeURIComponent():

使用转义符:

escape("% +&=");

OR

使用encodeURI()/encodeURIComponent()

encodeURI("http://www.google.com?var1=value1&var2=value2");

encodeURIComponent("var1=value1&var2=value2");

当前回答

@johann echavarria答案的现代改写:

控制台日志(阵列(256).fill().map((忽略,i)=>String.fromCharCode(i)).过滤器((字符)=>encodeURI(char)!==encodeURIComponent(字符)? {字符:char,encodeURI:encodeURI(char),encodeURIComponent:encodeURIComponent(char)}:错误))

或者,如果可以使用表,请将console.log替换为console.table(以获得更漂亮的输出)。

其他回答

我建议不要按原样使用这些方法中的一种。编写自己的函数来做正确的事情。

MDN给出了一个很好的url编码示例,如下所示。

var fileName = 'my file(2).txt';
var header = "Content-Disposition: attachment; filename*=UTF-8''" + encodeRFC5987ValueChars(fileName);

console.log(header); 
// logs "Content-Disposition: attachment; filename*=UTF-8''my%20file%282%29.txt"


function encodeRFC5987ValueChars (str) {
    return encodeURIComponent(str).
        // Note that although RFC3986 reserves "!", RFC5987 does not,
        // so we do not need to escape it
        replace(/['()]/g, escape). // i.e., %27 %28 %29
        replace(/\*/g, '%2A').
            // The following are not required for percent-encoding per RFC5987, 
            //  so we can allow for a little better readability over the wire: |`^
            replace(/%(?:7C|60|5E)/g, unescape);
}

https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/encodeURIComponent

我觉得这篇文章很有启发性:Javascript疯狂:查询字符串解析

当我试图解释为什么decodeURIComponent不能正确解码“+”时,我发现了这一点。以下是摘录:

String:                         "A + B"
Expected Query String Encoding: "A+%2B+B"
escape("A + B") =               "A%20+%20B"     Wrong!
encodeURI("A + B") =            "A%20+%20B"     Wrong!
encodeURIComponent("A + B") =   "A%20%2B%20B"   Acceptable, but strange

Encoded String:                 "A+%2B+B"
Expected Decoding:              "A + B"
unescape("A+%2B+B") =           "A+++B"       Wrong!
decodeURI("A+%2B+B") =          "A+++B"       Wrong!
decodeURIComponent("A+%2B+B") = "A+++B"       Wrong!

公认的答案是好的。延伸到最后一部分:

请注意,encodeURIComponent不转义“”字符。一个普通的错误是使用它来创建html属性,例如href='MyUrl'可能会出现注射错误。如果您是从字符串,对于属性引号使用“代替”,或添加额外的编码层('可以编码为%27)。

如果您希望安全起见,也应该对百分比编码的未保留字符进行编码。

您可以使用此方法来转义它们(源代码Mozilla)

function fixedEncodeURIComponent(str) {
  return encodeURIComponent(str).replace(/[!'()*]/g, function(c) {
    return '%' + c.charCodeAt(0).toString(16);
  });
}

// fixedEncodeURIComponent("'") --> "%27"

Java与JavaScript与PHP的小比较表。

1. Java URLEncoder.encode (using UTF8 charset)
2. JavaScript encodeURIComponent
3. JavaScript escape
4. PHP urlencode
5. PHP rawurlencode

char   JAVA JavaScript --PHP---
[ ]     +    %20  %20  +    %20
[!]     %21  !    %21  %21  %21
[*]     *    *    *    %2A  %2A
[']     %27  '    %27  %27  %27 
[(]     %28  (    %28  %28  %28
[)]     %29  )    %29  %29  %29
[;]     %3B  %3B  %3B  %3B  %3B
[:]     %3A  %3A  %3A  %3A  %3A
[@]     %40  %40  @    %40  %40
[&]     %26  %26  %26  %26  %26
[=]     %3D  %3D  %3D  %3D  %3D
[+]     %2B  %2B  +    %2B  %2B
[$]     %24  %24  %24  %24  %24
[,]     %2C  %2C  %2C  %2C  %2C
[/]     %2F  %2F  /    %2F  %2F
[?]     %3F  %3F  %3F  %3F  %3F
[#]     %23  %23  %23  %23  %23
[[]     %5B  %5B  %5B  %5B  %5B
[]]     %5D  %5D  %5D  %5D  %5D
----------------------------------------
[~]     %7E  ~    %7E  %7E  ~
[-]     -    -    -    -    -
[_]     _    _    _    _    _
[%]     %25  %25  %25  %25  %25
[\]     %5C  %5C  %5C  %5C  %5C
----------------------------------------
char  -JAVA-  --JavaScript--  -----PHP------
[ä]   %C3%A4  %C3%A4  %E4     %C3%A4  %C3%A4
[ф]   %D1%84  %D1%84  %u0444  %D1%84  %D1%84

@johann echavarria答案的现代改写:

控制台日志(阵列(256).fill().map((忽略,i)=>String.fromCharCode(i)).过滤器((字符)=>encodeURI(char)!==encodeURIComponent(字符)? {字符:char,encodeURI:encodeURI(char),encodeURIComponent:encodeURIComponent(char)}:错误))

或者,如果可以使用表,请将console.log替换为console.table(以获得更漂亮的输出)。