title: Enforce unique field in appengine datastore (java)
body: <p>I have a User class with a String field emailAddress, on which I want to enforce uniqueness.  I was having difficulty getting the available suggested solutions to work, so I wrote the following process which seems to work, using a separate class with the unique field as its primary key.  </p>
  
  <p>Whilst it seems to work, it smells because I'm intentionally creating an exception when nothing incorrect happens (by trying to retrieve a non-existent EmailAddress object).</p>
  
  <p>Can anyone comment on whether this method will work reliably, in particular across multiple appengine instances.  </p>
  
  <p>Thanks.</p>
  
  <p>Firstly, I have the User class:</p>
  
  <pre><code>@PersistenceCapable
  public class User {
    public User(String emailAddress, String otherData) {
      this.emailAddress = emailAddress;
      this.otherData = otherData;
    }
  
    @PrimaryKey
    @Persistent(valueStrategy = IdGeneratorStrategy.IDENTITY)
    private Key key;
  
    @Persistent
    private String emailAddress;
  
    @Persistent
    private String otherData;
  }
  </code></pre>
  
  <p>I then have an EmailAddress class, using the email address as the primary key:</p>
  
  <pre><code>@PersistenceCapable
  public class EmailAddress {
    public EmailAddress(String emailAddress) {
      this.emailAddress = emailAddress;
    }
  
    @PrimaryKey
    @Persistent
    private String emailAddress;
  }
  </code></pre>
  
  <p>Usage of these classes is then as follows:</p>
  
  <pre><code>public class UserManager {
  
    public User createUser(String email, String otherData) {
      User user = new User(emailAddress, otherData);
      EmailAddress emailAddress = new EmailAddress(email);
  
      PersistenceManager pm = PMF.get().getPersistenceManager();
      Transaction tx = pm.currentTransaction();
  
      User persistedUser = null;  
  
      try {
        tx.begin();
        EmailAddress testEmailAddress = null;
        try {
          testEmailAddress = pm.getObjectById(EmailAddress.class, email);
        } catch (Exception e) {
          //
        }
        if (null != testEmailAddress) {
          throw new RuntimeException("That email address already has an account");
        }
        pm.makePersistent(emailAddress);
        persistedUser  = pm.makePersistent(user);
        txn.commit();
        return persistedUser;
      } finally {
        if (txn.isActive()) {
          txn.rollback();
        }
        pm.close();
      }
    }
  
    ...
  
  }
  </code></pre>