portforward といっても、SSHではないです。念のため。
require 'socket'
LISTEN_PORT = 10080
CONNECT_ADDR = 'localhost'
CONNECT_PORT = 80
BUFSIZE = 4096
gs = TCPServer.open(LISTEN_PORT)
puts "listen port: #{gs.addr[1]}"
trap(:INT, "exit")
while true
Thread.new(gs.accept) { |s|
puts "accept: #{s.object_id}, remote: #{s.peeraddr[3]}:#{s.peeraddr[1]}"
TCPSocket.open(CONNECT_ADDR, CONNECT_PORT) { |gc|
th1 = Thread.new {
str = ''
while true
begin
gc.readpartial(BUFSIZE, str)
s.write(str)
rescue
break
end
end
}
str = ''
while true
begin
s.readpartial(BUFSIZE, str)
gc.write(str)
rescue
break
end
end
}
puts "closed: #{s.object_id}"
}
end
少し短く書いてみた:
require 'socket'
LISTEN_PORT = 10080
CONNECT_ADDR = 'localhost'
CONNECT_PORT = 80
BUFSIZE = 4096
gs = TCPServer.open(LISTEN_PORT)
puts "listen port: #{gs.addr[1]}"
trap(:INT, "exit")
while true
Thread.new(gs.accept) { |s|
puts "accept: #{s.object_id}, remote: #{s.peeraddr[3]}:#{s.peeraddr[1]}"
gc = TCPSocket.open(CONNECT_ADDR, CONNECT_PORT)
th1 = Thread.new {
s.write(gc.readpartial(BUFSIZE)) while true
}
th2 = Thread.new{
gc.write(s.readpartial(BUFSIZE)) while true
}
th1.join rescue nil
th2.join rescue nil
puts "closed: #{s.object_id}"
}
end
もっといい書き方もありそうだけど、とりあえずこんな感じかな。