Reputation: 1081
Is there a generic method to set a property in datastore entity instance from a string such that it carries out the underlying conversion based on the Property type.
person = Person ()
person.setattr("age", "26") # age is an IntegerProperty
person.setattr("dob", "1-Jan-2012",[format]) # dob is a Date Property
This is easy to write, but this is a very common use case and was wondering whether the Datastore Python API has any provision.
(Sorry if this is a pedestrian question, I am relatively new to Appengine and could not find thru the docs).
Appreciate your help.
Upvotes: 1
Views: 103
Reputation: 11706
I had a couple of days ago the same question for another usecase. To solve it I created a list of property types, to do the conversion I needed. This solution makes use of an undocumented db function and the internals of the db.Model class. Maybe there is a better solution.
from google.appengine.ext import db
kind = 'Person'
models_module = { 'Person' : 'models'} # module to import the model kind from
model_data_types = {} # create a dict of properties, like DateTimeProperty, IntegerProperty
__import__(models_module[kind], globals(), locals(), [kind], -1)
model_class = db.class_for_kind(kind) # not documented
for key in model_class._properties : # the internals of the model_class object
model_data_types[key] = model_class._properties[key].__class__.__name__
To convert your strings, you can create a class with string conversion functions like :
class StringConversions(object)
def IntegerProperty(self, astring):
return int(astring)
def DateTimeProperty(self, astring):
# do the conversion here
return ....
And use it like :
property_name = 'age'
astring = '26'
setattr(Person, property_name, getattr(StringConversions, model_data_types[property_name] )(astring) )
UPDATE:
There is no documentation for : db.class_for_kind(kind)
But there is better solution. Replace these two lines :
__import__(models_module[kind], globals(), locals(), [kind], -1)
model_class = db.class_for_kind(kind) # not documented
With :
module = __import__(models_module[kind], globals(), locals(), [kind], -1)
model_class = getattr(module, kind)
Upvotes: 2