I don't think we're disagreeing - user-defined keys are the only way
to enforce uniqueness.  I was just trying to point out that
user-defined longs work just as well for enforcing uniqueness as
user-defined Strings if your natural key is numeric.  There's no
reason to convert it to a String.

I don't personally think there's anything wrong with carefully chosen
natural keys.  Domain name in your example is a great natural key.

Accounts with an email address is a little weirder.  You want two
things:  Accounts should be able to change their email addresses (so
using the email as the Account key is a bad idea) but you also want to
enforce uniqueness of the email address field (users use it to log
in).  So the appropriate model for this in appengine is probably to
have Account and Email as separate entities, Account with a generated
id and Email with a tautological natural key.

...which provides one more illustration of why the JDO claim of
"transparent persistence" across multiple datastores is bogus.  You'd
never do this in an RDBMS.

Jeff

On Mon, Feb 22, 2010 at 8:09 PM, Max Ross (Google)
<[email protected]> wrote:
> Jeff,
>
> I agree with the majority of your design philosophy and the advice you're
> dispensing, but I still disagree with you on one pretty fundamental point.
> If I'm understanding your argument correctly, you're saying that best
> practices for primary key management don't involve user-defined strings,
> therefore user-defined strings aren't a necessary feature, but I think this
> ignores a pretty basic usage of uniqueness constraints.  Let's say you're a
> domain registrar, you're building your registration workflow on App Engine,
> and you need to guarantee that a domain name can only be claimed once.  If
> you use a numeric id mapped to the domain name you run the risk of letting
> two users reserve the same domain, and if you're a domain registrar that's
> really really bad.  There's no natural key we can bring in here.  Whether we
> as application developers run into them frequently or not, there exists a
> class of problems where a user-defined string pk is a necessary part of the
> solution.
>
> Regards,
> Max
>
> On Mon, Feb 22, 2010 at 1:52 PM, Jeff Schnitzer <[email protected]> wrote:
>>
>> On Mon, Feb 22, 2010 at 1:19 PM, Max Ross (Google)
>> <[email protected]> wrote:
>> >
>> > user-defined long-id keys are not quite as easily used.  You either need
>> > to
>> > commit to not letting the datastore generate ids for that kind or you
>> > need
>> > to reserve a batch of ids using the DatastoreService.allocateIds method.
>> > Otherwise you run the risk of a silent collision.  There is no such risk
>> > with user-defined string keys.
>>
>> Right, but if the user has a natural key (long, String, whatever) they
>> won't be using the generator anyways.  There are plenty of natural
>> long keys in the world... facebook userid being a popular one.
>>
>> FWIW, Objectify makes the distinction between ids of type Long, which
>> can be null and thus autogenerated, and long (the primitive) which
>> cannot be autogenerated.  I really hadn't intended to plug Objectify
>> here, really!
>>
>> > Valid point about renaming, but going back to the example I provided,
>> > the
>> > datastore does not distinguish between inserts and updates.  The only
>> > way
>> > you can guarantee that an entity was inserted, and therefore the only
>> > way
>> > you can guarantee the uniqueness of the name, is to use a user-defined
>> > key.
>> > If you're mapping id to name it will be possible to create two entities
>> > with
>> > the same name.  It's of course up to you to decide how important this is
>> > to
>> > defend against, but without the ability to provide your own id you
>> > wouldn't
>> > get to make this choice, and without the ability to provide your own
>> > string
>> > id you wouldn't be able to add some application-specific meaning to this
>> > choice.
>>
>> I totally agree with you WRT user-defined vs generated values, I just
>> don't see anything wrong with using the long id as a user-defined
>> value.  Just make sure you never ask for a generated one.  Seems
>> pretty straightforward.
>>
>> Jeff
>>
>> --
>> You received this message because you are subscribed to the Google Groups
>> "Google App Engine for Java" group.
>> To post to this group, send email to
>> [email protected].
>> To unsubscribe from this group, send email to
>> [email protected].
>> For more options, visit this group at
>> http://groups.google.com/group/google-appengine-java?hl=en.
>>
>
> --
> You received this message because you are subscribed to the Google Groups
> "Google App Engine for Java" group.
> To post to this group, send email to [email protected].
> To unsubscribe from this group, send email to
> [email protected].
> For more options, visit this group at
> http://groups.google.com/group/google-appengine-java?hl=en.
>

-- 
You received this message because you are subscribed to the Google Groups 
"Google App Engine for Java" group.
To post to this group, send email to [email protected].
To unsubscribe from this group, send email to 
[email protected].
For more options, visit this group at 
http://groups.google.com/group/google-appengine-java?hl=en.

Reply via email to