TLS1.2 サーバ

ちょっと TLS1.2 での通信を確かめることになって、たしかに TLS1.2 でしゃべってる HTPPSサーバが欲しかった。

ruby -r webrick/https -e 'WEBrick::HTTPServer.new(:Port=>3001,:DocumentRoot=>"./",:SSLEnable=>true,:SSLCertName=>[["CN", "foobar"]]).tap{|s|s.ssl_context.ssl_version=:TLSv1_2}.start'

取敢えず簡便なものが欲しいのでワンライナーで。

Port 指定注意、無しだと 80番を取りに行って駄目ならエラーになる、駄目じゃないときはそれはそれで危ないときなので注意。大体ドキュメントルートとして実行場所のローカルファイルさらしてる訳で、ローカルだけで見るようにしましょう。

SSL/TLS 用なので webrick/https library webrick/https (Ruby 2.5.0) をリクワイアする、これで webrick 自体もリクワイアされる。/https なしでも SSLEnable 指定は通るが別に SSL/TLS にはならない、設定値のハッシュにそのキーが追加されるだけということだろう。

webrick/httpsクワイアして :SSLEnable=>true にすると最低限 :SSLCertName も指定しないとエラーになる、これは
class OpenSSL::X509::Name (Ruby 2.5.0) の指定になるので、配列の配列が必要、最低限の指定ならまあ ”CN” にしときましょう。

そしてプロトコルを TLS1.2 に限りたいので
class OpenSSL::SSL::SSLContext (Ruby 2.5.0) #ssl_version= で指定する、選択肢は
constant OpenSSL::SSL::SSLContext::METHODS (Ruby 2.5.0) にある。このリストに :TLSv1_2 がない環境だとちょっと悲しい。ここで
instance method Object#tap (Ruby 2.5.0) を使ってる、HTTPServer.new の引数でなんとかならないかと思ったけど難しい、ここではハッシュ引数にしてるが、
constant WEBrick::Config::HTTP (Ruby 2.5.0) を渡してもいい、そのときは WEBrick::HTTPServer.new(WEBrick::Config::HTTP.tap{|c|c[:Port],c[:SSLEnable],c[:SSLCertName]=3001,true,\[\["CN","foobar"\]\]}) とでもするのだろうか、それで #ssl_context(OpenSSL::SSL::SSLContext) に触れないか。

最初のワンライナーに戻る。これを実行して適宜ブラウザからアクセスすると確かに TLS1.2 をしゃべってる、ほかのプロトコルではしゃべらない。ブラウザ表示ページのプロパティや、ブラウザの設定で使うプロトコルを調整したりで確かめた、 ssl_version=:TLSv1_2 のところも :TLSv1_1 やさらに下位にしてみたり。

あと、この辺のスクリプトはそこそこ古い Ruby でも動く、なのでハッシュ引数は古い記法で書いてる、まあそんな環境ではプロトコルの選択肢に :TLSv1_2 が出てこない訳だ。