RubyでHTTPS接続をしようとしたらエラーが出たのでメモ。
どうやら、Windows上でEasyInstallを使ってインストールしたrubyに特有の現象のようである。
環境:
OS: Windows 7
> ruby --version
ruby 2.2.4p230 (2015-12-16 revision 53155) [x64-mingw32]
#問題
サンプルコード
require 'open-uri'
url = 'https://example.com/'
html = open(url)
これを実行するとエラーが発生する。
C:/Ruby22-x64/lib/ruby/2.2.0/net/http.rb:923:in `connect': SSL_connect returned=1 errno=0 state=SSLv3 read server certificate B: certificate verify failed (OpenSSL::SSL::SSLError)
httpsなのがポイントで、httpだとエラーにならない。
#原因の特定
エラーメッセージで検索して以下のページを見つけたので、その通り調べてみる。
http://d.hatena.ne.jp/komiyak/20130508/1367993536
irbを立ち上げて以下の通り打ち込んだ。
irb(main):001:0> require 'openssl'
=> true
irb(main):002:0> p OpenSSL::X509::DEFAULT_CERT_FILE
"C:/Users/Justin/Projects/knap-build/var/knapsack/software/x64-windows/openssl/1
.0.1l/ssl/cert.pem"
=> "C:/Users/Justin/Projects/knap-build/var/knapsack/software/x64-windows/openss
l/1.0.1l/ssl/cert.pem"
上記のフォルダに証明書cert.pemがあることになっているが……いや、そんなフォルダはないぞ。
「SSL証明書のファイルがこの場所にあると言われているが、実際には証明書が存在しない」という状態なのでエラーが出ている。
#解決法
https://mcrn.jp/blog/2015/10/28/205049.html に記載の通りに、certified gemを導入した。
証明書のあるフォルダの情報は、dll内に埋め込まれているから書き換えるのは無理みたいだ。
- gem install certified を実行する。
- コード内に
require 'certified'
を追加する。
以上の変更をすると、正常に動作する。
余談だが、http://qiita.com/akaneko3/items/a162def655ce791e356f にも同様の事例があった。ただしこの記事の場合は、
"C:/Users/Luis/Code/luislavena/knap-build/var/knapsack/software/x64-windows/openssl/1.0.0o/ssl/cert.pem"
というフォルダが指定されていた。JustinじゃなくてLuisの場合もあるらしい。EasyInstallでインストールした時期の違いだろうか。
(どちらも、EasyInstallの開発者の名前らしい)
Qiita初投稿なので、拙いですが大目に見ていただければ幸い。