8150


こんにちわ！

windows環境で、.NetのHttpClient 、Socket で、  
サーバーと通信する際に、  
送信元の自分のIPアドレスを指定したいんですが、  
どうしたらよいでしょうか？

どういう状況かといいますと、

PCには、２枚 LANカードが刺さっており、  
それぞれ別のネットワーク1、2につながっています。  
サーバーA、サーバーB のIPアドレスはそれぞれ、  
同一で、固定で変更することができません。

■ネットワーク図

[code]

    ○サーバーA(192.168.1.2) 
    |※ネットワーク1 
    LANカードA(192.168.1.5) 
    ○PC 
    LANカードB(192.168.1.6) 
    |※ネットワーク2 
    ○サーバーB(192.168.1.2) 
    
[/code]

このとき、ネットワーク1,2のサーバーA,Bとそれぞれ通信をおこないたい考えです。  
単純な相手先のIPアドレス指定では、  
どちらか一方のサーバーとした通信ができません。

方法として、送信するLANカードを指定することができればよいみたいで、  
送信したいネットワークにつながっている自分のＬＡＮカードのＩＰアドレスを指定すると、  
そのＬＡＮカードから送信することは PINGで、送信元IPアドレス指定でできることがわかりました。

[code]

    ping -s 192.168.1.5 192.168.1.2 
    
[/code]

だと、サーバーA 、

[code]

    ping -s 192.168.1.6 192.168.1.2 
    
[/code]

では、サーバーBに送信することができていることがわかっています。

すいませんが、よろしくおねがいします。


CC BY-SA 3.0
2015-03-19T14:24:35.167
8147
2015-03-20T10:26:58.370
8922
question
.net http network socket tcp
ＬＡＮカード２枚差し時に、同一ＩＰアドレスのサーバーと通信する方法に関して


HttpClientクラスでは制御方法が提供されていません。Socketクラスであれば[Bind()メソッド](https://msdn.microsoft.com/ja-
jp/library/system.net.sockets.socket.bind\(v=vs.110\).aspx)で制御できます。


CC BY-SA 3.0
2015-03-19T15:14:09.023
8150
2015-03-19T15:14:09.023
4236
8147
answer


本家SOでも同じような質問がありますね。

[.net - Best way to specify the local endpoint for HTTP request? - Stack
Overflow](https://stackoverflow.com/q/26237192/2818869)

HttpClientでは難しいということで、HttpWebRequestクラスを使った方法が回答されています。

例えばサーバーAにアクセスするならこのようになるでしょうか。

[code]

    var req = HttpWebRequest.CreateHttp("http://192.168.1.2/");
    
    req.ServicePoint.BindIPEndPointDelegate = 
      (s, ep, retries) => 
        new IPEndPoint(IPAddress.Parse("192.168.1.5"), 1234 + retries);
    
    var response = req.GetResponse();
    
[/code]

（以下、コメント欄での指摘を受けて追記）

ServicePointは接続先（スキーマとホスト名）単位で同じものが使われます。今回の場合それらの要素は同じでしょうから、ホストAとホストBは同じServicePoint、同じBindIPEndPointDelegateが使われることになります。

このため、両方のホストにアクセスする必要があるなら、接続処理が行われるタイミング（例えばGetResponse）の時点で正しいエンドポイントを返す、具体的には「接続する直前にデリゲートを設定し、接続するまでの間に別のホストへ接続しないようにする」などの注意が必要です。

加えて、KeepAliveなどでコネクションを流用する際にもやはりホスト名で識別することになりますから、ホストAとホストBの間でコネクションが流用されないようにする必要があります。これについては
[`HttpWebRequest.ConnectionGroupName`](https://msdn.microsoft.com/ja-
jp/library/6y3d5dts\(v=vs.110\).aspx) プロパティにそれぞれ違う値を設定することで可能です。


CC BY-SA 3.0
2015-03-20T08:01:20.647
8178
2015-03-20T10:26:58.370
2017-05-23T12:38:56.467
-1
8000
8147
answer