web-dev-qa-db-fra.com

Décodage de l'encodage d'URL (encodage en pourcentage)

Je veux décoder l'encodage URL, existe-t-il un outil intégré pour ce faire ou quelqu'un pourrait-il me fournir un code sed qui le fera?

J'ai cherché un peu à travers nix.stackexchange.com et sur Internet mais je n'ai trouvé aucun outil en ligne de commande pour décoder l'encodage des URL.

Ce que je veux faire, c'est simplement mettre en place un fichier txt pour que:

  • %21 devient !
  • %23 devient #
  • %24 devient $
  • %26 devient &
  • %27 devient '
  • %28 devient (
  • %29 devient )

Etc.

106
DisplayName

Trouvé ces Python un liners qui font ce que vous voulez:

Python2

$ 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])"'

Python3

$ alias urldecode='python3 -c "import sys, urllib.parse as ul; \
    print(ul.unquote_plus(sys.argv[1]))"'

$ alias urlencode='python3 -c "import sys, urllib.parse as ul; \
    print (ul.quote_plus(sys.argv[1]))"'

Exemple

$ urldecode 'q+werty%3D%2F%3B'
q werty=/;

$ urlencode 'q werty=/;'
q+werty%3D%2F%3B

Références

120
slm

sed

Essayez la ligne de commande suivante:

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

ou l'alternative suivante en utilisant echo -e:

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

Remarque: La syntaxe ci-dessus peut ne pas convertir + En espaces et peut manger tous les retours à la ligne.


Vous pouvez le définir comme alias et l'ajouter à vos fichiers Shell rc :

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

Ensuite, chaque fois que vous en avez besoin, optez simplement pour:

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

Bash

Lors de l'écriture de scripts, vous pouvez utiliser la syntaxe suivante:

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

Cependant, la syntaxe ci-dessus ne traitera pas correctement les plus (+), Vous devez donc les remplacer par des espaces via sed ou comme suggéré par @ isaac , utilisez le syntaxe suivante:

decoded=$(input=${input//+/ }; printf "${input//%/\\x}")

Vous pouvez également utiliser les fonctions urlencode() et urldecode() suivantes:

urlencode() {
    # urlencode <string>
    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 <string>

    local url_encoded="${1//+/ }"
    printf '%b' "${url_encoded//%/\\x}"
}

Notez qu'au-dessus de urldecode() suppose que les données ne contiennent pas de barre oblique inverse.

Voici une version similaire de Joel trouvée sur: https://github.com/sixarm/urldecode.sh


bash + xxd

Fonction Bash avec l'outil xxd:

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
}

Trouvé dans fichier Gist de cdown , également sur stackoverflow .


PHP

En utilisant PHP vous pouvez essayer la commande suivante:

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

ou juste:

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

Utilisez -R Pour la saisie sur plusieurs lignes.


Perl

En Perl, vous pouvez utiliser URI::Escape .

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

Ou pour traiter un fichier:

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

awk

Essayez anon solution:

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

Remarque: Le paramètre -n Est spécifique à GNU awk.

Voir: tiliser awk printf pour urldecode texte .

décodage des noms de fichiers

Si vous devez supprimer le codage URL des noms de fichiers, utilisez l'outil deurlname de renameutils (par exemple deurlname *.*).

Voir également:


En relation:

67
kenorb

Il y a une fonction intégrée pour cela dans la bibliothèque standard Python. Dans Python 2, c'est urllib.unquote .

decoded_url=$(python2 -c 'import sys, urllib; print urllib.unquote(sys.argv[1])' "$encoded_url")

Ou pour traiter un fichier:

python2 -c 'import sys, urllib; print urllib.unquote(sys.stdin.read())' <file >file.new &&
mv -f file.new file

Dans Python 3, c'est urllib.parse.unquote .

decoded_url=$(python3 -c 'import sys, urllib.parse; print(urllib.parse.unquote(sys.argv[1]))' "$encoded_url")

Ou pour traiter un fichier:

python3 -c 'import sys, urllib; print(urllib.parse.unquote(sys.stdin.read()))' <file >file.new &&
mv -f file.new file

En Perl, vous pouvez utiliser URI::Escape .

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

Ou pour traiter un fichier:

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

Si vous voulez vous en tenir aux outils portables POSIX, c'est gênant, car le seul candidat sérieux est awk, qui n'analyse pas les nombres hexadécimaux. Voir tilisation de awk printf pour urldecode text pour des exemples avec des implémentations awk courantes, y compris BusyBox.

Si vous souhaitez utiliser une commande sed simple d'esprit, utilisez la commande suivante:

sed -e 's/%21/!/g' -e 's/%23/#/g' -e 's/%24/$/g' -e 's/%26/\&/g' -e "s/%27/'/g" -e 's/%28/(/g' -e 's/%29/)/g'

Mais il est plus pratique de créer un script comme (disons sedscript):

s/%21/!/g
s/%23/#/g
s/%24/$/g
s/%26/\&/g
s/%27/'/g
s/%28/(/g
s/%29/)/g

Exécutez ensuite sed -f sedscript < old > new, qui sortira comme vous le souhaitez.


Pour plus de facilité, la commande urlencode est également disponible directement dans gridsite-clients le package peut être installé à partir de (par Sudo apt-get install gridsite-clients dans le système Ubuntu/Debian).

NOM

    urlencode - convertit des chaînes vers ou depuis un formulaire encodé URL
SYNOPSIS
    urlencode [-m|-d] string [string ...]

LA DESCRIPTION

    urlencodeencode les chaînes conformément à la RFC 1738.

    Autrement dit, les caractères A-Za-z0-9._ et - ne sont pas modifiés, mais tous les autres caractères sont représentés sous la forme% HH, où HH est leur hexadécimal majuscule à deux chiffres ASCII représentation. Par exemple, l'URL http://www.gridpp.ac.uk/ devient http%3A%2F%2Fwww.gridpp.ac.uk%2F

    urlencode convertit chaque caractère dans toutes les chaînes données sur la ligne de commande. Si plusieurs chaînes sont données, elles sont concaténées avec des espaces de séparation avant la conversion.

OPTIONS
    -m
      Au lieu de la conversion complète, faites GridSite "encodage d'URL doux" dans lequel A-Z a-z 0-9. = - _ @ et/sont transmis sans modification. Il en résulte des chaînes légèrement plus lisibles par l'homme, mais l'application doit être prête à créer ou à simuler les répertoires impliqués par des barres obliques.
    -d
      Effectuez le décodage URL plutôt que le codage, selon la RFC 1738. Les chaînes% HH et% hh sont converties et les autres caractères sont transmis sans modification, à l'exception que +est converti en espace.

Exemple d'URL de décodage:

$ urlencode -d "http%3a%2f%2funix.stackexchange.com%2f"
http://unix.stackexchange.com/

$ urlencode -d "Example: %21, %22, . . . , %29 etc"
Example: !, ", . . . , ) etc
11
Pandya

Perl one liner:

$ Perl -pe 's/\%(\w\w)/chr hex $1/ge'

Exemple:

$ echo '%21%22' |  Perl -pe 's/\%(\w\w)/chr hex $1/ge'
!"
9
Adrian Pronk

GNU Awk

#!/usr/bin/awk -fn
@include "ord"
BEGIN {
   RS = "%.."
}
{
   printf "%s", $0
   if (RT != "") {
      printf "%s", chr("0x" substr(RT, 2)) 
   }
}
7
Steven Penny

Je ne peux pas commenter meilleure réponse dans ce fil , alors voici la mienne.

Personnellement, j'utilise ces alias pour l'encodage et le décodage d'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])"'

Les deux commandes vous permettent de convertir des données, passées en tant qu'argument de ligne de commande ou de les lire à partir de entrée standard , parce que les deux lignes simples vérifient s'il y a des arguments de ligne de commande (même vides) et les traitent ou lisent simplement l'entrée standard autrement.


mise à jour 2017-05-23 (codage slash)

En réponse au commentaire de @ Bevor.

Si vous devez également coder la barre oblique, ajoutez simplement un deuxième argument vide à la fonction de devis, puis la barre oblique sera également codée.

Donc, enfin urlencode alias in bash ressemble à ceci:

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

Exemple

$ 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
7
DIG mbl

Et une autre approche Perl:

#!/usr/bin/env Perl
use URI::Encode;
my $uri     = URI::Encode->new( { encode_reserved => 0 } );
while (<>) {

    print $uri->decode($_)
}

Vous devrez installer le URI::Encode module. Sur mon Debian, je pouvais simplement exécuter

Sudo apt-get install liburi-encode-Perl

Ensuite, j'ai exécuté le script ci-dessus sur un fichier de test contenant:

http://foo%21asd%23asd%24%26asd%27asd%28asd%29

Le résultat était (j'avais enregistré le script sous foo.pl):

$ ./foo.pl
http://foo!asd#asd$&asd'asd(asd)
4
terdon

Une réponse dans (principalement Posix) Shell:

$ input='%21%22'
$ printf "`printf "%s\n" "$input" | sed -e 's/+/ /g' -e 's/%\(..\)/\\\\x\1/g'`"
!"

Explication:

  • -e 's/+/ /g Transforme chaque + Dans l'espace (comme décrit dans la norme de codage url)
  • -e 's/%\(..\)/\\\\x\1/g' transforme chaque %XX en \\xXX. Notez que l'un des \ Sera supprimé en citant les règles.
  • Le printf interne est juste là pour passer l'entrée à sed. Nous pouvons le remplacer par tout autre mécanisme
  • Le printf externe interprète les séquences de \\xXX Et affiche le résultat.

Modifier:

Puisque % Doit toujours être interprété dans les URL, il est possible de simplifier cette réponse. De plus, je pense qu'il est plus propre d'utiliser xargs au lieu de backquotes (grâce à @josch).

$ input='%21%22+%25'
$ printf "%s\n" "$input" | sed -e 's/+/ /g; s/%/\\x/g' | xargs -0 printf
!" %

Malheureusement, (comme @josch l'a remarqué) aucune de ces solutions n'est compatible Posix car la séquence d'échappement \x N'est pas définie dans Posix.

3
Jérôme Pouiller

Une autre solution utilisant Ruby (acceptée python ne fonctionnait pas pour moi))

alias urldecode='Ruby -e "require \"cgi\"; puts CGI.unescape(ARGV[0])"'
alias urlencode='Ruby -e "require \"cgi\"; puts CGI.escape(ARGV[0])"'

Exemple

$ urldecode 'q+werty%3D%2F%3B'
q werty=/;

$ urlencode 'q werty=/;'
q+werty%3D%2F%3B
1
Shiyason

Voici une fonction BASH pour faire exactement cela:

function urldecode() {
        echo -ne $(echo -n "$1" | sed -E "s/%/\\\\x/g")
}
1
Adi D

Shell uniquement:

$ x='a%20%25%e3%81%82';printf "${x//\%/\\x}"
a %あ

Ajouter -- ou %b pour éviter que les arguments commençant par un tiret soient traités comme des options.

Dans zsh ${x//%/a} ajoute a à la fin mais ${x//\%/a} remplace % avec a.

1
Lri

La solution simple pour les chaînes courtes (Shell est lentwww):

$ str='q+werty%3D%2F%3B'

$ a=${str//+/ };printf "$(echo "${a//%/\\x}")\n"

q werty=/;
0
Isaac

Voici les bits pertinents d'un autre script (que je viens de voler sans vergogne de mon script de téléchargement youtube.com d'une autre réponse) J'ai déjà écrit. Il utilise sed et le Shell pour construire un urldecode fonctionnel.

set \! \" \# \$ \% \& \' \( \) \* \ \+ \, \/ \: \; \= \? \@ \[ \]
for c do set "$@" "'$c" "$c"; shift; done
curl -s "$url" | sed 's/\\u0026/\&/g;'"$(
    printf 's/%%%X/\\%s/g;' "$@"
)"

Je ne jure pas qu'il est complet - et en fait j'en doute - mais il a sûrement géré YouTube.

0
mikeserv