Methods
Public Class
Public Instance
Included modules
Public Class methods
new(origin, addresses, options)
[show source]
# File lib/httpx/io/tcp.rb 16 def initialize(origin, addresses, options) 17 @state = :idle 18 @addresses = [] 19 @hostname = origin.host 20 @options = options 21 @fallback_protocol = @options.fallback_protocol 22 @port = origin.port 23 @interests = :w 24 if @options.io 25 @io = case @options.io 26 when Hash 27 @options.io[origin.authority] 28 else 29 @options.io 30 end 31 raise Error, "Given IO objects do not match the request authority" unless @io 32 33 _, _, _, @ip = @io.addr 34 @addresses << @ip 35 @keep_open = true 36 @state = :connected 37 else 38 add_addresses(addresses) 39 end 40 @ip_index = @addresses.size - 1 41 end
Public Instance methods
add_addresses(addrs)
[show source]
# File lib/httpx/io/tcp.rb 47 def add_addresses(addrs) 48 return if addrs.empty? 49 50 addrs = addrs.map { |addr| addr.is_a?(IPAddr) ? addr : IPAddr.new(addr) } 51 52 ip_index = @ip_index || (@addresses.size - 1) 53 if addrs.first.ipv6? 54 # should be the next in line 55 @addresses = [*@addresses[0, ip_index], *addrs, *@addresses[ip_index..-1]] 56 else 57 @addresses.unshift(*addrs) 58 @ip_index += addrs.size if @ip_index 59 end 60 end
close()
[show source]
# File lib/httpx/io/tcp.rb 139 def close 140 return if @keep_open || closed? 141 142 begin 143 @io.close 144 ensure 145 transition(:closed) 146 end 147 end
closed?()
[show source]
# File lib/httpx/io/tcp.rb 153 def closed? 154 @state == :idle || @state == :closed 155 end
connect()
[show source]
# File lib/httpx/io/tcp.rb 70 def connect 71 return unless closed? 72 73 if !@io || @io.closed? 74 transition(:idle) 75 @io = build_socket 76 end 77 try_connect 78 rescue Errno::ECONNREFUSED, 79 Errno::EADDRNOTAVAIL, 80 Errno::EHOSTUNREACH, 81 SocketError, 82 IOError => e 83 raise e if @ip_index <= 0 84 85 log { "failed connecting to #{@ip} (#{e.message}), trying next..." } 86 @ip_index -= 1 87 @io = build_socket 88 retry 89 rescue Errno::ETIMEDOUT => e 90 raise ConnectTimeoutError.new(@options.timeout[:connect_timeout], e.message) if @ip_index <= 0 91 92 log { "failed connecting to #{@ip} (#{e.message}), trying next..." } 93 @ip_index -= 1 94 @io = build_socket 95 retry 96 end
connected?()
[show source]
# File lib/httpx/io/tcp.rb 149 def connected? 150 @state == :connected 151 end
expired?()
[show source]
# File lib/httpx/io/tcp.rb 157 def expired? 158 # do not mess with external sockets 159 return false if @options.io 160 161 return true unless @addresses 162 163 resolver_addresses = Resolver.nolookup_resolve(@hostname) 164 165 (Array(resolver_addresses) & @addresses).empty? 166 end
inspect()
:nocov:
[show source]
# File lib/httpx/io/tcp.rb 169 def inspect 170 "#<#{self.class}: #{@ip}:#{@port} (state: #{@state})>" 171 end
read(size, buffer)
[show source]
# File lib/httpx/io/tcp.rb 116 def read(size, buffer) 117 ret = @io.read_nonblock(size, buffer, exception: false) 118 if ret == :wait_readable 119 buffer.clear 120 return 0 121 end 122 return if ret.nil? 123 124 log { "READ: #{buffer.bytesize} bytes..." } 125 buffer.bytesize 126 end
write(buffer)
[show source]
# File lib/httpx/io/tcp.rb 128 def write(buffer) 129 siz = @io.write_nonblock(buffer, exception: false) 130 return 0 if siz == :wait_writable 131 return if siz.nil? 132 133 log { "WRITE: #{siz} bytes..." } 134 135 buffer.shift!(siz) 136 siz 137 end