58

私の地図は:

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

URLを使用するhttp://localhost:5000/Home/About/100%2f200と、一致するルートがありません。URLをに変更するとhttp://localhost:5000/Home/About/100、ルートが再び一致します。

スラッシュを含むパラメーターを操作する簡単な方法はありますか?他のエスケープされた値(スペース%20)は機能しているようです。

編集:

Base64をエンコードすることは私のために働きます。URLが醜くなりますが、今のところは問題ありません。

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));
    }
}

編集1:

最後に、最善の方法は、選択する必要のあるアイテムごとに適切にフォーマットされた文字列を保存することであることが判明しました。今は値をエンコードするだけで、デコードすることはないので、これははるかに優れています。すべての特殊文字は「-」になります。私のdb-tableの多くには、この追加の列「URL」があります。データはかなり安定しているので、私はこの方法で行くことができます。「URL」のデータが一意かどうかも確認できます。

EDIT2:

また、スペース文字にも注意してください。VS統合Webサーバーでは問題ないように見えますが、iis7では異なります。適切にURLエンコードされたスペース文字

4

10 に答える 10

26

以下は、解決策の簡単な説明と、これまでに述べたことの要約です。

リクエスト側:

  1. パスを URL エンコードします。
  2. 「%」を「!」に置き換えます。
  3. リクエストを行います。

応答側:

  1. 「!」を置き換えます。と '%'。
  2. パスを UrlDecode します。
  3. パラメータは意図したとおりに使用してください。

すすぎ、繰り返し、お楽しみください。

于 2011-03-09T16:06:03.327 に答える
24

.NET 4.0 ベータ 2 では、CLR チームが回避策を提供しています。

これを web.config ファイルに追加します。

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

これにより、URI を記述する RFC に従って Uri クラスが動作し、スラッシュをエスケープせずにパス内でエスケープできるようになります。CLR チームは、セキュリティ上の理由から仕様から逸脱していると報告しています。これを .config ファイルに設定すると、基本的に、スラッシュをエスケープ解除しないことに関連する追加のセキュリティ考慮事項の所有権を取得できます。

于 2009-11-16T23:00:58.267 に答える
13

もう 1 つのオプションは、クエリ文字列値を使用することです。非常に不自由ですが、カスタム エンコーディングよりも単純です。

http://localhost:5000/Home/About?100%2f200
于 2009-11-14T18:15:45.783 に答える
9

Java / Tomcat についても同様です。

URL にエンコードされた「/」(%2F) がある場合は、まだ問題があります。

RFC 3986 - セクション 2.2 は次のように述べています。(RFC 3986 - セクション 2.2)

しかし、Tomcat には問題があります。

http://tomcat.apache.org/security-6.html - Apache Tomcat 6.0.10 で修正済み

重要: ディレクトリ トラバーサル CVE-2007-0450

Tomcat は '\'、'%2F' および '%5C' [...] を許可します。

次の Java システム プロパティが Tomcat に追加され、URL のパス区切り文字の処理をさらに制御できるようになりました (両方のオプションのデフォルトは false)。

  • org.apache.tomcat.util.buf.UDecoder.ALLOW_ENCODED_SLASH: true|false
  • org.apache.catalina.connector.CoyoteAdapter.ALLOW_BACKSLASH: true|false

すべての URL がプロキシ サーバーと同じように Tomcat によって処理されることを保証することは不可能であるため、Tomcat は常に、コンテキスト アクセスを制限するプロキシが使用されていないかのように保護する必要があります。

影響: 6.0.0-6.0.9

したがって、%2F 文字を含む URL を取得した場合、Tomcat は「400 無効な URI: noSlash」を返します。

Tomcat 起動スクリプトでバグ修正を切り替えることができます。

set JAVA_OPTS=%JAVA_OPTS% %LOGGING_CONFIG%   -Dorg.apache.tomcat.util.buf.UDecoder.ALLOW_ENCODED_SLASH=true 
于 2010-09-28T07:38:38.953 に答える
0

それは .NET 4 について興味深いことです。とにかく、このリンクでは RFC 1738 について説明し、エンコードが必要な文字と単に「安全でない」文字が含まれています。 リンクテキスト

SEO フレンドリーな URL が必要な場合 (フォーラムの投稿の件名を URL に入れたい場合など)、エンコードをスキップして、AZ、az、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);
    }
于 2009-11-21T19:44:53.643 に答える
-1

Symfony 1.x 開発者が問題に直面したときにここで提案されているように (+ のPHP コメントでurlencode()提案されています):

  • 前に「/」を「%2F」にエンコードurlencode()
  • '%2F' を '/' にデコードします (必要な場合)urldecode()

注: を使用できますがrawurlencode()、「/」を 2 回 urlencode する必要があります。

利点:

  • 追加のエスケープ プロセスの必要性を回避します (「/」を「!」や「_」などの特殊文字に置き換える場合)
  • AllowEncodedSlashesApacheなどのサーバー設定に依存しない
于 2011-08-30T10:05:00.623 に答える
-3

を使用するだけServer.UrlDecodeです。それは動作します、私はテストしました。

于 2012-06-22T07:23:13.350 に答える