Reputation: 26966
In python appengine, I have a polymodel class (e.g. Animal
). I stored in the datastore some instances of child classes (e.g. Horse
).
If I delete the definition of the Horse
class in the python source code (or change its name), and get the stored Horse
entities using db.get
and the entity key, what will happen?
e.g. would the retrieved entity be of type Animal
? PolyModel
? Would there be an exception?
Upvotes: 0
Views: 52
Reputation: 39814
The datastore itself doesn't really know/care about the python class or the data model itself, those are really just implementation details specific to the GAE db
or ndb
client libraries. You can see that in the Creating an entity example (which uses a generic python client library, without a model definition) - the entity data is simple a dictionary with name-value pairs:
task = datastore.Entity(client.key('Task'))
task.update({
'category': 'Personal',
'done': False,
'priority': 4,
'description': 'Learn Cloud Datastore'
})
Renaming/deleting the entity model in your application won't delete the entities in the datastore, you'll still be able to see them in the datastore browser.
The key of an already created entity has the entity kind (as a string) embedded in it. Attempting to perform a db.get()
on that saved key will raise an KindError
exception because it performs a check on the data returned from the datastore against the imported models:
Traceback (most recent call last):
File "/usr/local/google_appengine/google/appengine/tools/devappserver2/python/request_handler.py", line 226, in handle_interactive_request
exec(compiled_code, self._command_globals)
File "<string>", line 12, in <module>
File "/usr/local/google_appengine/google/appengine/ext/db/__init__.py", line 1540, in get
return get_async(keys, **kwargs).get_result()
File "/usr/local/google_appengine/google/appengine/api/apiproxy_stub_map.py", line 613, in get_result
return self.__get_result_hook(self)
File "/usr/local/google_appengine/google/appengine/datastore/datastore_rpc.py", line 1715, in __get_hook
entities = extra_hook(entities)
File "/usr/local/google_appengine/google/appengine/api/datastore.py", line 643, in local_extra_hook
return extra_hook(result)
File "/usr/local/google_appengine/google/appengine/ext/db/__init__.py", line 1509, in extra_hook
cls1 = class_for_kind(entity.kind())
File "/usr/local/google_appengine/google/appengine/ext/db/__init__.py", line 299, in class_for_kind
raise KindError('No implementation for kind \'%s\'' % kind)
KindError: No implementation for kind 'Horse'
So if you want to perform a rework of your models and re-use the already stored data you should keep the old models around to be able to read the data and write it back under the new models.
Upvotes: 2