SHOEISHA iD

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

DeveloperZine(デベロッパージン)- エンジニアの意思決定を支える技術情報メディア ProductZine

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

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

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

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

ゲストブックアプリケーション

 それでは、JDOを使ってデータを保存するゲストブックアプリケーションを作ってみましょう。

プロジェクトの作成

 Eclipseのツールバーから「New Web Application Project」を選択します。

 プロジェクトの設定情報として、このサンプルでは次の値を設定します。

  1. Project nameに「guestbook」を入力します
  2. Packageに「guestbook」を入力します
  3. 今回もGWT(Google Web Toolkit)を使用しないため、「Use Google Web Toolkit」のチェックを外しておきます

 それ以外の項目はデフォルトのままとします。

設定ファイル

 Quercusを有効にするために「war/WEB-INF」以下にある次の3つのファイルを修正、追加します。

  • appengine-web.xml(App Engine定義ファイル)
  • web.xml(デプロイメント記述子ファイル)
  • php.ini(Quercus用PHP設定ファイル)

 これらの設定ファイルについては前編と同じ値を設定します。

ゲストブックのエントリを永続化するクラス

 最初にゲストブックのエントリを永続化するためのクラス、Entryクラスを作成します。

 Entryクラスでは名前とコメント、投稿日時を定義し、永続化するためのアノテーションを宣言します。

[リスト9]Entry.javaの一部
// (1)App Engineデータストアに対して永続化の対象とすることを宣言
@PersistenceCapable(identityType = IdentityType.APPLICATION)
public class Entry {
  private static final TimeZone TZ = TimeZone.getTimeZone("Asia/Tokyo");
  // (2)永続化対象のフィールド
  @PrimaryKey
  @Persistent(valueStrategy = IdGeneratorStrategy.IDENTITY)
  private Long id;
  @Persistent
  private String name;

  @Persistent
  private String comment;

  @Persistent
  private Date date;
  // (3)コンストラクタ
  public Entry(String name, String comment) {
    this.name = name;
    this.comment = comment;
    this.date = new Date();
  }
  // (4)日付を文字列に変換して返す
  public String getDateAsString() {
    SimpleDateFormat df = new SimpleDateFormat("yyyy/MM/dd HH:mm:ss");
    // 文字列に変換する際のTimeZoneを"Asia/Tokyo"に設定する
    df.setTimeZone(TZ);
    return df.format(this.date);
  }
  // その他のgetter/setter
}

 ここでは、次のような処理を実装しています。

  1. EntryクラスがApp Engineデータストアの永続化対象であることを宣言
  2. 永続化対象のフィールドに@Persistentアノテーションを付加
  3. 主キーとしてLong型のIdフィールドを定義し、値は自動生成します。

  4. コンストラクタでは名前とコメントを設定可能
  5. 登録日時はコンストラクタで設定します。

  6. 登録日時を文字列に変換して返す
  7. このとき、TimeZoneを"Asia/Tokyo"として設定します。

PHPでEntryクラスをラップするためのクラス

 この例ではなるべくPHPで頑張ることを目的にしていますので、JavaのEntryクラスをラップするためのPHPクラスを定義します。

 PHPのラップクラスとして「GuestBook」を次のように定義します。

[リスト10]guestbook.php
<?php
// (1)使用するJavaのクラスをインポートする
import javax.jdo.PersistenceManager;
import javax.jdo.Query;
import guestbook.Entry;
import guestbook.PMF;

class GuestBook {
  // (2)Entryクラスのインスタンスをメンバ変数として持つ
  private $entry;

  public function __construct($name, $comment, $entry) {
    if ($name != null && $comment != null) {
      $this->entry = new Entry($name, $comment);
    } else if ($entry != null) {
      $this->entry = $entry;
    }
  }
  // (3)Entryインスタンスに対するgetter関数
  public function getId() {
    return $this->entry->getId();
  }

  public function getName() {
    return $this->entry->getName();
  }

  public function getComment() {
    return $this->entry->getComment();
  }

  public function getDate() {
    return $this->entry->getDateAsString();
  }
  // (4)App Engineデータストアに保存
  public function put() {
    if ($this->entry == null) {
      return;
    }
    $pm = PMF::get()->getPersistenceManager();
    try {
      $pm->makePersistent($this->entry);
    } catch (Exception $e) {
      var_dump($e->Message);
    }
    $pm->close();
  }
  // (5)App EngineデータストアからEntryクラスのインスタンス一覧を取得
  public static function all($size) {
    $pm = PMF::get()->getPersistenceManager();
    $query = "select from guestbook.Entry order by date desc range 0," . $size;
    try {
      $entries = $pm->newQuery($query)->execute();
      for($i = 0; $i < $size; $i++)
      {
        $entry = $entries[$i];
        if ($entry == null)
          break;
        $book = new GuestBook(null, null, $entry);
        $array[] = $book;
      }
    } catch (Exception $e) {
      var_dump($e->Message);
    }
    $pm->close();
    return $array;
  }
  // (6)Idを指定してEntryクラスのインスタンスを削除
  public static function deleteById($id) {
    $pm = PMF::get()->getPersistenceManager();
    $query = "select from guestbook.Entry where id == " . $id;
    try {
      $entries = $pm->newQuery($query)->execute();
      $size = count($entries);
      if ($size > 0) {
        $entry = $entries[0];
        $pm->deletePersistent($entry);
      }
    } catch (Exception $e) {
      var_dump($e->Message);
    }
    $pm->close();
  }
}
?>
  1. 使用するJavaのクラスをインポートする
  2. QuercusではJavaのクラスも使うことができます。ここでは使用するJavaのクラスをimport命令でインポートしています。

  3. JavaのEntryクラスのインスタンスをメンバ変数として持つ
  4. 実際の値はJavaのEntryクラスで管理するため、PHPのGuestBookクラスではEntryクラスのインスタンスを持ちます。

  5. JavaのEntryインスタンスに対するgetter関数
  6. 後述するデータ表示用PHPスクリプトから値を取得するためのgetter関数を定義します。Entryクラスのメソッドを呼び出します。

  7. App Engineデータストアに保存
  8. PersistenceManagerクラスのインスタンスを使用してEntryクラスのインスタンスを保存します。

  9. App EngineデータストアからEntryクラスのインスタンス一覧を取得
  10. 引数として受け取った値を取得数の上限として、Entryクラスのインスタンスを取得します。JDOQLのRange句を使用しています。

  11. Idを指定してEntryクラスのインスタンスを削除
  12. 主キーであるIdの値を指定してApp EngineデータストアよりEntryクラスのインスタンスを取得し、nullでなければ削除します。クエリ文字列のfrom句にはEntryクラスのFQCNを指定しています。

次のページ
まとめ

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

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本格入門」「これからはじめるLaravel実践入門」「はじめてのAndroidアプリ開発 Kotlin編 」他、著書多数

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

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

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

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

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

この記事をシェア

CodeZine(コードジン)
https://codezine.jp/article/detail/4145 2009/07/28 14:00

イベント

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

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

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

メールバックナンバー