2014年2月23日日曜日

Golang Cafe #18を開催しました。

Golang Cafe #18を開催しました。

今回は、goauth2というライブラリを使って、GoogleのAPIを実行するというのが
テーマでした。

サンプルコードは、githubにありますので、そちらをごらんください。
(ディレクトリを別にしていて、goauth2sampleに入っています)

今回は、サンプルの解説と、installedAppsの認証を1回で完結させるというのをやりました。
installedAppsの認証を1回にするというのは、oauth2の認証(installedApps)では、最初にユーザに承認させることになっていて、承認後のコードをアプリケーションに教えてあげる必要があります。サンプルでは、引数で承認コードを指定するようにしていますが、その引数での指定をやめて、Webアプリのように承認後、継続する処理に変えるというのにチャレンジしました。

サンプルの解説からですが、まず、calendarsampleは、CalendarAPIを実行し、カレンダーリストを取得するサンプルです。

認証の設定をいれる

最初に、認証の設定を保持するConfig構造体にClientID、Secretなど必要な設定をいれます。
config := &oauth.Config{
       ClientId:     auth.ClientID,
       ClientSecret: auth.Secret,
       RedirectURL:  auth.RedirectUrl,
       Scope:        scope,
       AuthURL:      request_token_url,
       TokenURL:     auth_token_url,
       TokenCache:   oauth.CacheFile(cachefile),
}

ClientID、Secret、RedirectUrlはGoogle Developers Consoleでアプリケーションキーを取得したものを設定します。(私のサンプルはgithubにキーが上がってしまうと困るので、最初は入力させて、以降は、ファイルに保存したものを利用するコードになっています。)

ScopeはAPIによって指定するものが違うので、APIのドキュメントを参照して下さい。
TokenCacheは一度認証した時にキャッシュとしてファイルに保存され、ファイルがある間で、有効期限が過ぎていなければファイルの認証トークンを使ってAPIを実行するようになっています。

キャッシュから認証情報を取得する

次に、キャッシュからトークンを取得します。

    _, err = config.TokenCache.Token()
if err != nil {
    // キャッシュなし

    // 認証コードなし=>ブラウザで認証させるためにURLを出力
    if code == "" {
        url := config.AuthCodeURL("")
        fmt.Println("ブラウザで以下のURLにアクセスし、認証して下さい。")
        fmt.Println(url)
        return
    }

    // 認証トークンを取得する。(取得後、キャッシュへ)
    _, err = transport.Exchange(code)
    if err != nil {
        fmt.Println("Exchange: ", err)
        return
    }

}

キャッシュファイルがない場合は、errorが返されるので、認証コードを取得するURLを生成し、コードを取得します。(ここで、一度プログラムを終了させる。)
もし、引数で指定してあれば、transport.Exchange(コード)でExchangeし、認証トークンを取得します。

APIを実行する

APIを実行します。oauth2のパッケージで認証トークンを持っているので、何も考えずにGet()すれば、レスポンスが返ってきます。

// Calendar APIにアクセス
r, err := transport.Client().Get(request_url)

思ったよりも簡単だった。

やることがたくさんあるわけではなく、簡単にアクセスできることはわかりましたが、承認キーを渡してもらう部分を何とかしないと、installedAppsでは使えない気がします。(これをGAEのappcfg.pyは上手にやっているらしく、どうやっているのかソースを読んで解説して貰う必要がありそうです。+Ryuji IwataさんがPythonを知っているので今度読んで、解説してもらおうという話にもなりました。)
+Takanobu Haginoさんは、goroutineでWebサーバを起動(http.ListenAndServe())して、リダイレクト先をlocalhostにするという荒業を実現していました。私も挑戦したのですができなかったので、そのコードの解説はそちらに譲ることにします。)

次回は、2013の12個のベストプラクティスを読む予定です。

追記:
それから、今回無断欠席をされた方がいらっしゃったので、無断欠席に関する注意点を増やしました。申込をして、来られないのは仕方がないと思いますが、何の連絡も無いのはどうかと思いますので、次回から、そういう方は管理者権限で参加取り消しをする可能性があります。