2011年6月28日火曜日

Google App Engine for Java のデータストアAPIのテストを実装してみる(その16)

前回までに修正した、サンプルコードを掲載します。

import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertTrue;

import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;

import org.junit.After;
import org.junit.Before;
import org.junit.Test;

import com.google.appengine.api.datastore.DatastoreService;
import com.google.appengine.api.datastore.DatastoreServiceFactory;
import com.google.appengine.api.datastore.Entity;
import com.google.appengine.api.datastore.FetchOptions;
import com.google.appengine.api.datastore.Key;
import com.google.appengine.api.datastore.PreparedQuery;
import com.google.appengine.api.datastore.Query;
import com.google.appengine.api.datastore.Query.FilterOperator;
import com.google.appengine.tools.development.testing.LocalDatastoreServiceTestConfig;
import com.google.appengine.tools.development.testing.LocalServiceTestHelper;

/**
 * Google App Engine for Javaにおけるユニットテストのサンプルコード。
 */
public class LocalUnitTestSample {

 private static final String DATA_KIND = "sampleDataKind";

 private LocalServiceTestHelper helper = new LocalServiceTestHelper(new LocalDatastoreServiceTestConfig());

 //private String[] propertyNames = {"pName1","pName2","pName3","pName4","pName5"};
 private String propertyName = "propertyName";

 private String[] propertyValues = {"pValue1","pValue2","pValue3","pValue4","pValue5"};

 private DatastoreService ds;

 private List keyList;

 /**
  * @throws java.lang.Exception
  */
 @Before
 public void setUp() throws Exception {
  helper.setUp();

  //サンプルデータをデータストアに保存する
  putSampleData();
 }

 /**
  * サンプルデータをデータストアに保存するメソッド。
  */
 private void putSampleData() {
  keyList = new ArrayList();
  ds = DatastoreServiceFactory.getDatastoreService();
  for (int i = 0; i < propertyValues.length; i++) {
   Entity entity = new Entity(DATA_KIND);
   entity.setProperty(propertyName, propertyValues[i]);
   Key key = ds.put(entity);
   keyList.add(key);
  }
 }

 /**
  * @throws java.lang.Exception
  */
 @After
 public void tearDown() throws Exception {
  //サンプルデータをデータストアから削除する
  deleteSampleData();

  helper.tearDown();
 }

 /**
  * サンプルデータをデータストアから削除するメソッド。
  */
 private void deleteSampleData() {
  Iterator iter = keyList.iterator();
  while (iter.hasNext()){
   ds.delete(iter.next());
  }
 }

 @Test
 public void doTest(){
  //サンプルデータをデータストアから検索する
  for (int i = 0;i < propertyValues.length;i++){
   Query query = new Query(DATA_KIND);
   query.addFilter(propertyName, FilterOperator.EQUAL, propertyValues[i]);
   PreparedQuery prepare = ds.prepare(query);
   List entitiesList = prepare.asList(FetchOptions.Builder.withDefaults());
   assertEquals(1,entitiesList.size());
   Iterator iter = entitiesList.iterator();
   while (iter.hasNext()){
    Entity entity = iter.next();
    assertTrue(propertyValues[i].equals(entity.getProperty(propertyName)));
   }
  }
 }

}




インストール不要・無料のKaede翻訳ツール:
http://kaedetrans.appspot.com/

2011年6月27日月曜日

Google App Engine for Java のデータストアAPIのテストを実装してみる(その15)

サンプルコードの変更の続きです。


前回の変更で、
putSampleData()メソッドを修正しました。

今回は、
doTest()メソッドの修正です。

まず最初、for文です。
for (int i = 0;i < propertyNames.length;i++){
この行のpropertyNamesの部分がコンパイルエラーになりますので、
propertyValues


と変更します。
ループ条件を構成する配列を、propertyNamesからpropertyValuesにすることで、
プロパティの「値」の数だけ繰り返します。

その次は、
query.addFilter(propertyNames[i], FilterOperator.EQUAL, propertyValues[i]);
の行のうち、propertyNames[i]の部分がコンパイルエラーになるので、
ここに正しいプロパティ名にあたる文字列を入れます。
propertyName
です。
変更後のコードは、
query.addFilter(propertyName, FilterOperator.EQUAL, propertyValues[i])
です。

もう一つは、
whileループ内部のassertTrue()の引数です。
assertTrue(propertyValues[i].equals(entity.getProperty(propertyNames[i])));
この行のpropertyNames[i]を、propertyNameにします。
assertTrue(propertyValues[i].equals(entity.getProperty(propertyName)));
となります。



インストール不要・無料のKaede翻訳ツール:
http://kaedetrans.appspot.com/

2011年6月23日木曜日

Google App Engine for Java のデータストアAPIのテストを実装してみる(その14)

サンプルコードの変更の続きです。

前回の変更で、
フィールドpropertyNamesを削除して、
新たにフィールドpropertyNameを作成しました。

すると、コンパイルエラーとなりますので、
エラー部分を修正します。

まず、
putSampleData()メソッドです。

for (int i = 0;i < propertyNames.length;i++){

の行を、
for (int i = 0;i < propertyValues.length;i++){

と変更します。
propertyNamesをpropertyValuesとするわけです。

次に、
entity.setProperty(propertyNames[i],propertyValues[i]);


の行を
entity.setProperty(propertyName,propertyValues[i]);

とします。
propertyNames[i]をpropertyNameに変更しています。

次回は、doTest()メソッドを変更します。


インストール不要・無料のKaede翻訳ツール:
http://kaedetrans.appspot.com/

2011年6月21日火曜日

Google App Engine for Java のデータストアAPIのテストを実装してみる(その13)

サンプルコードの改造を進める前に、
テスト用のサンプルデータを変更します。

と言っても、プロパティ名を変更するだけです。

フィールドpropertyNamesはjava.lang.String配列になっていますが、
String型に変更します。

private String[] propertyNames = 
{"pName1","pName2","pName3","pName4","pName5"};
の行を、
private String propertyName = "propertyName";
と変更します。

次に、
メソッドputSampleData()の実装を変更します。


インストール不要・無料のKaede翻訳ツール:
http://kaedetrans.appspot.com/

2011年6月18日土曜日

Google App Engine for Java のデータストアAPIのテストを実装してみる(その12)

今回は、サンプルコードの改変はお休みです。
その代わり、サンプルコード全体の流れを
書いてみます。


このサンプルコードは、
setUp()
putSampleData()
doTest()
tearDown()
deleteSampleData()
の5つのメソッドを実装しています。
この中で、putSampleData()、deleteSampleData()の2つは
それぞれsetUp()、tearDown()の内部で呼び出されるだけなので、
テストを実行する上で、メソッド呼び出しの流れとしては
serUp()
doTest()
tearDown()
という順になります。JUnit4で使用されるアノテーションが付いた
メソッドだけです。

・テストの前準備(サンプルデータの保存)
・テストの実行(サンプルデータの検索)
・テストの後処理(サンプルデータの削除)
単純な流れですね。



インストール不要・無料のKaede翻訳ツール:
http://kaedetrans.appspot.com/

2011年6月17日金曜日

Google App Engine for Java のデータストアAPIのテストを実装してみる(その11)

前回は、tearDown()メソッドの中身を変更してみました。
2行だけのメソッドなので、行ごと順番を入れ替えただけです。

すると、NullPointerExceptionがスローされました。
LocalServiceTestHelper.tearDown()の呼び出しの後に
データストアのAPIを呼び出しているためでした。

今回は、tearDown()と対になるメソッドである、
@Beforeアノテーションの付いている
setUp()メソッド
を改造してみます。

その前に、tearDown()メソッドは元に戻しておきましょう。

サンプルコードの変更はこちら。
/**
  * @throws java.lang.Exception
  */
 @Before
 public void setUp() throws Exception {
  //サンプルデータをデータストアに保存する
  putSampleData();

  helper.setUp();

 }

 /**
  * @throws java.lang.Exception
  */
 @After
 public void tearDown() throws Exception {
  //サンプルデータをデータストアから削除する
  deleteSampleData();

  helper.tearDown();
 }


前述の通り、setUp()メソッドの2行を入れ替えただけです。

テストを実行すると、
やはりNullPointerExceptionが
helper.tearDown();
のところでスローされます。

データストアの操作は、
helper.setUp()と
helper.tearDown()
の間で行う必要があるということです。




インストール不要・無料のKaede翻訳ツール:
http://kaedetrans.appspot.com/

2011年6月13日月曜日

Google App Engine for Java のデータストアAPIのテストを実装してみる(その10)

データストアAPIのテストでは、
LocalServiceTestHelperの機能を利用して、
データストアへのデータの格納を行っています。

そのために実装する必要があるのは、
・LocalServiceTestHelperのインスタンスの生成
・LocalServiceTestHelper.setUp()の呼び出し
・LocalServiceTestHelper.tearDown()による後処理
となります。

この3つの手順の順番は変更できません。
試しに、
前回まで説明してきたサンプルコードの
tearDown()メソッド内、
deleteSampleData()メソッドと
helper.tearDown()メソッド
の順番を入れ替えてみましょう。

@After
public void tearDown(){
 deleteSampleData();
 helper.tearDown();
}

と変更して、テストを起動してみてください。
すると、
deleteSampleData()の行でNullPointerExceptionがスローされます。
helper.tearDown()が既に呼び出されているためです。




インストール不要・無料のKaede翻訳ツール:
http://kaedetrans.appspot.com/

2011年6月11日土曜日

Google App Engine for Java のデータストアAPIのテストを実装してみる(その9)

前回までで、LocalUnitTestSampleクラスについて
説明しました。

JUnit4では、
@Beforeアノテーションの付いたメソッド
↓
@Testアノテーションの付いたテストメソッド
↓
@Afterアノテーションの付いたメソッド
の順番で、各テストメソッドについて順に実行されるのですが、
LocalUnitTestSampleクラスでは、
@BeforeのsetUp()メソッドで、サンプルデータの準備
@TestのdoTest()メソッドで、データストアの検索と検証
@AfterのtearDown()メソッドで、サンプルデータの消去
という流れで処理されます。

この中で、LocalServiceTestHelperクラスの
・setUp()
・tearDown()
のメソッドの使い方について、
次回以降にサンプルコードに少し手を加えながら
実験してみます。



インストール不要・無料のKaede翻訳ツール:
http://kaedetrans.appspot.com/

2011年6月9日木曜日

Google App Engine fo Java のデータストアAPIのテストを実装してみる(その8)

前回のdoTest()メソッドの説明の続きです。


List entitiesList = prepare.asList(FetchOptions.Builder.withDefaults());
prepareからjava.util.List形式で検索結果のエンティティを取り出しています。
取り出したエンティティの数が1であることを検証するために
asList()メソッドを使っています。
取得するエンティティの数を限定する必要はないため、
引数はFetchOptions.Builder.withDefaults()です。


assertEquals(1,entitiesList.size());
検索結果のエンティティの数が1であることを検証しています。

Iterator iter = entitiesList.iterator();
取得したエンティティの中身について検証するために、
java.util.Iterator を取得します。

while (iter.hasNext()){
 Entity entity = iter.next();
 assertTrue(propertyValues[i].equals(entity.getProperty(propertyNames[i])));
}
iterに要素が残っている間のループです。
エンティティを取得して、propertyNames[i]の名前のプロパティを取得し、
propertyValues[i]と同じであることを検証しています。



インストール不要・無料のKaede翻訳ツール:
http://kaedetrans.appspot.com/

2011年6月7日火曜日

Google App Engine for Java のデータストアAPIのテストを実装してみる(その7)

今回は、テストの実体となる doTest()メソッドの説明を行います。
実のところ、このメソッドの中身はサンプルコードの要点ではないので、
とりあえず実装しているだけです。
サンプルコードは、@Beforeと@Afterの内部の実装について
説明するための実験用です。


@Test
 public void doTest(){
  //サンプルデータをデータストアから検索する
  for (int i = 0;i < propertyNames.length;i++){
   Query query = new Query(DATA_KIND);
   query.addFilter(propertyNames[i], FilterOperator.EQUAL, propertyValues[i]);
   PreparedQuery prepare = ds.prepare(query);
   List entitiesList = prepare.asList(FetchOptions.Builder.withDefaults());
   assertEquals(1,entitiesList.size());
   Iterator iter = entitiesList.iterator();
   while (iter.hasNext()){
    Entity entity = iter.next();
    assertTrue(propertyValues[i].equals(entity.getProperty(propertyNames[i])));
   }
  }
 }

@Testアノテーションの付いている
doTest()メソッドは、実際のテストコードです。

メソッド内で行われている動作は、
  propertyNamesの各要素をプロパティ名として、
  該当するプロパティ値を持つエンティティを検索する
   ↓
  取得したエンティティのプロパティ値を検証する
という内容です。
これをpropertyNamesの長さ分、繰り返しています(forブロック)。

Query query = new Query(DATA_KIND);
この行は、DATA_KINDで取得するデータの種類を指定して
Queryを生成しています。

query.addFilter(propertyNames[i],FilterOperator.Builder.EQUAL,propertyValues[i]);
引数propertyNames[i]は検索するプロパティ名、
引数FilterOperator.Builder.EQUALはプロパティ値の検索条件を同値とすること、
引数propertyValues[i]は、プロパティ値の境界を設定しています。

PreparedQuery prepare = ds.prepare(query);
ds.prepare()メソッドの検索条件を設定したクエリオブジェクトを渡して、
検索の実行を準備します。

この後、クエリを実行してエンティティを取り出しますが、
次回に説明します。



インストール不要・無料のKaede翻訳ツール:
http://kaedetrans.appspot.com/

2011年6月5日日曜日

Google App Engine for Java のデータストアAPIのテストを実装してみる(その6)

今回説明するのは、deleteSampleData()メソッドです。

/**
  * サンプルデータをデータストアから削除するメソッド。
  */
 private void deleteSampleData() {
  Iterator iter = keyList.iterator();
  while (iter.hasNext()){
   ds.delete(iter.next());
  }
 }


このメソッドは、
@Afterアノテーションの付けられている
tearDown()メソッド内で呼び出される、
サンプルデータをデータストアから削除するメソッドです。

実際に運用する場合は、このようなメソッドを実装する必要はありません。
helper.tearDown()メソッドでLocalServiceTestHelperの終了処理が行われると、
メモリ上に保存されたデータストアのデータは消去されるからです。

しかし、このサンプルコードでは、その機能を確認するために
実装しています。

それでは、メソッドの中身について説明します。

Iterator. iter = keyList.iterator();
の行は、keyListからKeyを格納したjava.util.Iteratorを取得します。

次のwhileブロックは、取得したiterを使って
キーを指定してデータの削除を行っています(ds.delete(iter.next())の行)。



インストール不要・無料のKaede翻訳ツール:
http://kaedetrans.appspot.com/

2011年6月2日木曜日

Google App Engine for Java のデータストアAPIのテストを実装してみる(その5)

今回は、tearDown()メソッドについて説明します。

/**
  * @throws java.lang.Exception
  */
 @After
 public void tearDown() throws Exception {
  //サンプルデータをデータストアから削除する
  deleteSampleData();

  helper.tearDown();
 }

tearDown()メソッドには、
@Afterアノテーションが付いています。

これにより、各テストメソッド(@Testアノテーション)の実行後に
tearDown()メソッドが呼び出されます。

メソッドの中身を見てみましょう。

deleteSampleData()メソッドは(次回以降説明します)、
データストアからサンプルとして保存したデータ(putSampleData()メソッド)を
削除するメソッドです。

helper.tearDown()は、LocalServiceTestHelperが提供する
ローカル環境でのサービスの終了処理を行います。
このメソッドが呼び出された後では、GAEのサービスをローカル環境で
利用することはできません。




インストール不要・無料のKaede翻訳ツール:
http://kaedetrans.appspot.com/