🐟

mTLSをrubyのFaradayを用いて実装してみた

2022/05/16に公開

目的

どうも、@yanteraです。
Ruby(Rails)+AWSの環境でmTLSをどうやって実現するのか考えてみました。

mTLSとは

簡単に言うと通信する場合に、サーバーとクライアントで相互認証を行う事らしいです。
クライアント側(サーバーにリクエストを送る側)にも証明書を用意する必要があります。
https://en.wikipedia.org/wiki/Mutual_authentication

コード

request.rb
class Request
  attr_reader :url

  def initialize
    @url = 'https://example.com'
  end

  def execute(payload = {})
    connection.post(url) do |request|
      request.body = payload
    end
  end

  def connection
    Faraday.new(url) do |builder|
      builder.headers['Content-Type'] = ''application/json'
      builder.headers['Authorization'] = ''
      builder.ssl.client_cert = client_cert
      builder.ssl.client_key = client_key
    end
  end

  def client_cert
    OpenSSL::X509::Certificate.new(File.read('ssl_client.crt'))
  end

  def client_key
    OpenSSL::PKey::RSA.new(File.read('ssl_client.key'))
  end
end
batch.rb
require_relative 'request'

Request.new.execute

ファイルの管理方法

  • S3から取得する場合
    • 重要なファイルを毎回ダウンロードするのは脆弱性含めてあまり良くないので、この方法はおすすめできません。
  • ParameterStore等を使用する
    • ParameterStoreを使用すれば、暗号化出来るオプションがあるのででセキュアに管理する事が可能です。
      • ParameterStoreに登録 -> 環境変数を呼び出す という流れが個人的には良さげでした。

環境変数を使う場合

下の例はRubyOnRailsですが、環境変数を使用しても問題なく動作しました。

  def client_cert
    OpenSSL::X509::Certificate.new(Rails.application.config.ssl_client_cert)
  end

  def client_key
    OpenSSL::PKey::RSA.new(Rails.application.config.ssl_client_key)
  end

所感

FaradayはデフォルトでSSL通信を行ってくれます。
ECS, FargateではParameterStoreから値を取得するという流れにしておけば、安心して実装出来るのではないかと感じました。

最後に

ここまで読んで下さりありがとうございます。
あくまで今回の実装は考えの一つだと思っています。良いアイディアや改善点があるなと思う方は意見を頂けますと幸いです。

GitHubで編集を提案

Discussion