一部で話題のIKEAorDEATHをGrailsのコントローラだけで作ってみた
http://ikeaordeath.com/ というサイト、ご存知ですか?IKEAで販売されてるアイテムとデスメタルバンドのバンド名、何がどっちかの2択を出してるサイトです。
ここを見てて、Grailsのコントローラだけでもこういう動きするページ作れそうだな、と思って作ってみました。Grailsで create-controller
して、こんなコードを。
package ikeametal class QuestionController { List ikeas = ["Vittsjö","Klubbo","Bastig","Boholmen","Grundtal","Dåtid","Samsplet","Skogaby","Adde","Nyvoll","Strandmon","Krokig","Vyssa Skont","Melltorp","Vridvinge"] List metals = ["Akercocke","Einherjer","Sargeist","Taake","Ensiferum","Midnattsol","Turisas","Thaurorod","Sikth","Eluveitie","Månegarm","Kovenant","Korpiklaani"] Random rand = new Random() static Integer total = 0 static Integer correct = 0 def index() { List joined = metals + ikeas def picked = joined[ rand.nextInt(joined.size()) ] render "<H1>$picked</H1> is IKEA or METAL ?" + g.link(action:"ikea",id:picked){"<H2>IKEA</H2>"} + g.link(action:"metal",id:picked){"<H2>METAL</H2>"} + "( $correct / $total )" } def metal() { total ++ def ans = metals.contains(params.id) ? "<H1>Right!</H1> ${params.id} is Metal Band.<!--${++correct}-->" : "<H1>Wrong.</H1> ${params.id} is IKEA Item." ans += g.link(action:"index"){"<H2>Next</H2>"}+"( $correct / $total )" render ans } def ikea() { total ++ def ans = ikeas.contains(params.id) ? "<H1>Right!</H1> ${params.id} is IKEA Item.<!--${++correct}-->" : "<H1>Wrong.</H1> ${params.id} is Metal Band." ans += g.link(action:"index"){"<H2>Next</H2>"}+"( $correct / $total )" render ans } }
Gistにも置いてあるので、見づらい方はそちらを見てください。
リスト ikeas
、 metals
はそれぞれイケア、メタルの出題リストです。 total
と correct
はそれぞれ出題総数と正解数ですね。コントローラだけで作るために、staticにしています。
アクション index
は出題画面で、イケアの場合は ikea
アクションに、メタルの場合は metal
アクションに飛ばします。このとき、 id
に選択した要素の文字列を入れておき、飛んだ先のアクションで params.id
で拾えるようにしておきます。
アクション metal
、 ikea
はそれぞれ正解の判定をするアクションで、三項演算子 ?
を使って判定しています。 ++correct
するためにHTMLのコメントを使ったり、ちょっと無理やりですね。 index
アクションから飛ばすパラメータを増やせば metal
アクションと ikea
アクションは分ける必要も無くなるので、気になる方はちょっと考えてみてください。
こんな風に、Grailsはちょっとしたお遊びプログラムを走らせるWebアプリケーションフレームワークとして使うこともできるんですよ!
Grailsでrun-scriptコマンドを使って任意のGroovyスクリプトを走らせ、その中でServiceを使う
Grailsには、create-script
コマンドを使ってscriptsディレクトリ配下にGantスクリプトを作り、任意のGrailsコマンドを追加する機能があります。
scriptsディレクトリ配下のGantスクリプトはGrailsコマンドとして実行可能になるため、 scripts/MyScript.groovy
を作ったら、 grails my-script
コマンドとして実行できますね。
では、run-script
コマンドはご存知でしょうか?
このコマンドは、任意のGroovyスクリプトを、Grailsのコンテキストを与えた上で実行可能にするコマンドです。Grails 1.3.6の頃からあるようです。
このコマンドは
> grails run-script src/groovy/package/MyScript.groovy
のように、実行するGroovyスクリプトを指定して実行します。このGroovyスクリプトの中では、Grailsのドメインクラスをそのまま利用することができます。
new MyDomain(str:"テストです").save() println MyDomain.count()
では、Serviceを使うにはどうするか?run-script
したときには、 applicationContext
が無くて applicationContext.getBean('myService')
みたいなことをさせて貰えません。ここはGrails本体の scripts/RunScript.groovy
を覗いてみましょう。
def shell = new GroovyShell(classLoader, new Binding(ctx: appCtx, grailsApplication: grailsApp))
なんていう行がありますね。どうやらrun-script
のときのApplicationContextは変数ctx
に入っているようです。
def my = ctx.getBean('myService') my.method()
これでServiceも呼べますね!GrailsApplicationが必要なら grailsApplication
に入っているので、これも覚えておくと良いでしょう。Gantを書くより手軽に定型的な処理を書き出しておけるので、いろいろと使い道がありそうです。
Yokohama.groovy #15 に参加してきた #yokohamagroovy #mattarigrails
たまには参加報告書きましょう。
- connpass - 2013/05/19 Yokohama.groovy #15 #yokohamagroovy #mattarigrails
- Togetter - 2013/05/19 Yokohama.groovy #15 #yokohamagroovy #mattarigrails
先月の Yokohama.groovy #14 から、 #mattarigrails と称してGrailsをもくもくする集団として #yokohamagroovy との合同開催で横浜タネマキさんにお邪魔しております。
参加メンバーにもよりますが、必ずしもGrailsやG*に縛られての作業でも無かったようです。AndroidアプリのOAuth連携をつくってみたり、デザイン系の作業をしたりしてる人もいました。
GroovyやGrailsなど、G*エコシステムに興味がある方、ゆる~く学びの時間を共有しに来てみませんか?是非是非お待ちしております。
今回の僕のテーマは、GrailsでのOAuth連携でした。
spring-security-oauth プラグイン
以前このプラグインでTumblrのアカウント連携をやったことがあったので、サクサクいけるだろ、なんて2時間ほどもくもくしてみたんですが、どうにもうまくいきません。あれ…おかしいな…とか言いながら見切りをつけて次に。
spring-security-twitter プラグイン
確かにドキュメントの通りにあれやこれややってあげれば動く。動くんだけどそこに至るまでキッチリ引っかかる罠、罠。主に s2-init-twitter
コマンドなんですが、動作にいくつか問題がありました。
Config.groovy
に追加される設定値が誤っている- ファイルのコピーに失敗する
- コピーされた spring-security-twitter.messages.properties が空
- 生成されるドメインクラス TwitterUser が動かない
んーいけてない。これぜんぶ修正したらだいぶ使いやすいんじゃないですかね。ついでにAPI経由でのPostの方法も調べましょう。とか言ったところでこの日の作業は時間切れ終了。
無事mergeされ spring-security-twitter プラグインが 0.5 から 0.5.2 にバージョンアップするに至り。
Twitter連携するWebアプリなんてあっという間にできるよ。そう、Grailsのspring-security-twitterプラグインならね!に至る。
といった流れだったのでございました。
次回 Yokohama.groovy #16 with #mattarigrails
2013/06/23(日) 13:30~19:00 横浜タネマキにて開催予定です。興味ある方はぜひご参加どうぞ~。
Windows PowerShell から Gradle wrapper (gradlew) を叩くときにはオプションのクオートをしよう
何回やっても忘れるのでメモ。。
> ./gradlew -q -Ddisable.groovydocs=true -Dgrails.home=C:\GGTS\grails-2.1.5 clean publishGuide_ja
Windows PowerShell からこんな gradlew
コマンドを叩くと
FAILURE: Could not determine which tasks to execute. * What went wrong: Task '.groovydocs=true' not found in root project 'grails-doc'.
とか
FAILURE: Could not determine which tasks to execute. * What went wrong: Project '.home=C' not found in root project 'grails-doc'.
みたいなことになります。一瞬エッΣ(゚Д゚)ってなるかもしれませんが、オプションをクオートしてやると通ります。
> ./gradlew -q "-Ddisable.groovydocs=true" "-Dgrails.home=C:\GGTS\grails-2.1.5" clean publishGuide_ja
> ./gradlew -q -D"disable.groovydocs=true" -D"grails.home=C:\GGTS\grails-2.1.5" clean publishGuide_ja
どちらかのクオートで通りました。
Twitter連携するWebアプリなんてあっという間にできるよ。そう、Grailsのspring-security-twitterプラグインならね!
pull requestがmergeされてプラグインが更新されて不便なところが解消された記念に紹介します。
- spring-security-twitter プラグインを導入する
- Role をつくる
- GSP に連携ボタンを設置する
たったこれだけです。
spring-security-twitter プラグインを導入する
http://grails.org/plugin/spring-security-twitter に書いてある通り、 BuildConfig.groovy
の repositories
ブロックに
mavenRepo "http://maven.springframework.org/release/"
を、 plugins
ブロックに
compile ":spring-security-twitter:0.5.2"
を、それぞれ追記します。そのあと refresh-dependencies
コマンドで、追記したプラグインの依存性を解決します。
grails> refresh-dependencies | Loading Grails 2.1.5 | Configuring classpath. | Environment set to development.... | Installing zip spring-security-twitter-0.5.2.zip..... | Installed plugin spring-security-twitter-0.5.2 | Resolving plugin JAR dependencies ************************************************************** * You've installed the Spring Security Twitter plugin. * * * * Next run the "s2-init-twitter" script to configure plugin. * * * ************************************************************** | Resolving plugin JAR dependencies..... | Installing zip spring-security-core-1.2.7.2.zip..... | Installed plugin spring-security-core-1.2.7.2 | Resolving plugin JAR dependencies ******************************************************* * You've installed the Spring Security Core plugin. * * * * Next run the "s2-quickstart" script to initialize * * Spring Security and create your domain classes. * * * ******************************************************* | Resolving plugin JAR dependencies... | Dependencies refreshed.
みたいな感じで、Mavenリポジトリからダウンロードしてプラグインのインストールをしてくれます。丁寧にインストラクションを出してくれてるので、まずは s2-quickstart
コマンドから打ちましょう。これは、spring-security-twitterプラグインのベースとなっているspring-security-coreプラグインのコマンドです。
grails> s2-quickstart jp.myapp User Role
これで、プラグインで扱うユーザとロールのドメインクラスができあがります。 jp.myapp
っていうのはpackage名ですね。自分のアプリで任意に決めて付けてください。次に
grails> s2-init-twitter (中略) > Enter your Twitter API Key twitter > Enter your Twitter API Consumer Key sOMeTwiTTErcoNSumERKEy > Enter your Twitter API Consumer Secret sOMeTwiTTErcoNSumERSEcRETTwiTTErcoNSumERS
です。 API Key というのを聞いてきますが、任意の文字列で構いません。 Consumer Key と Consumer Secret は https://dev.twitter.com/ で払い出したものを使いましょう。
Role をつくる
Role が無くても動作はするのですが、「認証を通ったか通ってないか」で画面を振り分けたりするときにこれが無いと不便なので、作っておきましょう。 BootStrap.groovy
に
import jp.myapp.Role class BootStrap { def init = { servletContext -> Role.findByAuthority("ROLE_USER") ?: new Role(authority:"ROLE_USER").save() Role.findByAuthority("ROLE_TWITTER") ?: new Role(authority:"ROLE_TWITTER").save() } }
みたいな感じで書いておけばOKです。ROLE_USERとROLE_TWITTERが存在しなかったら作って保存する、というだけのコードです。 ?:
はエルビス演算子ですね。2つ作ってる理由は、spring-security-twitterプラグインがデフォルトでその2つのロールを利用するからです。必要であれば設定を変えることもできます。
GSP に連携ボタンを設置する
こんなGSPコードを index.gsp
の末尾のほうに追記するだけで、連携を確認できます。
<sec:ifLoggedIn> <div class="message">Authenticated. Hello <sec:username/>!</div> </sec:ifLoggedIn> <sec:ifNotLoggedIn> <div class="message">Not authenticated. <twitterAuth:button /> </div> </sec:ifNotLoggedIn>
run-app
して動作を確認してみましょう。実行したアプリを開くと、こんな画面が出るので「Connect with Twitter」をクリックしましょう。
いつものTwitter連携画面が出るので、承認してあげます。
すると、元の画面に戻りますが、自分のTwitterIDでメッセージが表示されますね!
内部では、TwitterIDでアカウントが生成され、そのアカウントでのログイン処理が行われています。つまり、自分の作ったWebアプリ用のユーザ認証の仕組みと、そのTwitter連携ができているのです。
TwitterのAPIを使って投稿してみる
ここまでやったんだから、投稿についても試してみましょう。
まず、デフォルトパッケージで生成されている TwitterUser
クラスを自分のpackageに移動し、 TwitterTemplate
を取得するメソッドを追加します。こんな感じになりますね。
package jp.myapp import org.springframework.social.twitter.api.impl.TwitterTemplate; class TwitterUser { Long twitterId String username String tokenSecret String token static belongsTo = [user: User] static constraints = { twitterId(unique: true, nullable: false) username(nullable: false, blank: false) } TwitterTemplate getTwitterTemplate(config){ new TwitterTemplate( config.grails.plugins.springsecurity.twitter.consumerKey, config.grails.plugins.springsecurity.twitter.consumerSecret, token, tokenSecret ) } }
TwitterTemplate
はspring-social-twitterに含まれるクラスですね。もちろんimportもしてあげます。
あとは、つぶやくためのコントローラを作ってあげればよいです。こんな感じに書けますね。
package jp.myapp import grails.plugins.springsecurity.SpringSecurityService import org.springframework.social.twitter.api.impl.TwitterTemplate class TweetController { def springSecurityService def index() { def tw = TwitterUser.findByUsername( springSecurityService.getCurrentUser().username ).getTwitterTemplate(grailsApplication.config) def st = tw.timelineOperations().updateStatus("#Grails のspring-security-twitterプラグインを使ってつぶやいています。 #yokohamagroovy #mattarigrails") render st.getCreatedAt() } }
springSecurityService
からログインしているユーザを取得し、そのユーザ名を元に TwitterTemplate
を取得し、 TimelineOperations
のupdateStatusによってつぶやきを投稿しています。
このアクションを実行するには、アプリのコントローラ一覧から jp.myapp.TweetController
をクリックすればよいですね。renderでつぶやきの作成日時を返しているので、ブラウザ上は Wed May 22 16:16:11 JST 2013
みたいな結果が得られるでしょう。
基本的に TwitterTemplate
を取得できるようにしておけば、ほとんどあらゆるAPIの操作ができます。そのあたりは、TwitterTemplateのJavaDocから
- BlockOperations
- DirectMessageOperations
- FriendOperations
- GeoOperations
- ListOperations
- SearchOperations
- TimelineOperations
- UserOperations
あたりを辿ればだいたいわかりますよ!
GrailsのインタラクティブモードをWindowsで使うときはWindows PowerShell + Grails wrapperが快適
WindowsのコマンドプロンプトでGrailsのインタラクティブモードまともに動かないよねー、とお嘆きのみなさま。果たして何人いるのかわからないみなさま。
Grails wrapper は御存知ですか?
> grails wrapper
としてやると、自分のGrailsプロジェクトに grailsw
コマンドを追加して、あたかもそこにGrailsコマンドがあるかのように動作してくれる、蝶・便利なコマンドです。環境変数いじらなくても動いてくれるので楽ちんですね。シェル(grailsw)とバッチ(grailsw.bat)が用意されてるので、Windowsでの動作もバッチリです。Grails wrapperは次期バージョンからはデフォルトで入ってくれるという嬉しい話もありますね。
このGrails wrapperをWindows PowerShellで使うと…!!
> ./grailsw | Enter a script name to run. Use TAB for completion: grails> generate- generate-all generate-controller generate-views grails>
なんとインタラクティブモードに入れます。tab補完も動作します。もうこれGGTSからコマンド実行する理由ないじゃん重いし。なんてこった/(^o^)\
GGTSもAptana Studioみたいに、Grailsのインタラクティブモードのプロンプトウインドウ出しておいてくれれば使い勝手も多少はいいですのに。
ちなみに手元の環境
で試しました。設定してあるシステム環境変数は JAVA_HOME
のみ、つまり Path
追加してないのでWindows PowerShell上では java -version
コマンドすら通らない程度には環境変数設定してないんですが…。
Grails wrapperさんかっこ良すぎですね!
GrailsでWebスクレイピングをするときはjsoupで簡単・便利!(もちろんGroovyでもJavaでも)
先日、名古屋で学生向けGrails/Groovyハンズオンをやらせて頂きました。
その中で、学生さんから「任意のサイトからHTMLを取得して、HTML中の任意の要素を取得するのにスマートな方法はありませんか?」といったような質問を受けました。いわゆるWebスクレイピングですね。その場では、TagSoup http://ccil.org/~cowan/XML/tagsoup/ を紹介しつつ実演しました。手元にTagSoupを使ったコードがすでにあって、その場で時間をかけずに見せやすかったからです。
が、jsoup http://jsoup.org/ の方が使い方とかjavascriptと同じように書けてかっこ良いですね。なので、この記事ではjsoupで書きます。
まず、(Grailsを前提として) BuildConfig.groovy
のdependenciesにjsoupを追加してあげます。Mavenリポジトリのjsoupの最新版からGradleの記法を引っ張ってくればいいですね。
dependencies {
runtime 'org.jsoup:jsoup:1.7.2'
}
あとは、特定のアクションにアクセスしたら、対象のHTMLを取得して必要な要素だけ返すように書いてあげます。ここではYahooニュースのトップトピックスを取得し、アンカー付きで表示しています。
import org.jsoup.* import org.jsoup.nodes.* import org.jsoup.select.* class ScrapingController { def index() { Document doc = Jsoup.connect("http://dailynews.yahoo.co.jp/fc/").get() Elements topics = doc.select('#topTopics li a') render topics.join("<br>") } }
GroovyのスクリプトでGrapeを利用してjsoupを使う場合にはこんな感じになりますね。
@Grapes( @Grab(group='org.jsoup', module='jsoup', version='1.7.2') ) import org.jsoup.* import org.jsoup.nodes.* import org.jsoup.select.* Document doc = Jsoup.connect("http://dailynews.yahoo.co.jp/fc/").get() Elements topics = doc.select('#topTopics li a') def str = "" topics.each{ str += it.text() + "\n" } str
MavenリポジトリにはGrapeの記法もあるので楽ちんです。importも忘れずに!こっちはアンカー無しのプレーンテキストです。
ひとつ気をつけて欲しいのは、静的HTMLの上にAjaxで動的にHTML断片を追加しているようなページでは、ブラウザで表示したときに見えているHTML要素がセレクタに引っかかってこない、ということがあることです。
いずれにせよ、jsoupでは select()
でCSSやjQueryのセレクタと同じ書き方でHTMLの要素を取得できるので、スクレイピングのためにAPIをあれこれ調べる必要がありません。すてきですね!
Grails MiniProfiler プラグインはメモリリークに気をつけましょう。
BuildConfig.groovy
の plugins に
runtime ':profiler:0.4' runtime ':miniprofiler:0.1'
って書くだけで、リクエストごとの発行SQLやレスポンス時間などのプロファイリングを画面上に出してくれる MiniProfiler プラグイン。GGX 2012で話を聞いてから使っていましたが、たいへん盛大にメモリリークを起こしてくれるので、使う際にはそっち方面の注意が必要です。
この MiniProfiler、サーバ側で取得したプロファイル情報を、GSP表示後にAjaxで追加表示する、という動きをします。そのため、Ajaxで表示するための情報はいずこかで参照を持ち続け、メモリリーク(として見えるよう)になるのでしょう。あとプロファイル情報が多いと表示までにすごい時間かかります。
1リクエスト500SQLくらい発行する解析系のシステムに使ってみたら、1リクエストで15MBくらいのメモリリークを起こしていました(おそらく発行SQL数に比例する)。MiniProfiler が有効な状態で負荷試験をしたら、あっという間にメモリを喰い潰して常にFullGCが走り続けて応答がなくなる、という状況に陥るため、不要になったら必ず BuildConfig.groovy
から消しましょうね。
if (Environment.current == Environment.DEVELOPMENT) { runtime ':profiler:0.4' runtime ':miniprofiler:0.1' }
とかやって development 環境でだけ動作するようにしてみたけど、 run-war
(production環境)でもメモリリークが止まらなかったのが気になりました(少なくとも削除したら平和になった)。
Java/Groovy/G*界隈でBoostする為に有用なリンクを集めてみた(Grails編)
なぜかGrailsは無かったので情報を整理してみる。
- ◎:Grails入門者向けピックアップ
- ☆:2013/05/24追加分
(関連)
- Groovy/G*界隈でBoostする為に有用なリンクを集めてみた(Groovy編)
- Groovy/G*界隈でBoostする為に有用なリンクを集めてみた(Gradle編)
- Groovy/G*界隈でBoostする為に有用なリンクを集めてみた(Spock編)
公式
- Grails
- Grails - Reference Documentation - 本当に情報が豊富。英語が苦にならないならいちばんよい。
国内(ユーザーグループ界隈)
- Grails Japan!
- Grails日本語ドキュメント - まだ和訳されていない部分もあります。
- 今週のGrails! 日本語版 - 週単位のGrails関連記事まとめ。
- 日本Grails/Groovyユーザーグループ(JGGUG)
- ◎G* Magazine - JGGUGが提供するGroovyエコシステム情報誌。
- leftovers... - @tyamaさんのblog。Grailsのリリース関連情報。
- みちしるべ - @orange_cloverさんのblog。Groovyist/G*のあれやこれや、たいへんお世話になってます。
Grails関連勉強会・イベント
- JGGUG主催の勉強会 G*ワークショップZ - 毎月第3金曜日。テーマはGroovyエコシステム全般。
- Grails/Groovy入門 学生向け無料ハンズオン - 無料なのにGroovy本が貰えるやつ。品川。終了。
- Grails/Groovy入門 学生向け無料ハンズオン in 名古屋 - 無料なのにGroovy本が貰えるやつ。本記事掲載時点では募集中。→終了。
- ◎yokohama.groovy with mattari.grails - タネマキさんでやってる小ぢんまりしたゆるーい定期勉強会。毎月第3日曜日、場所代1000円。
JavaとGrails
- ◎Struts1ユーザにGrailsをオススメする6の理由 - The search is over - - Java開発者に異次元の生産性を
- Grails/Groovyの活用 - 開発効率を抜本的に改善するために
- G*Magazine 創刊準備号 - Java EE 開発をライトにする
導入・IDE
- ◎JDK - Java仮想マシン上で動作するので、入れてない場合はまずこれを。
- ◎GVM - Mac/Linuxではこれを使いましょう。
- ◎GVM: Groovy enVironment Manager - uehaj - 日本語のGVM紹介。
- ◎GGTS: Groovy/Grails Tool Suite - SpringSourceが提供しているEclipseクローンのIDE。Grailsが同梱されている。Windows版/Mac版/Linux版あり。
- Grails-IDE - EclipseプラグインとしてGrails対応を導入したい場合はこちら。素直にGGTSを使う方がよい。
- IntelliJ IDEA Ultimate - Grailsにおいてもっとも空気を読んでくれるIDE。お金のある人はぜひこちらを。
- GrailsをIntellijからリモートデバッグする - GGTSでも似たような感じでできる、とのこと。
チュートリアル
- ◎Grailsを用いたファイルアップローダ作成
- ◎Start up Grails - クイックスタート
- ◎Grailsをコントロールせよ! Part 1
- ◎Grailsをコントロールせよ! Part 2
↓GrailsでGoogle Calendarっぽいのをつくってみせるよ!っていう壮大なチュートリアル。英語。
- CREATING GOOGLE CALENDAR IN GRAILS - PART 1: THE MODEL - その1、モデル編。
- CREATING GOOGLE CALENDAR IN GRAILS – PART 2: DISPLAYING THE CALENDAR - その2、画面編。
- CREATING GOOGLE CALENDAR IN GRAILS – PART 3: CREATING AND MODIFYING EVENTS - その3、イベント編。
- GOOGLE CALENDAR IN GRAILS - ADDING TESTS WITH SPOCK - その4、Spockでのテスト編。
サンプルアプリ
- ◎Grails-Petclinic - Petclinicアプリ。
- ◎Grails+CloudFoundry向けサンプルアプリケーション - CloudFoundry向けの設定を含む簡単なアプリ。ローカル実行も問題なし。
- Grails-Website - Grailsのサイト。
プラグイン
豊富なプラグインによる機能追加で異次元の生産性を
- Grails Improx プラグイン 0.1 (コードネーム GrailsServ) リリースしました!
- Grails: Spring Security Pluginを使う
- Grails: Webアプリにモバイルビューを追加する - Spring Mobile プラグイン
- 静的リソース機能はGrails 2において中核的価値の一つである - Resources プラグイン
- Database Migration Pluginがすごい ~入門編~
- Database Migration Pluginがすごい ~ロールバック編~ - ☆この他にも database-migration プラグインの記事があります
- Grails 2.1 から標準でインストールされているCache Pluginを試す
- GrailsでCucumberを使用する
- 年末にGrailsのテストフィクスチャーも大掃除しよう - Build Test Data プラグインと Fixtures プラグイン
- テスティング Grails - リソースコレクション - テスティング関連のリンク集。
- Grails Database Reverse Engineering Plugin
- Grails+CloudFoundryハンズオン - Cloud Foundry プラグイン。
- GrailsでOpenIDのチュートリアル - Spring Security OpenID プラグイン
- Grails Plugin探訪 ~第7回 Remote Methods プラグイン~
- Grails Plugin探訪 ~第6回 Build Test Data プラグイン~
- Grails Plugin探訪 ~第5回 RabbitMQ プラグイン~
- Grails Plugin探訪 ~第4回 Cloud Foundry プラグイン~
- Grails Plugin探訪 ~第3回 MongoDB GORM プラグイン~
- Grails Plugin探訪 ~第2回 Spock プラグイン~
- Grails Plugin探訪 ~第1回 Application Info ~
- GrailsのプラグインをCloudBeesで公開する
- ☆Twitter連携するWebアプリなんてあっという間にできるよ。そう、Grailsのspring-security-twitterプラグインならね!
- ☆JGGUG合宿2011企画アプリ GDK48投票アプリの作り方(後編) - spring-security-twitter プラグイン
- ☆Web-based Groovy Console for Grailsを使用してブラウザからgroovyを実行する - console プラグインと spring-security-core プラグイン
- ☆grailsとjQuery MobileとSpring Security pluginでログイン画面を変更する
- ☆Grails with Spock
- ☆Spockを使ってGrailsのドメインクラスのConstraintsを華麗にテストする
- ☆GrailsでCucumberを使用する
- ☆grailsでcoffee-scriptを使う - coffeescript-resources プラグイン
フレームワーク比較・ベンチマーク
- Framework Benchmarks - servlet, php, node.js, wicket, play!, tapesty, spring, sinatra, django, rails, cake等。「Database access test (multiple queries)」を見てみよう。
- Rails vs Grails - ざっくり↓な内容。
Grailsはドメイン志向、RailsはWeb志向。どちらも素早くつくれる。Railsコミュニティは強力。RubyのエコシステムはRailsまわりで花開いたため、Javaのエコシステムを包含するGroovyエコシステムより薄い。基幹系、Java経験者ならGrailsをおすすめする。
- Grails 2.1.0 performance - Rails、Sinatraと。Grailsの性能は良くなっているがメモリ消費も大きい。
- Play vs. Grails Smackdown - play!と。
スライド
ほかに有用な情報、ありませんか?
やや力尽きているので、これも紹介しといて!的な情報、ぜひぜひくださいませ。追記させていただきます。
サクサクWebアプリを作って公開!Grails+CloudFoundryハンズオンをやりました。
先週の金曜日4/19、G*ワークショップZ Apr 2013 - Grails+CloudFoundryハンズオンをやりました。
30分ほどCloudFoundryについて日本CloudFoundryグループの中の人に話をして貰い、そのあとの1時間半でGrailsでWebアプリを作成して、cloudfoundry.comにデプロイしてみましょう、というハンズオンです。
発表資料は http://bit.ly/GrailsCF で見ることができます。
作成したGrailsアプリのソースコードは https://github.com/morika-t/morika にあります。
Togetterはこちら。kimukou2628さんありがとうございます!
事前にcloudfoundry.comのアカウントとGrailsの動作環境は整えておいてくださいね、というかたちで始めました。Mac/LinuxではGVM http://gvmtool.net/ を使えばあっという間にGrailsの環境が作れちゃいますね。Windowsでも、Grailsのバイナリを持ってきて環境変数を設定するか、GGTS(Grailsが同梱されている)を入れれば済むので、ハードルは低いです。JDK入れてない!という人はまず最初にJavaを入れてくださいね。=D
もう1人の発表者の要望(?)で、発表者2人が来場者と同じ方向を向いて、来場者に背を向けて発表する、というかたちになり、身内からこんな言葉を頂くなどもしました。ふふ
背中向けてしゃべるのが斬新 #jggug
— Kazuki YAMAMOTOさん (@yamkazu) 2013年4月19日
何この斬新な布陣 #jggug
— Yasuharu Nakanoさん (@nobeans) 2013年4月19日
サンプルのGrailsアプリは、画像を添付したデータを保存・一覧できる、という簡単なものです。Rails Girls App Tutorialで作っているものに非常に近いですね。もっとも、Rails GirlsではCarrierWaveというgemを使って画像を扱いますが、今回のGrailsアプリはGrailsの機能で実装しています。
Grailsのcloud-foundryプラグインでは、grailsコマンドとして cf-push や cf-update、cf-logs などを実行できるので、Rubyやgem、vmcのインストールが不要なのがポイントです。Grailsのインタラクティブモードを利用すれば、コマンド実行時のロード時間もそれほど気にならなくなるでしょう。
ハンズオンを進める中で、cloudfoundry.comのpostgresサービスが死んでbindできない、という状況が発生し、急遽mysqlを使う、というトラブルも発生しました。これには発表者2人とも焦りましたが、GrailsアプリのソースコードはDataSource.groovyを含め一切変更することなく、cf-pushしなおしてmysqlをbindするだけ、で先に進めることができました。
いろいろと質問も出まして、嬉しい限りでした。
- DBの冗長化は? → DB(CloudFoundryのService)の冗長化はサービス事業者側の責任。複数のサービスをbindすることはできる。
- アプリのupdate時のダウンタイム(サービス中断時間)はどうにかできない? → 無償のcloudfoundry.comではどうしようもない。サービス中断が問題になるようならheroku/Cloudn/CloudBees/AppFogなど、有料のPaaSプロバイダを利用した方がスジが良い。
- 立ち上げられるインスタンス数の上限は? → cloudfoundry.comでは、メモリ2GBの割り当て範囲内で。CloudFoundryの仕組み自体は、DEAを別々のマシン上に立ててスケールアウトすることができるようになっているので、ハードを増やしてrouterががんばれる限り増やせる。AppFogでは128インスタンスまで使える。
- HTTPS(SSL)の利用は? → 証明書を利用者側で用意する以外にやり方がない。 cf-push 等をするときの経路にSSLを使いたい場合には grails.plugin.cloudfoundry.target の値を 'http://api.cloudfoundry.com' ではなく 'https://api.cloudfoundry.com' とすれば良い。
そのほかの質疑については、 https://gist.github.com/morika-t/5424468 に書かれています。
また、cloudfoundry.comにデプロイしたGrailsアプリがJava6上で動作する場合には、ローカル側でwarファイルが作られる際の互換性をJava1.6指定とする必要があります。cloudfoundry.comはJava7にも対応しているので、cf-push するときに --runtime=java7 としてやればJava7で動作してくれるようです。
grails prod cf-update とするだけで、コンパイル、war作成、アップロード、既存サービスの停止と再起動までやってくれるので、楽ちんですね。 #jggug
— Akira Shimosakoさん (@simosako) 2013年4月19日
grailsのcloud-foundry pluginすげー
— とーますさん (@grimrose) 2013年4月19日
手を動かして、道具としての素晴らしさを感じてもらうことができて良かった!