Twilio SendGridライブラリで送信リクエストとレスポンスを取得する方法 ~Ruby編~
- 2025年9月11日
- by SendGrid
- Category: 技術ネタ 機能・使い方
メール送信リクエストを実行したのに、ActivityやEvent Webhookにイベントが記録されていない!という経験はありませんか?イベントが発生しない主な原因として、Twilio SendGridに送信リクエストが届いていない可能性が考えられます。問題が発生した際に原因をしっかり特定できるよう、実際に送ったJSON形式の送信リクエストとそのHTTPレスポンスを必ずログに出力しましょう。
SMTPやWeb APIで送信する場合は、TelnetやcURLなどのツールによって簡単に送信リクエストとレスポンスが取得できるので、チュートリアルをお試しください。今回のブログでは、Ruby向けのSendGridライブラリ(以降、sendgrid-rubyと表記)における取得方法を紹介します。
今回は、Ruby 3.4.4で確認しました。利用したライブラリは以下のとおりです。
sendgrid-rubyを使った送信処理のサンプルコード
ライブラリはRubyのパッケージ管理ツールであるgemを利用して取得します。
gem install sendgrid-ruby dotenv base64
sendgrid-rubyを使った送信コードは次のとおりです。
require 'sendgrid-ruby' require 'dotenv/load' require 'json' include SendGrid mail = Mail.new # 差出人 mail.from = Email.new(email: 'kozotaro@example.com', name: '構造太郎') # 宛先 personalization = Personalization.new personalization.add_to(Email.new(email: 'kozohanako@example.com', name: '構造花子')) mail.add_personalization(personalization) # 件名 mail.subject = 'Rubyのライブラリを使ったメール送信' # 本文:テキストパート mail.add_content(Content.new( type: 'text/plain', value: <<~TEXT 構造さん お元気ですか。 TEXT )) # 本文:HTMLパート mail.add_content(Content.new( type: 'text/html', value: <<~HTML <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8"> <meta name="viewport" content="width=device-width, initial-scale=1, minimum-scale=1, maximum-scale=1"> </head> <body> <p>構造さん</p> <p>お元気ですか。</p> </body> </html> HTML )) # 送信リクエストの取得 request_body = mail.to_json puts "----- 送信リクエストを標準出力する -----" puts JSON.pretty_generate(request_body) # メールの送信 sg = API.new(api_key: ENV.fetch("SENDGRID_API_KEY")) response = sg.client.mail._('send').post(request_body: request_body) puts "----- レスポンスを標準出力する -----" puts "#{response.status_code}" puts "----------" response.headers.each do |key, value| puts "#{key}: #{Array(value).join(', ')}" end puts "----------" puts response.body # 成功時(202)は空
.envファイルにはダッシュボードで作成したAPIキーを定義します。
SENDGRID_API_KEY=SG.xxxxxxxxxxxxxxxxxxxxxxxxx
送信リクエストとレスポンスを取得する部分を詳しくみていきましょう。
送信リクエストの取得方法
送信リクエストは次の方法で取得できます。
# 送信リクエストの取得 request_body = mail.to_json puts "----- 送信リクエストを標準出力する -----" puts JSON.pretty_generate(request_body)
JSON.pretty_generateメソッドで整形して出力すると次のようになります。
----- 送信リクエストを標準出力する ----- { "from": { "email": "kozotaro@example.com", "name": "構造太郎" }, "subject": "Rubyのライブラリを使ったメール送信", "personalizations": [ { "to": [ { "email": "kozohanako@example.com", "name": "構造花子" } ] } ], "content": [ { "type": "text/plain", "value": "構造さん\nお元気ですか。\n" }, { "type": "text/html", "value": "<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Strict//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd\">\n<html xmlns=\"http://www.w3.org/1999/xhtml\">\n<head>\n <meta http-equiv=\"Content-Type\" content=\"text/html; charset=utf-8\">\n <meta name=\"viewport\" content=\"width=device-width, initial-scale=1, minimum-scale=1, maximum-scale=1\">\n</head>\n<body>\n <p>構造さん</p>\n <p>お元気ですか。</p>\n</body>\n</html> \n" } ] }
続いて、レスポンスを取得する方法について紹介します。
レスポンスの取得方法
送信リクエストに対するレスポンスは次の方法で取得します。
response = sg.client.mail._('send').post(request_body: request_body) puts "----- レスポンスを標準出力する -----" puts "#{response.status_code}" puts "----------" response.headers.each do |key, value| puts "#{key}: #{Array(value).join(', ')}" end puts "----------" puts response.body # 正常応答時(202)は空
原因を特定する際、特に大事なのはステータスコードとボディの情報です。正常応答(ステータスコードが2xx系)であれば、SendGridに送信リクエストが届いています。レスポンスがエラーの場合(ステータスコードが2xx系以外)は、SendGridに送信リクエストが届いていない、もしくは受け付けられていないので、bodyの「errors」で示されたメッセージをもとに原因を確認しましょう。
正常応答の場合
----- レスポンスを標準出力する ----- 202 ---------- server: nginx date: Wed, 27 Aug 2025 05:28:17 GMT content-length: 0 connection: close x-message-id: 17yjymcnS3GXcWPjX6kAyA access-control-allow-origin: https://sendgrid.api-docs.io access-control-allow-methods: POST access-control-allow-headers: Authorization, Content-Type, On-behalf-of, x-sg-elas-acl access-control-max-age: 600 x-no-cors-reason: https://sendgrid.com/docs/Classroom/Basics/API/cors.html strict-transport-security: max-age=31536000; includeSubDomains content-security-policy: frame-ancestors 'none' cache-control: no-cache x-content-type-options: no-sniff referrer-policy: strict-origin-when-cross-origin ----------
エラ-の場合(正しくないメールアドレス形式を指定した場合)
----- レスポンスを標準出力する ----- 400 ---------- server: nginx date: Wed, 27 Aug 2025 06:07:00 GMT content-type: application/json content-length: 204 connection: close access-control-allow-origin: https://sendgrid.api-docs.io access-control-allow-methods: POST access-control-allow-headers: Authorization, Content-Type, On-behalf-of, x-sg-elas-acl access-control-max-age: 600 x-no-cors-reason: https://sendgrid.com/docs/Classroom/Basics/API/cors.html strict-transport-security: max-age=31536000; includeSubDomains content-security-policy: frame-ancestors 'none' cache-control: no-cache x-content-type-options: no-sniff referrer-policy: strict-origin-when-cross-origin ---------- {"errors":[{"message":"Does not contain a valid address.","field":"personalizations.0.to.0.email","help":"http://sendgrid.com/docs/API_Reference/Web_API_v3/Mail/errors.html#message.personalizations.to"}]}
エラ-の場合(無効な認証情報が指定された場合)
----- レスポンスを標準出力する ----- 401 ---------- server: nginx date: Wed, 27 Aug 2025 06:08:51 GMT content-type: application/json content-length: 116 connection: close access-control-allow-origin: https://sendgrid.api-docs.io access-control-allow-methods: POST access-control-allow-headers: Authorization, Content-Type, On-behalf-of, x-sg-elas-acl access-control-max-age: 600 x-no-cors-reason: https://sendgrid.com/docs/Classroom/Basics/API/cors.html strict-transport-security: max-age=31536000; includeSubDomains content-security-policy: frame-ancestors 'none' cache-control: no-cache x-content-type-options: no-sniff referrer-policy: strict-origin-when-cross-origin ---------- {"errors":[{"message":"The provided authorization grant is invalid, expired, or revoked","field":null,"help":null}]}
レスポンスでエラーが返された場合は、送信リクエストに誤りがないかどうか確認しましょう。SendGridが用意するSandboxモードを利用することで、実際にメール送信を行うことなく、リクエストが正しいかどうかの検証ができます。
mail = Mail.new … # SandBoxModeで送信リクエストを検証する ms = MailSettings.new ms.sandbox_mode = SandBoxMode.new(enable: true) mail.mail_settings = ms # 送信リクエストの取得 request_body = mail.to_json # メールの送信 sg = API.new(api_key: ENV.fetch("SENDGRID_API_KEY")) response = sg.client.mail._('send').post(request_body: request_body) puts "----- レスポンスを標準出力する -----" puts "#{response.status_code}" puts "----------" response.headers.each do |key, value| puts "#{key}: #{Array(value).join(', ')}" end puts "----------" puts response.body # 成功時(202)は空
リクエストは正常に受け付けられたがメールへの差し込みがうまくいかない、指定したテンプレートが反映されないなど、お困りの場合は、弊社サポートチームがフォローいたします。送信リクエストとレスポンス、受信メールを添えてお問い合わせください。
コードの再確認をしましょう
SendGridでは送信後の状況をActivityやEvent Webhookで確認できるため、その手前の送信リクエストやレスポンスのログ出力を忘れがちです。今回のブログをきっかけに、しっかりログ出力できているかご自身のコードをもう一度見直してみてください。