Creating Entity Models (original) (raw)

You need to create a model class for your entity. You can do this in two ways:

This document describes how to create each of these types of model classes. It also describes how to create a model hook, so that your application can run some code before or after some type of operations, for example, before each get().

Creating a model class with properties

Before creating an entity, you must create a model class that defines one or more entity properties. For example:

...

where you want each Account entity to have properties for user name, user ID, and email.

For a full list of property types, see the Entity Property Reference.

Creating an Expando model class

You don't have to use a model class that defines properties in advance. A special model subclass called Expando changes the behavior of its entities so that any attribute assigned is saved to the data store. Note that such attributes can't start with an underscore.

Here is how to create an Expando model:

...

This writes an entity to the data store with afoo property with integer value 1, a bar property with string value 'blah', and a repeated tag property with string values 'exp', 'and', and 'oh'. The properties are indexed, and you can inspect them using the entity's _properties attribute:

An Expando created by getting a value from the data store has properties for all property values that were saved in the data store.

An application can add predefined properties to anExpando subclass:

...

This gives employee a name attribute with value 'Sandy', an age attribute with value None, and a dynamic attribute location with value 'SF'.

To create an Expando subclass whose properties are unindexed, set _default_indexed = False in the subclass definition:

...

You can also set _default_indexed on an Expando entity. In this case it will affect all properties assigned after it was set.

Another useful technique is querying an Expando kind for a dynamic property. A query like the following

won't work, because the class doesn't have a property object for the location property. Instead, use GenericProperty, the class Expando uses for dynamic properties:

Using Model Hooks

NDB offers a lightweight hooking mechanism. By defining a hook, an application can run some code before or after some type of operations; for example, a Modelmight run some function before every get().

A hook function runs when using the synchronous, asynchronous and multi versions of the appropriate method. For example, a "pre-get" hook would apply to all ofget(), get_async(), and get_multi(). There are pre-RPC and post-RPC versions of each hook.

Hooks can be useful for the following:

The following example shows how to define hook functions:

...

...

If you use post-hooks with asynchronous APIs, the hooks are triggered by callingcheck_result(), get_result() or yielding (inside a tasklet) an async method's future. Post hooks do not check whether the RPC was successful; the hook runs regardless of failure.

All post- hooks have a Futureargument at the end of the call signature. This Future object holds the result of the action. You can call get_result()on this Future to retrieve the result; you can be sure that get_result()won't block, since the Future is complete by the time the hook is called.

Raising an exception during a pre-hook prevents the request from taking place. Although hooks are triggered inside <var>*</var>_async methods, you cannot pre-empt an RPC by raising tasklets.Return in a pre-RPC hook.

What's next