2012-02-09 13 views
2

ほとんどのHTTPリクエストで送信されたHTTPヘッダを追加する(またはユーザエージェント文字列を変更する)必要があります。マシン上のすべての* HTTPリクエストにヘッダを追加する

ほとんどの場合、Internet Explorer内のすべてのものと、.NETアプリケーションからのものがあります。

私はすでにBHOを書くことでInternet Explorer側を評価しましたが、BHOはIEにロードされたClickOnceコントロールによって要求された要求を傍受しません。

私の場合の.NETアプリケーションは、すべてWebRequest.Createを使用してリクエストしています。

これは可能ですか?私はSystem.Netスタックのどこかにコードを注入したいと思っています。

プロキシは1つの可能性がありましたが、地獄のように機能しないプロキシを作成することは困難でした。 HTTPSトラフィックは別の問題です。

+0

実際にはプロキシ以外の方法はありません。 *ほとんどの* HTTP要求について、あなたは何を言いますか?どのようなリクエスト*あなたがキャッチしたくない?他のブラウザ(Firefox、Chromeなど)はどうですか? –

+0

2番目の段落で「ほとんど」の意味を説明します。 – RMD

+0

さて、あなたがIEだけを意味していたのは明らかではありませんでした。ちょうどIEを含めることは奇妙に思えましたが、他のブラウザは気にしませんでした。 –

答えて

6

私はこれを考え出した。

WebRequest.Createファクトリによって返される前に、HttpWebRequestのユーザーエージェントを明示的に設定するカスタムWeb要求モジュールを作成しました。あなたはこのアセンブリに署名し、GACに追加する必要があります

public class CustomHttpRequestCreator : IWebRequestCreate 
{ 
    public CustomHttpRequestCreator(){} 

    public WebRequest Create(Uri uri) 
    { 
     HttpWebRequest webRequest = Activator.CreateInstance(typeof(HttpWebRequest), 
             BindingFlags.CreateInstance | BindingFlags.Public | 
             BindingFlags.NonPublic | BindingFlags.Instance, 
             null, new object[] { uri, null }, null) as HttpWebRequest; 

     webRequest.UserAgent = "OMG IT WORKED!"; 
     return webRequest; 
    } 
} 

まず、IWebRequestCreateを実装したクラスを作成します。誰かがWebRequest.Createを呼び出すたび

<system.net> 
    <webRequestModules> 
     <remove prefix="http:"/> 
     <remove prefix="https:"/> 
     <add prefix="http:" type="HttpWebRequestTest.CustomHttpRequestCreator, HttpWebRequestTest, Version=1.0.0.0, Culture=neutral, PublicKeyToken=4ba7a6b9db5020b7" /> 
     <add prefix="https:" type="HttpWebRequestTest.CustomHttpRequestCreator, HttpWebRequestTest, Version=1.0.0.0, Culture=neutral, PublicKeyToken=4ba7a6b9db5020b7" /> 
    </webRequestModules> 
</system.net> 

は今、彼らはすでに設定されているユーザーエージェント文字列では、HttpWebRequestを取得します:

は今、あなたのマシン上のmachine.configに、以下の構成セクションを追加します。


私はまた、HttpWebRequestのから継承されたカスタムクラスを作成しようとしましたが、デフォルトのパブリックコンストラクタがありませんでしたので、これはトリッキーでした。唯一のパブリックコンストラクタは、ISerializableの廃止された実装でした。

ISerializableコンストラクタで使用するderviedクラスを正常に取得できましたが、結果として得られる「疑似水和」オブジェクトは有効な状態にはありませんでした.ISerializable実装は時代遅れであり、マイクロソフトが管理しています。

さらに、より詳細に使用する際に発生したエラーを調査すると、この作業を行うことができます。具体的には、ServicePoint関連のアクセスに問題があります。反射を利用することで、物事を働かせることができるかもしれません。ここに参考のための私の実装です:

public class CustomHttpWebRequest : HttpWebRequest 
{ 
    public CustomHttpWebRequest(SerializationInfo serializationInfo, StreamingContext streamingContext) : base(serializationInfo, streamingContext) { } 

    internal CustomHttpWebRequest(Uri uri) : base(BuildSerializationInfo(uri), new StreamingContext()) 
    { 
     this.UserAgent = "OMG IT WORKED! (Constructor)"; 
    } 

    private static SerializationInfo BuildSerializationInfo(Uri uri) 
    { 
     HttpWebRequest webRequest = Activator.CreateInstance(typeof(HttpWebRequest), 
             BindingFlags.CreateInstance | BindingFlags.Public | 
             BindingFlags.NonPublic | BindingFlags.Instance, 
             null, new object[] { uri, null }, null) as HttpWebRequest; 

     var serializationInfo = new SerializationInfo(typeof(HttpWebRequest), new System.Runtime.Serialization.FormatterConverter()); 
     ((ISerializable)webRequest).GetObjectData(serializationInfo, new StreamingContext()); 
     return serializationInfo; 
    } 

    public override WebResponse GetResponse() 
    { 
     this.UserAgent = "OMG IT WORKED!"; 
     return base.GetResponse(); 
    } 

    public override IAsyncResult BeginGetResponse(AsyncCallback callback, object state) 
    { 
     this.UserAgent = "OMG IT WORKED ASYNC!"; 
     return base.BeginGetResponse(callback, state); 
    } 
} 
+0

それは同時に素晴らしいと恐ろしいです。 –

関連する問題