SHOEISHA iD

※旧SEメンバーシップ会員の方は、同じ登録情報(メールアドレス&パスワード)でログインいただけます

CodeZine編集部では、現場で活躍するデベロッパーをスターにするためのカンファレンス「Developers Summit」や、エンジニアの生きざまをブーストするためのイベント「Developers Boost」など、さまざまなカンファレンスを企画・運営しています。

Google App Engine for Javaで動作するスクリプト系言語

PHPも使える! Google App Engine for Java(後編)

Google App Engine for Javaで動作するスクリプト系言語 (2)

  • X ポスト
  • このエントリーをはてなブックマークに追加

JDO

 JDOは、データベースから独立してデータの永続化操作を行うための処理を定義した仕様で、RDBMSやオブジェクトデータベース、XMLなどさまざまな種類のデータストアに対応しています。

 Google App Engine for JavaではJDO 2.3に対応しており、DataNucleus Access Platform 1.1を基にした実装ライブラリを含んでいます。

 JDOでは、POJO(Plain Old Java Object)に対して、永続化対象となるクラスやフィールドにアノテーションを記述することで、どのようなデータを永続化させるのかという定義を行います。アノテーション定義を行ったJavaクラスは、App Engineデータストアではエンティティ(Entity)として扱われます。エンティティは1つ以上のプロパティ(Property)を持ちます。

 アノテーションで定義したクラスは通常のコンパイル後に「Enhancement」と呼ばれる後処理を実行することでJDOとの関連づけを行います。Google Plugin for Eclipseではこの処理は自動的に実行されます。

 Javaのソースをコンパイルすると、次のようにコンソールにEnhancementの結果が表示されます。

Enhancement実行コンソール画面
Enhancement実行コンソール画面

JDOによる永続化の指定

 それではどのようにJavaクラス(POJO)に対して永続化の情報を定義するかを見ていきましょう。

 ここではコンタクト情報を管理するクラスを永続化対象とするコードを例にとります。

[リスト1]ContactInfo.javaの一部
package sample;
// (1)永続化対象クラスの定義
@PersistenceCapable(identityType = IdentityType.APPLICATION)
public class ContactInfo {
    // (2)主キーとなる永続化対象フィールドの定義
    @PrimaryKey
    @Persistent(valueStrategy = IdGeneratorStrategy.IDENTITY)
    private Long id;
    // (3)永続化対象フィールドの定義
    @Persistent
    private String firstName;
    // (3)永続化対象フィールドの定義
    @Persistent
    private String lastName;
    // (3)永続化対象フィールドの定義
    @Persistent
    private String email;

    public ContactInfo(String firstName, String lastName, String email) {
        this.firstName = firstName;
        this.lastName = lastName;
        this.email = email;
    }
    // getter/setter
}
(1)永続化対象クラスの定義

 永続化対象クラスに対して@PersistenceCapableアノテーションを宣言します。

(2)主キーとなる永続化対象フィールドの定義

 主キーとなる永続化対象フィールドに対して@PrimaryKeyアノテーションを宣言しますす。一つのクラスに必ず一つは主キーとなるフィールドを定義しなければなりません(埋め込みクラスをのぞく)。

 永続化対象フィールドに対して@Persistentアノテーションを宣言しますが、主キーで値を自動生成する場合には、この例のようにvalueStrategyに対してIdGeneratorStrategyのEnum値を設定する必要があります。

(3)永続化対象フィールドの定義

 永続化対象フィールドに対して@Persistentアノテーションを宣言します。

 @Persistentアノテーションを定義できるフィールドの型は次のようなものがあります。

  • App EngineデータストアでサポートされたCore type
  • java.util.List<...>のようなCollectionまたはCore typeの配列
  • @PersistenceCapable宣言されたクラスのインスタンスや、このインスタンスのCollection
  • Serializableなクラスのインスタンスや、このインスタンスのCollection
  • エンティティでプロパティとして永続化されるように定義されている埋め込みクラス

 Core typeには次のようなものがあります。

  • java.lang.String
  • boolean/java.lang.Boolean
  • short/java.lang.Short
  • int/java.lang.Integer
  • long/java.lang.Long
  • float/java.lang.Float
  • double/java.lang.Double
  • java.util.Date
  • com.google.appengine.api.datastore.ShortBlob
  • com.google.appengine.api.datastore.Text
  • com.google.appengine.api.datastore.Blob
  • com.google.appengine.api.datastore.Key
  • com.google.appengine.api.users.User
  • com.google.appengine.api.datastore.Link

 また、主キーとなるフィールドにはメールアドレスなどの値を設定することもできます。

永続化対象クラスの操作に必要なクラス

 アノテーションで永続化対象としたクラスをApp Engineデータストアとやりとりするには、PersistenceManagerクラスを使用します。

 PersistenceManagerクラスのインスタンスは、次のように取得するのが一般的です。

[リスト2]PersistenceManagerを取得する
PersistenceManager pm = PMF.get().getPersistenceManager();

 ここで出てくるPMFというクラスは、PersistenceManagerFactoryクラス(PersistenceManagerのファクトリクラス)のインスタンスを管理するユーティリティクラスです。Google App Engine for Javaのドキュメントにもよく出てきます。

[リスト3]PMF.java
import javax.jdo.JDOHelper;
import javax.jdo.PersistenceManagerFactory;

public final class PMF {
    // (1)jdoconfig.xmlのpersistence-manager-factory/@nameの値を指定
    private static final PersistenceManagerFactory pmfInstance =
        JDOHelper.getPersistenceManagerFactory("transactions-optional");

    private PMF() {}

    public static PersistenceManagerFactory get() {
        return pmfInstance;
    }
}

 (1)の処理でJDOHelperクラスのgetPersistenceManagerFactoryメソッドに渡している「transactions-optional」という文字列はJDOの設定名を表しています。この名前は「src/META-INF/jdoconfig.xml」で定義されるJDOの設定情報と一致させる必要があります。

 このjdoconfig.xmlファイルは、Google Plugin for Eclipseでプロジェクトを作成するとツールにより「src/META-INF」以下に生成され、ビルド時に「war/WEB-INF/classes/META-INF」以下に配置されます。

永続化対象クラスの保存、更新、削除、検索

 先ほどのContactInfoクラスを例に、保存、更新、削除、検索の処理を見ていきましょう。

 ContactInfoクラスのインスタンスを保存するには、PersistenceManagerクラスのmakePersistent()メソッドを使用します。

 PersistenceManagerクラスのインスタンスは、使い終わったら必ずclose()メソッドを呼び出す必要があります。

[リスト4]保存の例
    PersistenceManager pm = PMF.get().getPersistenceManager();
    ContactInfo c = new ContactInfo("Alfred", "Smith", "Alfred@example.com");
    try {
        pm.makePersistent(c);
    } finally {
        pm.close();
    }

 次にemailの値を更新する例を見ていきます。取得したContactInfoクラスのインスタンスに対してsetEmail()メソッドで新しい値を設定し、PersistenceManagerクラスのmakePersistent()メソッドに渡します。

[リスト5]更新の例
    PersistenceManager pm = PMF.get().getPersistenceManager();
    ContactInfo c = ... // 取得
    c.setEmail("Alfred.Smith@example.com");
    try {
        pm.makePersistent(c);
    } finally {
        pm.close();
    }

 削除する場合には、PersistenceManagerクラスのdeletePersistent()メソッドを使用します。

[リスト6]削除の例
    PersistenceManager pm = PMF.get().getPersistenceManager();
    ContactInfo c = ... // 取得
    try {
        pm.deletePersistent(c);
    } finally {
        pm.close();
    }

 検索では、JDOQLというSQLに似た言語が使用できます。次の例では、lastNameが"Smith"に一致するContactInfoクラスのインスタンスを取得しています。

[リスト7]検索の例
    PersistenceManager pm = PMF.get().getPersistenceManager();
    try {
        Query query = pm.newQuery("select from sample.ContactInfo " +
                                  "where lastName == lastNameParam " +
                                  "parameters String lastNameParam");
        List<ContactInfo> results = (List<ContactInfo>) query.execute("Smith");
    } finally {
        pm.close();
    }

 検索結果はjava.util.List<ContactInfo>として返されます。

 クエリ文のfromの後には検索対象となるクラスのFQCN(Fully Qualified Class Name)を指定します。

 この例ではクエリ文で"lastNameParam"というパラメータを定義し、Queryクラスのexecute()メソッドに"lastNameParam"パラメータの値を渡しています。

 Queryクラスではパラメータや他の条件を別メソッドで渡すことができますが、次のように1行ですべてを記述することもできます。

[リスト8]パラメータもクエリ文字列に含めた場合の検索例
    PersistenceManager pm = PMF.get().getPersistenceManager();
    try {
        Query query = pm.newQuery("select from sample.ContactInfo " +
                                  "where lastName == 'Smith'");
        List<ContactInfo> results = (List<ContactInfo>) query.execute();
    } finally {
        pm.close();
    }

次のページ
ゲストブックアプリケーション

この記事は参考になりましたか?

  • X ポスト
  • このエントリーをはてなブックマークに追加
Google App Engine for Javaで動作するスクリプト系言語連載記事一覧
この記事の著者

山田 祥寛(ヤマダ ヨシヒロ)

静岡県榛原町生まれ。一橋大学経済学部卒業後、NECにてシステム企画業務に携わるが、2003年4月に念願かなってフリーライターに転身。Microsoft MVP for Visual Studio and Development Technologies。執筆コミュニティ「WINGSプロジェクト」代表。主な著書に「独習シリーズ(Java・C#・Python・PHP・Ruby・JSP&サーブレットなど)」「速習シリーズ(ASP.NET Core・Vue.js・React・TypeScript・ECMAScript、Laravelなど)」「改訂3版JavaScript本格入門」「これからはじめるReact実践入門」「はじめてのAndroidアプリ開発 Kotlin編 」他、著書多数

※プロフィールは、執筆時点、または直近の記事の寄稿時点での内容です

WINGSプロジェクト 花田 善仁(ハナダ ヨシヒト)

WINGSプロジェクトについて>有限会社 WINGSプロジェクトが運営する、テクニカル執筆コミュニティ(代表 山田祥寛)。主にWeb開発分野の書籍/記事執筆、翻訳、講演等を幅広く手がける。2018年11月時点での登録メンバは55名で、現在も執筆メンバを募集中。興味のある方は、どしどし応募頂きたい。著書記事多数。 RSS X: @WingsPro_info(公式)、@WingsPro_info/wings(メンバーリスト) Facebook

※プロフィールは、執筆時点、または直近の記事の寄稿時点での内容です

この記事は参考になりましたか?

この記事をシェア

  • X ポスト
  • このエントリーをはてなブックマークに追加
CodeZine(コードジン)
https://codezine.jp/article/detail/4145 2009/07/28 14:00

おすすめ

アクセスランキング

アクセスランキング

イベント

CodeZine編集部では、現場で活躍するデベロッパーをスターにするためのカンファレンス「Developers Summit」や、エンジニアの生きざまをブーストするためのイベント「Developers Boost」など、さまざまなカンファレンスを企画・運営しています。

新規会員登録無料のご案内

  • ・全ての過去記事が閲覧できます
  • ・会員限定メルマガを受信できます

メールバックナンバー

アクセスランキング

アクセスランキング