39

HTTPGETをに送信したいhttp://example.com/%2F。私の最初の推測は次のようになります。

using (WebClient webClient = new WebClient())
{
  webClient.DownloadData("http://example.com/%2F");
}

残念ながら、実際にネットワーク上で送信されるのは次のとおりです。

GET // HTTP/1.1
Host: example.com
Connection: Keep-Alive

したがって、 http: //example.com/%2Fは送信前にhttp://example.com//に変換されます。

このGETリクエストを実際に送信する方法はありますか?

OCSPプロトコルでは、HTTP / GETを介してOCSPを使用する場合、base-64エンコードのurlエンコードを送信する必要があるため、準拠するには「/」ではなく実際の%2Fを送信する必要があります。

編集:

OCSPプロトコル標準( RFC 2560付録A.1.1)の関連部分は次のとおりです。

GETメソッドを使用するOCSP要求は、次のように構成されます。

GET {url} /{url-OCSPRequestのDERエンコーディングのbase-64エンコーディングのエンコーディング}

私はこれについて他の読み方を非常に受け入れていますが、他に何を意味するのかわかりません。

4

5 に答える 5

49

これはひどいハックであり、フレームワークの将来のバージョンなどとは互換性がないはずです。

しかし、それは機能します!

(私のマシンでは...)

Uri uri = new Uri("http://example.com/%2F");
ForceCanonicalPathAndQuery(uri);
using (WebClient webClient = new WebClient())
{
  webClient.DownloadData(uri);
}

void ForceCanonicalPathAndQuery(Uri uri){
  string paq = uri.PathAndQuery; // need to access PathAndQuery
  FieldInfo flagsFieldInfo = typeof(Uri).GetField("m_Flags", BindingFlags.Instance | BindingFlags.NonPublic);
  ulong flags = (ulong) flagsFieldInfo.GetValue(uri);
  flags &= ~((ulong) 0x30); // Flags.PathNotCanonical|Flags.QueryNotCanonical
  flagsFieldInfo.SetValue(uri, flags);
}
于 2009-04-24T08:15:24.507 に答える
30

デフォルトでは、UriクラスはURIでエスケープ/文字( )を許可しません(これはRFC 3986%2fの私の読みでは合法であるように見えますが)。

Uri uri = new Uri("http://example.com/%2F");
Console.WriteLine(uri.AbsoluteUri); // prints: http://example.com//

(注: URIの出力にUri.ToStringを使用しないでください。)

Microsoft Connectでのこの問題のバグレポートによると、この動作は仕様によるものですが、app.configまたはweb.configファイルに以下を追加することで回避できます。

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

(これは、リフレクションを使用してプライベートフィールドを変更せずにこのバグを回避する「公式」の方法であるため、 https: //stackoverflow.com/a/10415482から再投稿されました。)

編集: Connectバグレポートは表示されなくなりましたが、のドキュメントで<schemeSettings>/は、URIでエスケープ文字を許可するためにこのアプローチを推奨しています。(その記事によると)エスケープされたスラッシュを正しく処理しないコンポーネントにはセキュリティ上の影響がある可能性があることに注意してください。

于 2012-08-29T02:32:44.077 に答える
13

これに関する更新:Uriクラスのデフォルトの動作が実際に.NET 4.5で変更されたように見えます。エスケープされたスラッシュを使用できるようになり、それらは変更されません。

.NET 3.5、.NET 4.0、.NET 4.5/4.5.1で次のコードを実行しました

static void Main(string[] args)
{
    var uri = new Uri("http://www.yahooo.com/%2F");
    var client = new WebClient();
    client.DownloadString(uri);
}

.NET 3.5 / 4.0では、トレースは、%2Fが実際には期待どおりにエスケープされていないことを示しています。

フィドラートレース

ただし、.NET 4.5 / 4.5.1では、%2Fがエスケープされていないことがわかります(GET /%2Fに注意してください)。

フィドラートレース

UriでToString()を使用することもでき、同じ結果が得られます。

したがって、結論として、.NET> = .NET 4.5を使用している場合は、RFCに沿った動作をするように見えます。

私は、Monoで同じアプローチを機能させることを試みたところです。私はここにアプローチに関する私の質問を投稿しました:モノラルでエスケープされたスラッシュでURIを取得する

于 2013-12-22T20:15:40.727 に答える
0

Ramusによって投稿された回答に対する私のコメントで述べたように、このハックを機能させるには、.Net Standard(および場合によってはそれ以降のバージョンの.Net Framework)に次のものが必要です。

Uri uri = new Uri("http://example.com/%2F");
ForceCanonicalPathAndQuery(uri);
using (WebClient webClient = new WebClient())
{
  webClient.DownloadData(uri);
}

void ForceCanonicalPathAndQuery(Uri uri){
  string paq = uri.PathAndQuery; // need to access PathAndQuery
  FieldInfo flagsFieldInfo = typeof(Uri).GetField("_flags", BindingFlags.Instance | BindingFlags.NonPublic);
  ulong flags = (ulong) flagsFieldInfo.GetValue(uri);
  flags &= ~((ulong) 0xC30); // Flags.PathNotCanonical|Flags.QueryNotCanonical
  flagsFieldInfo.SetValue(uri, flags);
}
于 2019-10-13T05:18:59.890 に答える
-7

ダブルエンコード:%252F

ただし、HttpWebRequestを使用する場合は、実際にはURLをエンコードしないように指示できます。どちらの方法でも機能します。

また、WebClientがURIを受け入れる場合は、新しいURIを作成し、エンコードしないように設定できます。

于 2009-04-23T10:55:52.830 に答える