On 23 déc, 20:23, "[email protected]" <[email protected]> wrote:
> i'm trying to do some instantiation of models, based on run time
> parameters. i'm new to django/python so not sure the term, but the
> relative java term is reflection.

The term in Python is... well, it isn't. With a dynamic language, it's
just daily programming, you know ?-)

(ok, nitpicking, sorry. Please don't hold it against me - or at least
read the practical solution at the bottom before).

> for example, if i have a model, in my django models.py:
>
> class Foo(models.Model):
>     name = models.CharField(max_length=20)
>
> now in some views.py code, i'm given, say some xml that defines a new
> Foo object, so i want to dynamically create a new Foo object and save
> it.  <xml><Foo><name>bar</name></Foo></xml>
>
> i've tried a few things below, but namely, what i'm trying to do is
> parse the xml, see that i need to create "Foo" and set it's name to
> bar:
>
> tag = "Foo"
> key = "name"
> value = "bar"
>
>  _temp = __import__('project.test.models', globals(), locals(),
> ['Foo'], -1)
>  createobj = getattr(_temp, tag)

This returns a class object, not an instance.

> setattr(createobj, key, value)

This sets the "name" attribute of *class* Foo to "bar".

> createobj.save()
>
> i'm getting unbound method on save,

Not surprinsing since you're calling it on a class object... An
unbound method (IOW: an instance method looked up on the class) takes
an instance as first param - you know, the (in)famous  'self'
argument ?

<digression topic="python-object-model">
What is defined (using the 'def' statement) in a class statement is
_really_ a function. It only becomes a "method" (in fact just a thin
wrapper around the class, instance and function - name it, a partial
evaluation of the function) when looked up on an instance - and an
"unbound method" (same thing modulo the instance) when looked up on
the class.

IOW and to make a long story short:

instance.method(arg)
# is equivalent to
cls.method(instance, arg)
# which - if and only if "method" is defined in "cls"  (_not_
inherited)
# is equivalent to:
cls.__dict__['method'](instance, arg)

If you want to learn more about it, google for python+descriptor
+protocol. It's the same thing that powers computed attributes (aka
properties), and it's something worth learning about.
</digression>

> and tried various ways to save.
> but i'm thinking it is in the class instantiation where the problem
> is.

Indeed. You didn't create a Foo instance.


Ok, now for the solution(s):

# 1/ Django's models are all loaded at startup and cached.
#    To get a model by appname/model, just use:

from db.models.loading import get_model
model_class = get_model("test", tag)

# NB : at this point, "model_class" is what you named "createobj"

# 2/ once you have the class, you need an instance:

instance = model_class()

# 3/ then you can set the attribute and save the instance:

setattr(instance, key, value)
instance.save()

# ALT 1
# you can save on typing, using keyword args
# to instanciate your model:

from db.models.loading import get_model
model_class = get_model("test", tag)
instance = model_class(**{key:value})
instance.save()

# ALT2
#  and save even more typing using the
#  model's manager "create" method:

from db.models.loading import get_model
model_class = get_model("test", tag)
# create and save the instance in one step
instance = model_class.objects.create(**{key:value})


HTH.

Oh, and welcome onboard BTW - we all hope you'll enjoy the trip !-)
--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups 
"Django users" 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/django-users?hl=en
-~----------~----~----~----~------~----~------~--~---

Reply via email to