From: tadanori kojima Date: 2011-08-10T18:21:30+09:00 Subject: [ruby-dev:44373] Re: [Ruby 1.9 - Feature #5180] net/http の接続時に用いる IP アドレスの指定 load balancer利用時のreal IPへの接続などのユースケースは理解できますが ----- Net::HTTP.start("127.0.0.1") {|h| print h.request_get( '/index.html' , {"host"=>"ruby-lang.org"}).body } ※startはIP指定、リクエスト時のhostヘッダにホスト名 ----- というのがHTTP的なふつうの対処な気がします ホストがv4/v6の両アドレスを持つ場合などにv4で接続したい、 となるときも同じような感じでしょうか On Wed, 10 Aug 2011 15:05:24 +0900 Yui NARUSE wrote: > > Issue #5180 has been updated by Yui NARUSE. > > > Shyouhei Urabe wrote: > > (08/10/2011 11:46 AM), Yui NARUSE wrote: > > > 例えば、ホスト名は "ruby-lang.org" としたいが、IP アドレスは 127.0.0.1 とか。 > > > > /etc/hostsを書け、ではだめですか。名前解決のレイヤーの要件をHTTPで解決するのは筋が悪いでしょう。 > > 127.0.0.1 の例だとそうなんですね。 > > 別のユースケースとして、同じホスト名(というかドメイン名)を持つ複数のサーバ群に対して、 > それぞれに動作確認で通信したい事があったんですが、この場合だと一定のホスト名を送りつつ 、 > IP アドレスは網羅しないといけないので、/etc/hosts だとサーバーの数だけ書き換えて試すのを > 繰り返さないといけないのでつらいです。 > ---------------------------------------- > Feature #5180: net/http の接続時に用いる IP アドレスの指定 > http://redmine.ruby-lang.org/issues/5180 > > Author: Yui NARUSE > Status: Open > Priority: Normal > Assignee: > Category: lib > Target version: > > > 通常 net/http を使う時は、Net::HTTP.start("ruby-lang.org") などとホスト名を使います。 > で、Socket がホスト名から IP アドレスを引いて、コネクションが張られます。 > 普通の人はこれで足りるわけですが、ふつうな人はしばしば DNS で引けない IP アドレスに接続したくなります。 > 例えば、ホスト名は "ruby-lang.org" としたいが、IP アドレスは 127.0.0.1 とか。 > > 以下のパッチをあてると、 > Net::HTTP.start("ruby-lang.org", ipaddr: '127.0.0.1') > などとできるようになります。 > > diff --git a/lib/net/http.rb b/lib/net/http.rb > index 7b9ec4f..6d034e0 100644 > --- a/lib/net/http.rb > +++ b/lib/net/http.rb > @@ -524,7 +524,7 @@ module Net #:nodoc: > # _opt_ :: optional hash > # > # _opt_ sets following values by its accessor. > - # The keys are ca_file, ca_path, cert, cert_store, ciphers, > + # The keys are ipaddr, ca_file, ca_path, cert, cert_store, ciphers, > # close_on_empty_response, key, open_timeout, read_timeout, ssl_timeout, > # ssl_version, use_ssl, verify_callback, verify_depth and verify_mode. > # If you set :use_ssl as true, you can use https and default value of > @@ -542,6 +542,7 @@ module Net #:nodoc: > port, p_addr, p_port, p_user, p_pass = *arg > port = https_default_port if !port && opt && opt[:use_ssl] > http = new(address, port, p_addr, p_port, p_user, p_pass) > + http.ipaddr = opt[:ipaddr] if opt[:ipaddr] > > if opt > if opt[:use_ssl] > @@ -575,6 +576,7 @@ module Net #:nodoc: > def initialize(address, port = nil) > @address = address > @port = (port || HTTP.default_port) > + @ipaddr = nil > @curr_http_version = HTTPVersion > @no_keepalive_server = false > @close_on_empty_response = false > @@ -620,6 +622,17 @@ module Net #:nodoc: > # The port number to connect to. > attr_reader :port > > + # The IP address to connect to/used to connect to > + def ipaddr > + started? ? @socket.io.peeraddr[3] : @ipaddr > + end > + > + # Set the IP address to connect to > + def ipaddr=(addr) > + raise IOError, "ipaddr value changed, but session already started" if started? > + @ipaddr = addr > + end > + > # Number of seconds to wait for the connection to open. Any number > # may be used, including Floats for fractional seconds. If the HTTP > # object cannot open a connection in this many seconds, it raises a > @@ -945,7 +958,7 @@ module Net #:nodoc: > # without proxy > > def conn_address > - address() > + @ipaddr || address() > end > > def conn_port > > > -- > http://redmine.ruby-lang.org