代码之家  ›  专栏  ›  技术社区  ›  Dan Sosedoff

有没有办法将ruby net::http请求附加到特定的IP地址/网络接口上?

  •  11
  • Dan Sosedoff  · 技术社区  · 14 年前

    我正在寻找一种使用标准NET::HTTP库为每个GET请求使用不同IP地址的方法。服务器有5个IP地址,并假定当达到每个IP的请求限制时,某些API会阻止访问。所以,唯一的方法就是使用另一台服务器。我在Ruby文档中找不到任何关于它的信息。

    例如,curl允许您将其附加到特定的IP地址(在php中):

    $req = curl_init($url)
    curl_setopt($req, CURLOPT_INTERFACE, 'ip.address.goes.here';
    $result = curl_exec($req);
    

    有没有办法用net::http库来完成它?作为备选方案-路缘石(红宝石卷边)。但这将是我最后一次尝试。

    建议/想法?

    P.S.有路缘石的解决方案(有脏试验,IP被替换):

    require 'rubygems'
    require 'curb'
    
    ip_addresses = [
      '1.1.1.1',
      '2.2.2.2',
      '3.3.3.3',
      '4.4.4.4',
      '5.5.5.5'
    ]
    
    ip_addresses.each do |address|
      url = 'http://www.ip-adress.com/'
      c = Curl::Easy.new(url)
      c.interface = address
      c.perform
      ip = c.body_str.scan(/<h2>My IP address is: ([\d\.]{1,})<\/h2>/).first
      puts "for #{address} got response: #{ip}"
    end
    
    4 回复  |  直到 6 年前
        1
  •  2
  •   zaius    14 年前

    看起来你不能用net:http来完成。这是来源

    http://github.com/ruby/ruby/blob/trunk/lib/net/http.rb

    644线是打开连接的地方。

      s = timeout(@open_timeout) { TCPSocket.open(conn_address(), conn_port()) }
    

    tcpsocket.open的第三个和第四个参数是local_地址和local_端口,由于没有指定它们,所以不可能。看来你得走路边了。

        2
  •  6
  •   jhosteny    10 年前

    我知道这是老的,但希望有人发现这是有用的,因为我今天需要这个。您可以执行以下操作:

    http = Net::HTTP.new(uri.host, uri.port)
    http.local_host = ip
    response = http.request(request)
    

    请注意,我认为您不能使用net::http.start,因为它不接受本地主机作为选项。

        3
  •  5
  •   Hakan Ensari    14 年前

    事实上,如果你的猴子补丁tcpsocket,有一种方法可以做到这一点:

    https://gist.github.com/800214

    路缘石很棒,但不会和JRuby合作,所以我一直在寻找替代品…

        4
  •  -1
  •   Farhana Naaz Ansari Jay Dwivedi    6 年前

    当然可以。我做如下:

    # remote_host can be IP or hostname
    uri     = URI.parse( "http://" + remote_host )
    http    = Net::HTTP.new( uri.host, uri.port )
    request = Net::HTTP::Get.new(uri.request_uri)
    request.initialize_http_header( { "Host" => domain })
    response = http.request( request )