LoginSignup
4
4

More than 5 years have passed since last update.

[Grails]アプリケーションにTwitterでのログイン機能を実装する

Posted at

未完

下書きが埋まってしまったのでとりあえず公開。

参考:
http://grails.org/plugin/spring-security-core
http://grails.org/plugin/spring-security-twitter
http://grails.hatenablog.com/entry/2013/05/22/163539

なお、アプリケーション名とパッケージ名は socialtest という前提。

以下のプラグインをインストール

grails-app/conf/BuildConfig.groovy
    plugins {
        compile ":spring-security-core:2.0-RC2"
        compile ":spring-security-twitter:0.6"
    }

spring-security-twitterspring-security-core に依存している。
spring-security-coreに関しては以前使い方をメモしている。

grails cleanを実行。
grails compile を実行。
そうすると以下のようなメッセージが表示され、 spring-security-corespring-security-twitter がインストールされる。

| Installed plugin spring-security-core-2.0-RC2

*******************************************************
* You've installed the Spring Security Core plugin.   *
*                                                     *
* Next run the "s2-quickstart" script to initialize   *
* Spring Security and create your domain classes.     *
*                                                     *
*******************************************************

| Installed plugin spring-security-twitter-0.6

**************************************************************
* You've installed the Spring Security Twitter plugin.       *
*                                                            *
* Next run the "s2-init-twitter" script to configure plugin. *
*                                                            *
**************************************************************

以下のコマンドを実行して、 spring-security-core 用のドメインを生成する。

grails s2-quickstart socialtest Person Role

以下のようなメッセージが表示される。

*******************************************************
* Created security-related domain classes. Your       *
* grails-app/conf/Config.groovy has been updated with *
* the class names of the configured domain classes;   *
* please verify that the values are correct.          *
*******************************************************

続いてインストール時に出力されていたように s2-init-twitterを使ってみるが・・・

Creating app based on configuration:
consumerKey = CONSUMER_KEY
consumerSecret = CONSUMER_KEY
language = en_US
button = [text:Login with Twitter]
popup = false
autoCreate = [active:true, roles:[ROLE_USER, ROLE_TWITTER]]
filter = [processUrl:/j_spring_twitter_security_check, processPopupUrl:/twitterAuth/popup]
domain = [classname:TwitterUser, connectionPropertyName:user]
| Error Error executing script S2InitTwitter: java.lang.ClassNotFoundException: org.codehaus.groovy.grails.plugins.springsecurity.SpringSecurityUtils (Use --stacktrace to see the full trace)

例外発生。
これは、プラグインのS2InitTwitter.groovyの85行目にある、
def SpringSecurityUtils = classLoader.loadClass('org.codehaus.groovy.grails.plugins.springsecurity.SpringSecurityUtilsが原因。
このクラスは今はgrails.plugin.springsecurity.SpringSecurityUtilsにある。

公式ドキュメントのInstallationを読んでみると、s2-init-twitterなんていうコマンドは出てこずに、 BuildConfig.groovy にTwitterのコンシューマキーとコンシューマシークレットを記述してね、と書かれているのでそのとおりにする。(末尾に追記)

C
grails.plugin.springsecurity.twitter.consumerKey='コンシューマキー'
grails.plugin.springsecurity.twitter.consumerSecret='コンシューマシークレット'

次にTwitterユーザのドメインを生成する。
grails create-domain-class TwitterUser

中身は以下のようにする。

C
package socialtest

class TwitterUser {
    /**
     * Twitter Username (notice that it could be modified by user, Twitter allows that)
     */
    String username

    /**
     * Twitter User Id
     */
    Long twitterId

    /**
     * Twitter API token
     */
    String token

    /**
     * Twitter API secret
     */
    String tokenSecret

    /**
     * Related to main App User
     */
    static belongsTo = [user: Person]

    static constraints = {
        twitterId(unique: true, nullable: false)
        username(nullable: false, blank: false)
    }
}

この状態でrun-appを実行すると、以下のようなエラーが発生する。

| Running Grails application
Configuring Spring Security Core ...
... finished configuring Spring Security Core
Configuring Spring Security Twitter ...
... finished configuring Spring Security Twitter
Error |
2014-01-15 14:07:22,039 [localhost-startStop-1] ERROR twitter.DefaultTwitterAuthDao  - Can't find domain: TwitterUser

公式ドキュメントには、 TwitterUser というドメイン名がデフォルトで認識されると書かれているが、どうもちゃんと読み込んでくれないので、再度 Config.groovy を編集して、 TwitterUser をプラグインに認識させる。(末尾に追記)

grails-app/conf/Config.groovy
grails.plugin.springsecurity.twitter.consumerKey=  'コンシューマキー'
grails.plugin.springsecurity.twitter.consumerSecret= 'コンシューマシークレット'

// これを追記
grails.plugin.springsecurity.twitter.domain.classname= 'socialtest.TwitterUser'

index.gsp の</body>の直前などに以下を挿入。

grails-app/views/index.gsp
    <sec:ifLoggedIn>
        <div class="message">Authenticated</div>
        Hello <sec:username/>!
    </sec:ifLoggedIn>
    <sec:ifNotLoggedIn>
        <div class="message">Not authenticated</div>
        <twitterAuth:button />
    </sec:ifNotLoggedIn>

そしていよいよgrails run-appを実行してトップページにアクセスするとページにTwitterのログインリンクが表示されているはず。
基本的にはこれでTwitterのアカウントを使って、アプリケーションにログインする処理が全て完了となる。

リンクをカスタマイズしたい・・・

何かテキストすらカスタマイズできないんですね。
いろいろやり方はあると思うけど、結局TwitterにリンクするURLさえ分かればコッチのもの。
というで、プラグイン内の TwitterAuthTagLib.groovy を参考に自分でURLを取得してゴニョゴニョすればOK
例えば以下のとおり。

grails-app/views/index.gsp
<%
    def conf = grails.plugin.springsecurity.SpringSecurityUtils.securityConfig.twitter
    def url = conf.filter.processUrl
    String text = "Twitterへログインしたいか!?"
 %>
<g:link uri="${url}">${text.encodeAsHTML()}</g:link>

Twitterから帰ってくる時のURLは以下
http://localhost:8080/socialtest/j_spring_twitter_security_check?oauth_token=[oauthToken]&oauth_verifier=[oauthVerifier]

行き帰りも、かならずTwitterAuthFilterを経由する。
上記のURLは、TwitterAuthFilter#attemptAuthentication()のなかでブレークポイントを張っていて、Twitterから戻ってくる際に処理がとまると、Twitter側の画面の方で自動で移動しない場合はこちら、的なリンクを出してくれていて、それで判明。
上記のURLから、コールバック用のURLはTwitterで設定したものではなくて、spring-security-twitterが設定したものになっているのが分かる。

4
4
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
4
4