全容を開示:Groovy in Actionの2人の著者であるDierk KoenigとGuillaume Laforgeは、私が参画しているGrails開発チームの同僚です。
Groovy 1.0の公式リリースと合わせて発行されたGroovy in Actionは、Groovy開発の公式ガイドです。各トピックを思慮深く取り上げていることから明らかなように、本書はその情報の源となっているものをストレートに表現しています。Dierk Koenigとその他2名の共著者はGroovyのコミッターであり、もう1人の著者であるGuillaume LaforgeはGroovyのプロジェクトマネージャーを務めています。
著者たちは、Groovyを特定の状況に適用するための手引書か、Groovyのあらゆることに関するレファレンスガイドをおそらく求めているベテランのGroovy開発者だけでなく、おそらく言語、イディオム、使い方について一通り見ておきたいGroovy初心者の双方に役立つ本を作りました。
Groovyに以前ふれたことがなく、単にこの本を手に取っただけという方は、Your way to Groovyと題された第1章の終わりに来るまでには、全開状態のGroovyに取り組む態勢になっている可能性が高いでしょう。入門編にあたるこの章は、Groovyについて、その使いやすさ、信じられないほどのJavaとの統合性、そして様々な経歴を持つ開発者をひきつける魅力をしっかりと訴えます。
Groovy言語について理解する
ここからは、本書の3つの中核部分の1つ目へと入っていきます。パート1のThe Groovy Languageは、Groovyのよさを理解し始めたばかりの人も、この言語の基本をより深く理解しようとする臨時のGroovy開発者も、必読です。パート1の6つの章はすべて、1ページももらさず読むのに値します。
シンタックス規則、データタイプ(またはその欠如)、Groovyライフサイクルの基本から始まり、パート1は私たちをGroovyの世界へとそっと導いてくれます。Groovyにおいては、Javaでプリミティブ型として扱っているタイプであっても、すべてがオブジェクトとなることを学びます。したがって、例えば数値型に対する典型的な算術演算子にもアクセスできるばかりか、これらのタイプのオブジェクトに関して対応する算術メソッドも呼び出せます。本書は各ポイントを説明する上でコード事例をフル活用します。その慣例にしたがい、Groovyのシェルを起動し、このふるまいが実際に稼動する様子をざっと見てみましょう。
> groovysh
Let's get Groovy!
================
Version: 1.0 JVM: 1.5.0_06-64
Type 'exit' to terminate the shell
Type 'help' for command help
Type 'go' to execute the statements
groovy> def x = 1
groovy> int y = 2
groovy> println x + y
groovy> println x.plus(y)
groovy> println x instanceof Integer
groovy> println y instanceof Integer
groovy> go
3
3
true
true
===> null
groovy>
ここでは、Javaではプリミティブ型とみなされるものに対する実際のメソッドを呼び出せることが分かります。xは型なし、yはint型だと宣言されると考えて、Groovyは両方の変数をjava.lang.Integer のインスタンスとして認識することから、Groovyの型推論を少し見てみましょう。Groovyではすべてがオブジェクトですから、算術演算子(+)とそれに対応するメソッド(プラス)の両方が同じ結果を生むことが分かります。(万が一C++の開発者の皆さんの中でJavaにおいて演算子のオーバーロードを期待して待っている方は、ぜひGroovyで試してみてください。待ったかいがあると思います。)
パート1はさらにGroovyのコレクションを探っていきます。本書をここまで読んだ時点で、Javaの経験者は、Groovyの簡潔で表現に富む性質を本当に正しく認識し始めるでしょう。手元のタスクを明確に伝え、他でよく見る煩雑なシンタックスを省いたコードを書くことによる可読性というメリットも実感し始めます。例えば、マップを容易に定義できたり、そのデータへ自由にアクセスできたりするというメリットを考えてみてください。
def myMap = [a:1, b:2, c:3]
assert myMap['a'] == 1
assert myMap.a == 1
assert myMap.get('a') == 1
assert myMap.get('a', 0) == 1 // return 0 if key 'a' is not
// present in the map
myMapの宣言は、Javaで使うようなやや冗長な4行のコード(つまり、最初の1行はマップの宣言・初期化、後の3行は3つのKeyValueペアの投入のため)を義務付けることなく、プログラマーの意図を明確に伝えます。
Groovyのコレクションへの素晴らしいサポートを理解したら、次はクロージャのもつ力が明らかにされます。Dierkと共著者は、この困難となりうる問題を適切に取り扱い、クロージャが私たちの日々のコーディング作業にメリットをもたらしうる領域について、多数の例を挙げています。簡潔なコードというテーマに続き、私個人が気に入っているのは、クロージャによるリソースハンドリングの概論です。
:処理中に例外が生じたときにクローズの命令文が届かないかもしれないという事実を見過ごして、ストリームを開いたものの、メソッドの終わりにクローズを呼び出すコードを何度目にしたことがありますか?try/catchブロックで保護される必要があるのです。いえ、そうではなくてtry/finallyブロックにすべきです。皆さん、そうすべきでしょうか?finallyブロックの中に、クローズは処理が必要な別の例外を入れ込むことができます。これでは覚えておくべき詳細が多すぎるため、リソースハンドリングが間違って実施されるケースが多いのです。Groovyのクロージャへのサポートがあれば、そのロジックを一箇所に入れて、次のように使うことができます。
new File('myfile.txt').eachLine { println it }FileのeachLineメソッドは、ファイル入力ストリームを適切に開き、閉じることを担当します。これにより、ファイルハンドルでリソース漏れが偶然起きるのを防ぐことができます。
この簡潔さはコードの可読性というメリットを生み出すだけでなく、プログラムの正確さと保全性にも役立ちます。
パート1の終わりに近づくにつれ、Groovyのやり方がブール論理、ルーピングなどの構造を制御するために適用されていることが分かります。ここではThe Groovy Truthなどのセクションがあります。これはGroovyでのブール論理の理解とデバッギングに関する頼りになる参考資料として、メーリングリストでもすでに広く言及されています。他の制御構造の裏と表についてだけでなく、switch命令文がint値しかサポートしないJavaの制約からついに解き放たれたことも書かれています。その代わりにGroovyは、はるかに自然で柔軟性に富み、有益なswitch命令文の実装を提供します。著者たちは下記の例を提供し、0、レンジ内の任意の値(0から9)、リスト内の任意の値(8、9、または11)、float型の任意のオブジェクト、または3で割り切れる任意の整数という順番で、条件の1つを満たそうとしています。10という値はこれらの条件を一切満たすことができず、最終的には2文字の値についての正規表現テストに合格します。
switch (10) {
case 0 : assert false ; break
case 0..9 : assert false ; break
case [8,9,11] : assert false ; break
case Float : assert false ; break
case {it%3 == 0}: assert false ; break
case ~/../ : assert true ; break
default : assert false ; break
}
パート1は、Groovyの主要な特徴の1つである動的な性質についての話題でしめくくられます。パート1の最終章は、Groovyビーン、GPath、そしてランタイム時にオブジェクトまたはクラスのふるまいを修正できる最も重要なGroovyメタオブジェクトプロトコルを取り上げます。
Groovyツールキットを組み立てる
Groovy言語をしっかり理解し習得した上で、Groovy in Actionパート2ではまずGroovyライブラリをひととおり見ていきます。パート2はGroovyビルダーに関する章で始まります。ビルダーはGroovyではかなり一般的で、しかも使用すると非常に強力なツールですから、この章の内容をきちんと消化しておくことが望ましいでしょう。
パート1で登場した様々な構成概念の持つ簡潔さと有用性を歓迎するという方であれば、Working with the GDKという次の章も少し時間をかけて読むといいでしょう。GDK(Groovy開発キット)は標準のJava APIを補完する形で、スレッドとの通信から様々な種類のI/Oの実行に至るまでの多数の便利なメソッドを提供します。実のところ、java.io.Fileに便利なeachLineメソッド(前述)を追加するのはこのGDKなのです。
Groovyライブラリをひととおり見るというテーマは、Groovyを使ったデータベースのプログラミング作業の簡素化の章へと続いていき、後半ではGroovyにおけるXMLとの連携の容易さが取り上げられます。内容は明確で有益ですが、時間がない場合は、XMLまたはデータベース関連の作業をするときになってからこれらの章を読んでもいいでしょう。
パート2の中でおそらく最も重要な箇所の中に、GroovyをJavaアプリケーションに統合する戦略について説明している非常に高い評価を得ている章があります。間違いなく、Groovyに関する最も有力な意見の1つがJavaとのシームレスな統合です。既存の投資を活用する必要がある、アプリケーションの一部の領域で静的な型付けを求めている、または理論速度を求めているといったいずれの場合にせよ、アプリケーションにおいてJavaは今後も一翼を担う可能性が高いのです。結果として、JavaとGroovyのコンポーネントを統合させられることが、開発の取り組みのなかで重要な検討事項となります。
.しかしJavaとGroovyのクラス間の依存性が非常に弱い場合、何が起きるのでしょうか?JavaクラスがGroovyクラスに依存していて、そのGroovyクラスが別のJavaクラスに依存しているという状況にはどのように対処すればいいのでしょうか?Groovy in Actionは、この非常に一般的な状況を「鶏が先か卵が先かという依存関係の問題」として説明しています。著者たちはこの問題に関して仮定に基づいた例を提供してくれましたが、ありがたいことに解決策はわずらわしいものでありませんでした。この解決策ではインターフェースをより入念に利用するよう推奨していますが、それ自体が得策なのです。この解決策は、コードベースを(1)Groovyコード、(2)Javaコード、(3)最初の2つのモジュール間で共有するインターフェース(Javaで記述すべき)という3つの中核的なモジュールに分類することを推奨しています。次に、JavaとGroovyクラスをコンパイルする前に共有されるインターフェースをまずコンパイルすることにより、依存関係が突然非常に扱いやすい作業となるのです。
本書はこの例に付随してサンプルのビルドスクリプトを提供するまでには至りません。ビルドスクリプトを最初から作るのはかなり簡単ではありますが、正常に機能するモデルから始めるのはどんなときでもいいものです。このトピックは本当に重要であり、JavaとGroovyコードをおそらく統合したくなる状況が多くなるため、エンドツーエンドの統合例は間違いなく役に立つでしょう。
掘り下げる
パート3はEveryday Groovyをテーマに据え、日常の開発作業のヒント・こつに関する章から始まり、Groovyを使って共通のニーズに応えていきます。この章は、使い勝手のよい便利な言語(または「スクリプト言語」という専門語が好きな方はその呼び名でも)としてのGroovyの利点を示し、Groovyが本物のスイスアーミーナイフのように万能であることが分かります。様々な問題を解決するのに代表的なJava手法についこだわりたくなるのですが、著者たちはより的確な解決策につながることの多い同等のGroovyイディオムを示します。Groovy方式がGroovy開発によりぴったりとはまる傾向にある(当然のことですが)のが分かります。この章は、Groovyコードの実行、デバッギング、プロファイルを容易にする作業空間の設定を狙った注目に値する提案を投げかけ、しめくくっています。
Groovyをワークフローに導入する上で、低リスクかつ見返りの大きい領域を探しているのであれば、単体テストをGroovyで記述するのが賢明な選択です。例えば、現行のテストケースを行き詰らせるデータ設定量についてちょっと考えてみてください。リストを投入する、マップを構築する、または大きな文字列に取り組む場所を検討してください。これらの領域はすべて、Groovyを使えば大幅に簡素化できます。次の章では、テストの記述からビルドプロセスへの統合に至るまで、ここでも単体テストをGroovyで楽しいものにするために知っておくべき事項を取り上げています。
著者たちは、Groovyを使ったWindowsプラットフォーム上の様々なタスクの自動化に関する章でパート3をしめくくっています。Groovyを使って表計算やWord文書を作成する方法、Windowsレジストリと通信する方法、Groovyによって手作業で行うはずだった繰り返しの多いタスクの多くを支援(またはおそらくなくしてしまう)する方法について学最初の15章で豊富な情報を提供するだけでは満足せず、著者たちはGrailsに関する特別な章も含めました。Grailsは、Groovy、Spring、Hibernate、その他の実証済みの技術上で構築されている、刺激的で急速なWebアプリケーション開発フレームワークです。この章を見逃してはいけません。私自身がGrailsに参画しているからという理由だけでなく、この章が良質かつ安全な楽しみをもたらす賢明でユニークなスタイルで書かれているからこそ、私はこの章を推奨します。
埃が積もることはない
全体において、Dierkとその共著者たちは、読みやすい入門書と便利なレファレンスマニュアルのバランスを見事に取ったGroovy言語の必須ガイドを作り上げました。Groovy in Actionを読み終えた後でも、Groovyにまつわる作業のすべてに関して、本書を本棚に公開しておくか手元に置いておくといいでしょう。Groovyが正規表現を使っての作業をどれだけ容易にするか示す簡単な例を見つけようと付属書をぱらぱらめくる場合であろうと、変数がクロージャ内でどのようにスコープされるか覚えておきたい場合であろうと、Groovy in Actionは皆さんの本棚に居場所を何度も得ることになるでしょう。
著者について
Jason Rudolph(source)はRailincのアプリケーションアーキテクトであり、北米全体にわたって列車をより効率よく動かすソフトウェアを開発しています。最近は、Fortune 500の鉄道・設備リース会社、および米国連邦鉄道局が依存する運転安全性のための業界全体の点検レポーティングおよび管理システムを提供しました。
Jasonが関心を寄せているのは、動的言語、軽量開発手法、開発者の生産性向上、そしてプログラミングをより楽しくする取り組みなどです。これらの分野に関心があったために、JasonはGrailsのコミッターとなり、熱心に支持するようになったのです。Jasonは、この刺激的なフレームワークに関する記事をいくつか書いているとともに、Getting Started(サイト・英語)という本を書いています。またバージニア大学で情報科学の学位を取得しています。現在は、(機能するWebアプリケーションを実際によく見せることができる)妻と、(走りでは飼い主のJasonに勝るがリスにはかなわない)犬と共にノースカロライナ州ローリーで暮らしています。