What's the best way to specify a key_name for App Engine NDB Model?
Asked Answered
A

1

8

I'm trying to create an ndb model where each record has an unique field "name". I would like to define this field as the key_name field and use it to look up the records. Do I have to include a name field or can I somehow set the key_name field to an arbitrary string that the user can specify as long as it's unique?

I'm thinking of using Model.get_or_insert to make sure that old records don't get overwritten, but is there a way to tell if the return value is newly created or pre-existing? I want to be able to display an error message if the user entered a duplicate name.

Lastly, I tried to create a key_name field on a DjangoForms model that uses the above ndb model as the metaclass so I can use djangoforms for validation/rendering but for some reason my defined fields don't show up.

class UserProfileForm(djangoforms.ModelForm): key_name = djangoforms.StringProperty() class Meta: model = UserProfile

Astoria answered 18/4, 2012 at 18:31 Comment(1)
You should really ask separate questions for each of these, rather than lumping them all together.Scudder
M
14

Do I have to include a name field or can I somehow set the key_name field to an arbitrary string that the user can specify as long as it's unique?

You can pass your your unique key name as the id parameter to model constructor: profile = UserProfile(id='my_unique_name').

I'm thinking of using Model.get_or_insert to make sure that old records don't get overwritten, but is there a way to tell if the return value is newly created or pre-existing? I want to be able to display an error message if the user entered a duplicate name.

Use Model.get_by_id(). It will return a model instance or None if a model is not found:

profile = UserProfile.get_by_id('my_unique_name')
if profile:
    # display error message saying that the user already exists.

Lastly, I tried to create a key_name field on a DjangoForms model that uses the above ndb model as the metaclass so I can use djangoforms for validation/rendering but for some reason my defined fields don't show up.

I don't know how DjangoForms work, but most likely they are not compatible with NDB. You will want to create your own validation logic.

Mascon answered 18/4, 2012 at 19:16 Comment(3)
Your solution to part 2 won't work if he wants to create the user transactionally if it doesn't already exist - a transaction is required for that.Scudder
@NickJohnson what would you suggest? To override Model.get_or_insert() and to raise an exception inside the transaction if get part returns user?Mascon
I'd suggest implementing a transaction that does exactly what's needed - attempt to get the model; throw an error if it exists, and create it if it doesn't.Scudder

© 2022 - 2024 — McMap. All rights reserved.