---
title: 'Java Datastore API für die Google App Engine'
url: 'https://tutego.de/blog/javainsel/2009/07/java-datastore-api-fur-die-google-app-engine'
markdown: 'https://tutego.de/blog/javainsel/2009/07/java-datastore-api-fur-die-google-app-engine.md'
date: '2009-07-28'
description: 'Um in der Google Cloud Daten zu speichern bietet Google drei API an: JPA, JDO und eine Low-Level-API. Infos dazu gibt liefert [http://code.google.com/intl/de/appengine/docs/java/datastore/. JPA](http://code.google.com/intl/de/appengine/docs/java/datastore/. JPA "http://code.google.com/intl/de/appen…'
taxonomy:
  category:
    - GWT
---

# Java Datastore API für die Google App Engine

![Illustration einer tropischen Insel mit Palmen und einem hohen Berg](https://tutego.de/blog/javainsel/user/themes/tutego/images/insel-cover.jpg)# Java Blog für Programmierer

[Java Blog für Programmierer](https://tutego.de/blog/javainsel/)

## Java Datastore API für die Google App Engine

28.07.2009 · [Christian Ullenboom](https://tutego.de/blog/javainsel/author/admin/)

Um in der Google Cloud Daten zu speichern bietet Google drei API an: JPA, JDO und eine Low-Level-API. Infos dazu gibt liefert \[<http://code.google.com/intl/de/appengine/docs/java/datastore/>. JPA\](<http://code.google.com/intl/de/appengine/docs/java/datastore/>. JPA "<http://code.google.com/intl/de/appengine/docs/java/datastore/>") und JDO basieren im Kern auf der Low-Level API, die auf die [http://en.wikipedia.org/wiki/BigTable](http://en.wikipedia.org/wiki/BigTable "http://en.wikipedia.org/wiki/BigTable") zurückgreift.

Für JPA und JDO gibt es selbst von Google viele Beispiele, aber die Low-Level-API ist nicht so gut dokumentiert und selbst das Beispielprogramm in der JavaDoc enthält Fehler. Zeit daher, ein sehr einfaches Beispiel mit einer 1:n Relationen anzugehen.

Im Mittelpunkt der API steht der DatastoreService, der ein bisschen an den EntityManager von JPA erinnert. Er bietet Methoden für die CRUD-Operationen. Mein Beispiel geht schon ein bisschen “pseudo-ORM” an die Aufgabe ran, einer Person Nachrichten zuordnen zu können:

Die Personen-Klasse:

```java
package com.tutego.server.entity;

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

import com.google.appengine.api.datastore.DatastoreServiceFactory;
import com.google.appengine.api.datastore.Entity;
import com.google.appengine.api.datastore.EntityNotFoundException;
import com.google.appengine.api.datastore.Key;
import com.google.appengine.api.datastore.Query;

public class Person
{
 private final static String ENTITY_NAME = "Person";
 Entity personEntity;

 public enum Gender
 {
```

MALE, FEMALE

```
 }
```

public Person()

```java
 {
 personEntity = new Entity( ENTITY_NAME );
 }
```

private Person( `Key` key )

```java
 {
 try
 {
 personEntity = DatastoreServiceFactory.getDatastoreService().get( key );
 }
 catch ( EntityNotFoundException e )
 {
 }
 }
```

private Person( `Entity` entity )

```java
 {
 personEntity = entity;
 }

 public static Person get( Key key )
 {
 return new Person( key );
 }

 public void setUsername( String username )
 {
 personEntity.setProperty( "username", username );
 }
```

public `String` `getUsername()`

```java
 {
 return personEntity.getProperty( "username" ).toString();
 }

 public void setGender( Gender gender )
 {
 personEntity.setProperty( "gender", gender.toString() );
 }
```

public `Gender` `getGender()`

```java
 {
 return Gender.valueOf( personEntity.getProperty( "gender" ).toString() );
 }
```

public `Key` `put()`

```java
 {
 return DatastoreServiceFactory.getDatastoreService().put( personEntity );
 }
```

public static void `deleteAll()`

```java
 {
 Query deleteAllQuery = new Query( ENTITY_NAME );

 for ( Entity entity : DatastoreServiceFactory.getDatastoreService().prepare( deleteAllQuery ).asIterable() )
 DatastoreServiceFactory.getDatastoreService().delete( entity.getKey() );
 }

 private static List<Person> executeQuery( Query query )
 {
 List<Person> result = new ArrayList<Person>();
 for ( Entity entity : DatastoreServiceFactory.getDatastoreService().prepare( query ).asIterable() )
 result.add( new Person( entity ) );
 return result;
 }

 public static List<Person> findAllPersons()
 {
 Query query = new Query( ENTITY_NAME );

 return executeQuery( query );
 }

 public static List<Person> findPersonByGender( Gender gender )
 {
 Query query = new Query( ENTITY_NAME );
 query.addFilter( "gender", Query.FilterOperator.EQUAL, gender.toString() );

 return executeQuery( query );
 }

 @Override
```

public `String` `toString()`

```java
 {
 return String.format( "Person[%s,%s]", getUsername(), getGender() );
 }
}
```

Die Nachrichten-Klasse:

```java
package com.tutego.server.entity;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;

import com.google.appengine.api.datastore.DatastoreServiceFactory;
import com.google.appengine.api.datastore.Entity;
import com.google.appengine.api.datastore.EntityNotFoundException;
import com.google.appengine.api.datastore.Key;
import com.google.appengine.api.datastore.Query;

public class Message
{
 private final static String ENTITY_NAME = "Message";

 private Entity messageEntity;
```

public `Message`()

```java
 {
 messageEntity = new Entity( ENTITY_NAME );
 }
```

private `Message`( `Key` key )

```java
 {
 try
 {
 messageEntity = DatastoreServiceFactory.getDatastoreService().get( key );
 }
 catch ( EntityNotFoundException e )
 {
 }
 }
```

private `Message`( `Entity` entity )

```java
 {
 messageEntity = entity;
 }

 public static Message get( Key key )
 {
 return new Message( key );
 }

 public void setText( String text )
 {
 messageEntity.setProperty( "text", text );
 }
```

public `String` `getText()`

```java
 {
 return messageEntity.getProperty( "text" ).toString();
 }

 public void setCreationTime( Date d )
 {
 messageEntity.setProperty( "creationtime", "" + d.getTime() );
 }
```

public `Date` `getCreationTime()`

```java
 {
 return new Date( Long.parseLong( messageEntity.getProperty( "creationtime" ).toString() ) );
 }

 public void setReceiver( Person p )
 {
 messageEntity.setProperty( "person_fk", p.personEntity.getKey() );
 }
```

public `Key` `put()`

```java
 {
 return DatastoreServiceFactory.getDatastoreService().put( messageEntity );
 }

 private static List<Message> executeQuery( Query query )
 {
 List<Message> result = new ArrayList<Message>();

 for ( Entity entity : DatastoreServiceFactory.getDatastoreService().prepare( query ).asIterable() )
 result.add( new Message( entity ) );
 return result;
 }

 public static List<Message> findMessagesForPerson( Person p )
 {
 Query query = new Query( ENTITY_NAME );
 query.addFilter( "person_fk", Query.FilterOperator.EQUAL, p.personEntity.getKey() );

 return executeQuery( query );
 }

 @Override
```

public `String` `toString()`

```java
 {
 return String.format( "Message[%s,%s]", getCreationTime(), getText() );
 }
}
```

Getestet werden soll das ganze in einer einfachen Server-Funktion:

```java
StringWriter sw = new StringWriter();
PrintWriter out = new PrintWriter( sw );

// Insert new entity

Person p1 = new Person();
p1.setUsername( "chris" );
p1.setGender( Person.Gender.MALE );
Key key1 = p1.put();

out.println( "* Key für erste Person " + p1 );
out.println( KeyFactory.keyToString( key1 ) );

Person p2 = new Person();
p2.setUsername( "pallas" );
p2.setGender( Person.Gender.FEMALE );
p2.put();

Person p3 = new Person();
p3.setUsername( "tina" );
p3.setGender( Person.Gender.FEMALE );
p3.put();
```

// Search for entity with a given key

```java
Person p = Person.get( key1 );
out.println( "* Suche mit Schlüssel " + key1 );
out.println( p.getUsername() );

// Query

List<Person> findAll = Person.findAllPersons();
out.println( "* Alle Personen" );
out.println( findAll.toString() );

// Query

List<Person> females = Person.findPersonByGender( Gender.FEMALE );
out.println( "* Alle Frauen:" );
out.println( females.toString() );

Message msg1 = new Message();
msg1.setText( "Hallo Maus" );
msg1.setCreationTime( new Date(1) );
msg1.setReceiver( p );
msg1.put();

Message msg2 = new Message();
msg2.setText( "Hallo Ratte" );
msg2.setCreationTime( new Date(2) );
msg2.setReceiver( p );
msg2.put();

out.println( "* Alle Nachrichten für " + p );
out.println( Message.findMessagesForPerson( p ) );
out.println( "\\n" );

// Clean up

Person.deleteAll();

out.flush();

return sw.toString().replace( "\\n", "<br/>" );
```

Als Ergebnis kommt HTML zurück, was der Client zum Testen anschauen kann.

Kategorien: [GWT](https://tutego.de/blog/javainsel/category/gwt/)

[← Alle Beiträge](https://tutego.de/blog/javainsel/)

---

## Navigation

- Previous: [Thema der Woche: Stripes, ein einfaches Web Presentation Framework](https://tutego.de/blog/javainsel/2009/07/thema-der-woche-stripes-ein-einfaches-web-presentation-framework.md)
- Next: [Thema der Woche: Repository-Pattern in DDD und DAO](https://tutego.de/blog/javainsel/2009/07/thema-der-woche-repository-pattern-in-ddd-und-dao.md)
