如何在命令行上编码和解码百分比编码的字符串?

如何在命令行上编码和解码百分比编码 (URL编码)字符串?

我正在寻找可以做到这一点的解决方案:

$ percent-encode "ændrük" %C3%A6ndr%C3%BCk $ percent-decode "%C3%A6ndr%C3%BCk" ændrük 

这些命令可以满足你的需求:

 python -c "import urllib, sys; print urllib.quote(sys.argv[1])" æ python -c "import urllib, sys; print urllib.unquote(sys.argv[1])" %C3%A6 

如果要将空格编码为+ ,请将urllib.quote替换为urllib.quote_plus

我猜你会想要别名 😉

贝壳

请尝试以下命令行:

 $ echo "%C3%A6ndr%C3%BCk" | sed 's@+@ @g;s@%@\\x@g' | xargs -0 printf "%b" ændrük 

您可以将其定义为别名并将其添加到shell rc文件中:

 $ alias urldecode='sed "s@+@ @g;s@%@\\\\x@g" | xargs -0 printf "%b"' 

然后每当你需要它时,只需要:

 $ echo "http%3A%2F%2Fwww" | urldecode http://www 

庆典

编写脚本时,可以使用以下语法:

 input="http%3A%2F%2Fwww" decoded=$(printf '%b' "${input//%/\\x}") 

但是上面的语法不能正确处理加号( + ),所以你要通过sed用空格替换它们。

您还可以使用以下urlencode()urldecode()函数:

 urlencode() { # urlencode  local length="${#1}" for (( i = 0; i < length; i++ )); do local c="${1:i:1}" case $c in [a-zA-Z0-9.~_-]) printf "$c" ;; *) printf '%%%02X' "'$c" esac done } urldecode() { # urldecode  local url_encoded="${1//+/ }" printf '%b' "${url_encoded//%/\\x}" } 

请注意,您的urldecode()假定数据不包含反斜杠。


bash + xxd

使用xxd工具进行Bashfunction:

 urlencode() { local length="${#1}" for (( i = 0; i < length; i++ )); do local c="${1:i:1}" case $c in [a-zA-Z0-9.~_-]) printf "$c" ;; *) printf "$c" | xxd -p -c1 | while read x;do printf "%%%s" "$x";done esac done } 

在cdown的gist文件中找到,也在stackoverflow中找到 。


python

尝试定义以下别名:

 alias urldecode='python -c "import sys, urllib as ul; print ul.unquote_plus(sys.argv[1])"' alias urlencode='python -c "import sys, urllib as ul; print ul.quote_plus(sys.argv[1])"' 

用法:

 $ urlencode "ændrük" C%26ndrC%3Ck $ urldecode "%C3%A6ndr%C3%BCk" ændrük 

资料来源: ruslanspivak


PHP

使用PHP,您可以尝试以下命令:

 $ echo oil+and+gas | php -r 'echo urldecode(fgets(STDIN));' // Or: php://stdin oil and gas 

要不就:

 php -r 'echo urldecode("oil+and+gas");' 

使用-R进行多行输入。


Perl的

在Perl中,您可以使用URI::Escape

 decoded_url=$(perl -MURI::Escape -e 'print uri_unescape($ARGV[0])' "$encoded_url") 

或者处理文件:

 perl -i -MURI::Escape -e 'print uri_unescape($ARGV[0])' file 

SED

使用sed可以通过以下方式实现:

 cat file | sed -e's/%\([0-9A-F][0-9A-F]\)/\\\\\x\1/g' | xargs echo -e 

AWK

尝试anon解决方案:

 awk -niord '{printf RT?$0chr("0x"substr(RT,2)):$0}' RS=%.. 

请参阅: 使用awk printf来urldecode文本 。


解码文件名

如果需要从文件名中删除url编码,请使用deurlname工具(例如deurlname *.* )。

也可以看看:

  • 批量下载时可以解码uri文件名吗?
  • 如何从文件名中删除URI编码?

有关:

  • 如何在shell中解码URL编码的字符串? 在SO
  • 解码 unix SE上的URL编码(编码百分比)

百分比编码保留的URI字符和非ASCII字符

 jq -s -R -r @uri 

-s (– --slurp )将输入行读入数组, -s -R (– --slurp --raw-input )将输入读入单个字符串。 -r (– --raw-output )输出字符串的内容而不是JSON字符串文字。

对所有字符进行百分比编码

 xxd -p|tr -d \\n|sed 's/../%&/g' 

tr -d \\n删除每60个字符后由xxd -p添加的换行符。

对Bash中除ASCII字母数字字符外的所有字符进行百分比编码

 eu () { local LC_ALL=C c while IFS= read -r -n1 -d '' c do if [[ $c = [[:alnum:]] ]] then printf %s "$c" else printf %%%02x "'$c" fi done } 

如果没有-d ''这将跳过换行符和空字节。 没有IFS=这会用IFS替换IFS字符。 如果没有LC_ALL=C这将例如用UTF-8语言环境中的%3042替换

仅用于解码的纯bash解决方案:

 $ a='%C3%A6ndr%C3%BCk' $ echo -e "${a//%/\\x}" ændrük 

我不能在这个post中评论最佳答案 ,所以这是我的。

就个人而言,我使用这些别名进行URL编码和解码:

 alias urlencode='python -c "import urllib, sys; print urllib.quote( sys.argv[1] if len(sys.argv) > 1 else sys.stdin.read()[0:-1])"' alias urldecode='python -c "import urllib, sys; print urllib.unquote(sys.argv[1] if len(sys.argv) > 1 else sys.stdin.read()[0:-1])"' 

这两个命令都允许您转换数据,作为命令行参数传递或从标准输入读取它,因为两个单行检查是否存在命令行参数(甚至是空参数)并处理它们或者只读取标准输入。

更新2015-07-16(空第1个arg)

……根据@muru评论。

更新2017-05-28(斜线编码)

如果你还需要对斜杠进行编码,只需在quote函数中添加一个空的第二个参数,那么斜杠也将被编码。

所以,最后在bash中的 urlencode 别名如下所示:

 alias urlencode='python -c "import urllib, sys; print urllib.quote(sys.argv[1] if len(sys.argv) > 1 else sys.stdin.read()[0:-1], \"\")"' 

 $ urlencode "Проба пера/Pen test" %D0%9F%D1%80%D0%BE%D0%B1%D0%B0%20%D0%BF%D0%B5%D1%80%D0%B0%2FPen%20test $ echo "Проба пера/Pen test" | urlencode %D0%9F%D1%80%D0%BE%D0%B1%D0%B0%20%D0%BF%D0%B5%D1%80%D0%B0%2FPen%20test $ urldecode %D0%9F%D1%80%D0%BE%D0%B1%D0%B0%20%D0%BF%D0%B5%D1%80%D0%B0%2FPen%20test Проба пера/Pen test $ echo "%D0%9F%D1%80%D0%BE%D0%B1%D0%B0%20%D0%BF%D0%B5%D1%80%D0%B0%2FPen%20test" | urldecode Проба пера/Pen test $ urlencode "Проба пера/Pen test" | urldecode Проба пера/Pen test $ echo "Проба пера/Pen test" | urlencode | urldecode Проба пера/Pen test 

我找到了一个包renameutils ,它包含实用程序deurlname ,它能够重命名包含“percent-encoded”字符的文件。

不幸的是,它不解码stdin或命令行选项,而只重命名文件,因此你必须创建一个虚拟文件来获取解码(重命名文件的名称),但是使用一些bash脚本可以自动化该过程。

没有关于编码部分的信息,即使因为编码哪些字符可能有问题。 只有非ASCII?

我认为应该有一些更好的工具/方法。

这是一个用于编码的POSIX Awk函数:

 function encodeURIComponent(str, j, q) { while (y++ < 125) z[sprintf("%c", y)] = y while (y = substr(str, ++j, 1)) q = y ~ /[[:alnum:]_.!~*\47()-]/ ? qy : q sprintf("%%%02X", z[y]) return q }