それマグで!

知識はカップより、マグでゆっくり頂きます。 takuya_1stのブログ

習慣に早くから配慮した者は、 おそらく人生の実りも大きい。

Google アカウントをOAuthして、アクセストークンを取得する

gmail を送信するために、OAuthで権限をもらう。

GmailSMTPを使うには、OAuth利用が必要になる。 less secure apps ( 安全性の低いアプリ) は非推奨になった。

git clone git@github.com:takuya/ruby-oauth-google-gmail.git
bundle install 
bundle exec ruby oauth-gmail-localhost.rb

準備

  • OAuthについて
  • client_secret
  • access_token
  • refresh_token

OAuth について

Google のアプリはOAuthで使うのが基本形になってる。

OAuthは3者間認証。

ユーザ・Google・アプリの三者間で信頼関係を作る。

アプリは、ユーザーに許可を求める。 ユーザーはGoogleにからアプリへの許可を出していいか訊かれる ユーザーが許可するとアプリに許可が出る。

単純だけど、中央にGoogleがいるのでそこで許可設定・権限設定が可能になる。

ユーザの代理をしたいアプリを作る。

アプリ識別 client_secret/client_id 
スコープ https://mail.google.com

このアプリに、ユーザから許可を出す

アクセス用一時パスワード access_token 
一時パスワード発行用キー refresh_token

アプリは、ユーザからAccess Tokenを貰って代理として振る舞う。Access Token はGoogle から発行される。Google はユーザの許可をとってアクセス権を付与して発行する。

Access Token は3600秒の時間制限。有効期限が切れたら、Refreshトークンを使って再取得する。再取得の際は許可済みなので、ユーザーの許可はいらない

ユーザが許可を取り消していたら、refresh token を使った再取得で失敗する。アプリはAccess Token を取れないので、ユーザの代理はできなくなる。よってアプリから権限を剥奪できる。

スコープは権限。スコープでユーザからアプリに許可する権限範囲を決める。

アプリのClient Secret の発行

Google Console にアクセスして、アプリを作る。

アプリの作成手順は、次の通り

  1. プロジェクトを作る
  2. 使いたいAPIを有効にする
  3. OAuth 同意画面を作る
  4. アプリIDを作る

アプリのIDはClient IDと呼ばれる。ここではプログラム(シェルスクリプト)からアクセスするのでデスクトップクライアントを作る。

プロジェクトを作る

名前を決めるだけでいい。スコープはOAuth時に指定できるし、後で変更できるので空欄でいい。

使いたいAPIを有効にする。

ライブラリから使いたいAPIGmailを指定する。指定なしでOAuthしてもメールアドレス取得ができたはず。

OAuth同意画面。

「外部」「内部」を選べる。Gsuiteの場合は内部を選んでおくと無難。

テスト設定は、テストユーザを作ってテスト設定にしておくと無難。自分だけが使いたいときは基本的にテスト。

ここの設定をミスると、同意画面表示でエラーになるので、権限(テスト・内部・外部)に注意する。

JSONの取得(アプリIDの取得)

アプリを作るとclient_secret_xxxxx.jsonが作成されるのでダウンロードする。

ダウンロードは後から行えないので注意する。

あとでダウンロードしたらClient_Secretが含まれないので、意味がない

ダウンロードしそこねたら、シークレットの再生成を押してJSONを再発行する。

手作業でコピペしてもいいけど、JSONは手作業で編集するとミスが多いのでダウンロードするほうが無難。

ユーザ・ログインをしてキーをもらう

サンプルを元に、スクリプトを作っておいたので、ログインしてアプリにユーザのアクセストークンを渡す。

git clone git@github.com:takuya/ruby-oauth-google-gmail.git
bundle install 
bundle exec ruby oauth-gmail-localhost.rb

アクセストークンは、 tokens.yml に保存する。キーはメールアドレスなので保存用にユーザ名が必要。

トークンを使ってアクセスする

たとえば、Gmail Api にアクセスしてラベル一覧を取得する。

puts "####"
puts "Test Access Gmail Api as User(#{user_id})"
service = Google::Apis::GmailV1::GmailService.new
service.client_options.application_name = APPLICATION_NAME
service.authorization = credentials
result = service.list_user_labels user_id
puts "Get Gmail Labels"
puts "Labels:"
puts "No labels found" if result.labels.empty?
result.labels.each { |label| puts "- #{label.name}" }

これでラベル一覧が取得できればOK

リフレッシュトーク

トークンの更新は自動的に行われる。

refresh token を指定して、 credentials.refresh! を呼び出せば、アクセストークンが更新されて保存される。

有効期限関係なく、何度更新しても大丈夫なので、気にせず使える。

メモ

認証・認可

この記事は、「敢えて」認証認可という用語を使っていません。認可という用語は日常語から離れてているため、イメージが湧きづらい語だからです。また認証も使っていません。認証は日常で使われすぎていて、意味範囲が広すぎて理解の妨げになるためです。

認証では、誰が誰の何を認証するかを含めて語らなくてはいけません。ログインで十分です。

認可では、誰が誰の権限を認可するかを含めて語らなくてはいけません。権限と許可で十分です。

なぜなら、Google , Google アカウント、アプリの3者しか登場人物がおらず、イメージは湧きやすいからです。日常語で意味が曖昧な熟語をあえて使う必要はないと考えます。

参考資料