Slash encodé dans L'URL

ma carte est:

routes.MapRoute(
   "Default",                                             // Route name
   "{controller}/{action}/{id}",                          // URL with params
   new { controller = "Home", action = "Index", id = "" } // Param defaults
);

si j'utilise L'URL http://localhost:5000/Home/About/100%2f200 il n'y a pas de route correspondante. Je change L'URL en http://localhost:5000/Home/About/100 puis la route est de nouveau appariée.

Est-il un moyen facile de travailler avec des paramètres qui contiennent des barres obliques? D'autres valeurs échappées (espace %20 ) semblent fonctionner.

EDIT:

pour coder Base64 fonctionne pour moi. Cela rend l'URL moche, mais C'est OK pour le moment.

public class UrlEncoder
{ 
    public string URLDecode(string  decode)
    {
        if (decode == null) return null;
        if (decode.StartsWith("="))
        {
            return FromBase64(decode.TrimStart('='));
        }
        else
        {
            return HttpUtility.UrlDecode( decode) ;
        }
    }

    public string UrlEncode(string encode)
    {
        if (encode == null) return null;
        string encoded = HttpUtility.PathEncode(encode);
        if (encoded.Replace("%20", "") == encode.Replace(" ", ""))
        {
            return encoded;
        }
        else
        {
            return "=" + ToBase64(encode);
        }
    }

    public string ToBase64(string encode)
    {
        Byte[] btByteArray = null;
        UTF8Encoding encoding = new UTF8Encoding();
        btByteArray = encoding.GetBytes(encode);
        string sResult = System.Convert.ToBase64String(btByteArray, 0, btByteArray.Length);
        sResult = sResult.Replace("+", "-").Replace("/", "_");
        return sResult;
    }

    public string FromBase64(string decode)
    {
        decode = decode.Replace("-", "+").Replace("_", "/");
        UTF8Encoding encoding = new UTF8Encoding();
        return encoding.GetString(Convert.FromBase64String(decode));
    }
}

edit 1:

à la fin, il s'est avéré que la meilleure façon était de sauvegarder une corde bien formatée pour chaque élément que je dois sélectionner. C'est bien mieux parce que maintenant je n'encode que les valeurs et ne les décode jamais. Tous les caractères spéciaux deviennent" -". Beaucoup de mes tables db ont maintenant cette colonne supplémentaire "URL". Les données sont assez stables, c'est pourquoi je peux aller par là. Je peux même vérifier, si les données dans "URL" est unique.

EDIT2:

aussi attention au caractère d'espace. Il semble ok sur VS webserver intégré, mais est différent sur iis7 correctement url Encoder caractère d'espace

56
demandé sur Community 2009-02-26 20:58:57

9 réponses

si ce n'est que votre dernier paramètre, vous pouvez faire:

routes.MapRoute(
    "Default",                                                // Route name
    "{controller}/{action}/{*id}",                            // URL with parameters
    new { controller = "Home", action = "Index", id = "" });  // Parameter defaults
45
répondu Mehrdad Afshari 2009-02-26 18:01:54

dans .NET 4.0 beta 2, L'équipe CLR a proposé une solution.

ajoutez ceci à votre site web.fichier de configuration:

<uri> 
    <schemeSettings>
        <add name="http" genericUriParserOptions="DontUnescapePathDotsAndSlashes" />
    </schemeSettings>
</uri>

cela provoque la classe Uri à se comporter selon le RFC décrivant URIs, permettant aux slashes d'être échappés dans le chemin sans être échappés. L'équipe CLR indique qu'ils s'écartent de la spécification pour des raisons de sécurité, et de mettre cela dans votre .le fichier de configuration vous fait prendre la propriété de la sécurité supplémentaire considérations liées au fait de ne pas défaire les entailles.

24
répondu Andrew Arnott 2009-11-16 23:00:58

Voici une explication simple de la solution et un résumé de ce qui a déjà été dit.

Demande côté:

  1. UrlEncode votre chemin.
  2. Remplacer le '%' de '!'.
  3. faire la demande.

réponses:

  1. remplacer le"!' avec.'%'
  2. Urldécode votre chemin.
  3. Utilisez les paramètres comme prévu.

rincer, répéter, apprécier.

21
répondu Don Rolling 2011-03-09 16:06:03

Une autre option est d'utiliser une valeur querystring. Très boiteux, mais plus simple que l'encodage personnalisé.

http://localhost:5000/Home/About?100%2f200
11
répondu Jon Galloway 2009-11-14 18:15:45

idem pour Java / Tomcat.

il y a toujours un problème si vous avez un " / " encodé (%2F) dans votre URL.

RFC 3986 - Section 2.2 dit: "Si les données pour le composant URI serait en conflit avec un caractère réservé du but comme un séparateur, le conflit de données doit être pour cent codé avant l'URI est formé."(RFC 3986 - Section 2.2)

mais il y a un problème avec Tomcat:

http://tomcat.apache.org/security-6.html - fixe dans Apache Tomcat 6.0.10

important: répertoire transversal CVE-2007-0450

Tomcat permet '\', '%2F' et '%5C" [...] .

les propriétés suivantes du système Java ont été ajoutés à Tomcat pour fournir un contrôle supplémentaire de la manipulation de délimiteurs de chemin dans les URLs (les deux options par défaut à false):

  • org.Apache.tomcat.util.buf.UDecoder.ALLOW_ENCODED_SLASH: vrai /faux
  • org.Apache.Catalina.connecteur.CoyoteAdapter.ALLOW_BACKSLASH: vrai /faux

en Raison de l'impossibilité de garantir que toutes les URLs sont gérées par Tomcat ils sont dans des serveurs proxy, Tomcat devrait toujours être sécurisé comme si non l'accès au contexte restreint par procuration était utiliser.

affecte: 6.0.0-6.0.9

donc si vous avez une URL avec le caractère %2F, Tomcat retourne: "400 URI invalide: noSlash"

vous pouvez basculer du bugfix dans le script de démarrage Tomcat:

set JAVA_OPTS=%JAVA_OPTS% %LOGGING_CONFIG%   -Dorg.apache.tomcat.util.buf.UDecoder.ALLOW_ENCODED_SLASH=true 
9
répondu simonox 2010-09-28 07:38:38

vous pouvez éviter le double encodage/décodage suggestions ci-dessus et tout simplement utiliser HttpServerUtility.UrlTokenEncode et L'UrlTokenDecode correspondante.

1
répondu silentnoise 2016-03-16 17:15:13

c'est intéressant à propos de .NET 4. Quoi qu'il en soit, ce lien décrit la RFC 1738 et inclut les caractères qui doivent être encodés et qui sont tout simplement "dangereux". texte du lien

si je veux une URL conviviale SEO, (comme quand vous voulez mettre un sujet forum post dans L'URL), est de sauter l'encodage et de remplacer tout ce qui n'est pas A-Z, a-z, 0-9.

public static string CreateSubjectSEO(string str)
    {
        int ci;
        char[] arr = str.ToCharArray();
        for (int i = 0; i < arr.Length; i++)
        {
            ci = Convert.ToInt32(arr[i]);
            if (!((ci > 47 && ci < 58) || (ci > 64 && ci < 91) || (ci > 96 && ci < 123)))
            {
                arr[i] = '-';
            }
        }
        return new string(arr);
    }
0
répondu BillB 2009-11-21 19:44:53

comme suggéré ici quand le problème a été confronté par Symfony 1.x développeurs (+suggéré dans les commentaires PHP pour urlencode() ):

  • Coder ' / " à "%2F " avant urlencode()
  • Décoder "%2F' ' / ' après (si nécessaire) urldecode()

Note: Vous pouvez utiliser rawurlencode() , mais vous devrez tout de même urlencode '/' deux fois.

avantages:

  • évite le recours à d'autres procédés d'échappement (si l'on remplace " / "par un caractère spécial comme"!'ou '_')
  • ne dépend d'aucun paramètre de serveur tel que AllowEncodedSlashes pour Apache
-1
répondu Frosty Z 2011-08-30 10:13:34

il suffit d'utiliser Server.UrlDecode . Il fonctionne, je l'ai testé.

-3
répondu shijas km 2012-06-22 08:01:25