RubyでHTTPサーバを立てる①
主にこちらの内容の翻訳になります
また、この投稿の続きを書きました。
RubyでHTTPサーバを立てる② - be-kan's blog
内容的には、以下の4つです。
・TCPサーバを立てる
・TCPクライアントを作成する
・HTTPサーバを立てる
・HTTPサーバの中でRack Appを動かす
当内容、GitHubにソースコードをあげています。
https://github.com/be-kan/http_server_in_ruby/blob/master/README.md
TCPサーバを立てる
require 'socket' server = TCPServer.new(5678) while session = server.accept session.puts "hello time is #{Time.now}" session.close end
上記のコードでは、ポート5678番を開けて、クライアントから接続されるのを待っています。
クライアントから接続があると、クライアントにメッセージを送り、接続を切って次の接続を待つ、というようなコードになっています。
TCPクライアントを作成する
equire 'socket' server = TCPSocket.new 'localhost', 5678 while line = server.gets puts line end server.close
上記のコードでは、ポート5678番に接続するクライアントを作成しています。
サーバに接続すると、先ほどのコードによりクライアントに「hello~」というメッセージが送信されており(つまりクライアントはサーバからそのメッセージを受け取り)、それを表示し、サーバとの接続を切ります。
試しにやってみましょう。
$ ruby tcp_server.rb
でサーバを立てた後、
$ ruby tcp_client.rb
とすると、メッセージが返って来るはずです!
HTTPサーバを立てる。
require 'socket' server = TCPServer.new 5678 while session = server.accept request = session.gets puts request session.print "HTTP/1.1 200\r\n" session.print "Content-Type: text/html\r\n" session.print "\r\n" session.print "Hello world! The time is #{Time.now}" session.close end
HTTPサーバと言っても、TCPサーバとほとんど変わりません。
異なるのは、HTTPサーバではHTTPプロトコルでメッセージをやり取りする、というところです。
上記のコードでは、そのプロトコル(通信の約束事・フォーマットのようなもの)を手動で書いています。
HTTPサーバの中でRack Appを動かす
require 'socket' require 'rack' require 'rack/lobster' app = Rack::Lobster.new server = TCPServer.new 5678 while session = server.accept request = session.gets puts request method, full_path = request.split(' ') path, query = full_path.split('?') status, headers, body = app.call({ 'REQUEST_METHOD' => method, 'PATH_INFO' => path, 'QUERY_STRING' => query }) session.print "HTTP/1.1 #{status}\r\n" headers.each do |key, value| session.print "#{key}: #{value}\r\n" end session.print "\r\n" body.each do |part| session.print part end session.close end
このサーバをブラウザで開くと、以下のような画面になるはずです。
「flip!」をクリックすると、TCPサーバにリクエストが送られます。TCPサーバは、送られてきたリクエストをmethod, path, queryに分解します。
そして分解したmethodなどを、Rack Appに送り、Rack Appからstatus, headers, bodyを受け取ります。
実際に送られたパラメータの値は以下です。
{ 'REQUEST_METHOD' => 'GET', 'PATH_INFO' => '/', 'QUERY_STRING' => '?flip=left' }
そして、TCPサーバは、Rackから受け取った情報を、クライアント側に送っています。
次回は、HTTPサーバの中でRailsを動かしてみたいと思います!