On Thu, Oct 6, 2011 at 1:34 AM, PatrickCD <patrick.do...@gmail.com> wrote:

> Nick,
>
> > It _is_ a hack. A better approach would be to use a single class with
> > appropriate properties, or create a new instance of a new class and
> discard
> > the old one at such time as you need to make the change.
>
> Thanks for your reply. I'm sure you're bored of this thread so I'll
> try to summarise.
>
> To take another example, SQLAlchemy supports what it calls "Single
> Table Inheritance" -
> http://www.sqlalchemy.org/docs/orm/inheritance.html#single-table-inheritance
> . In this approach, there is a field "type" that SQLAlchemy uses to
> determine what class the row should be mapped to. So if you change the
> 'type' you change the class.
>

This is true, but I think if you ask the SQLAlchemy authors, they would also
say that they don't expect this to change after a row is created.


>
> You seem to be saying that each record in the datastore should map to
> one and only one Python class, so a similar approach doesn't work.
>

No, you can map datastore entities to objects any way you like. I'm just
pointing out that the thing you're trying to do is a hack, and violates some
basic expectations OO systems make, and the way you're trying to do it is
unsupported and may break.



>
> Polymodel Objects in the GAE Datastore have a property "class" which
> stores a list of super classes. This property appears to be used by
> the DataStore API in a similar way to how "type" is used  by
> SQLAlchemy.  It's currently possible to change the value of this field
> by setting the __class__ attribute of an instance and saving it back
> to the DataStore. However, you state:
>
> "You're breaking any number of invariants by doing this, so things may
> break without notice at any time. "
>
> Somewhat cryptic, but I'll take your word for it.
>

Invariants like "the set of superclasses of an instance will remain constant
after an object is created". It's possible that not just us, but also other
Python libraries expect that invariant, so once you start messing with it,
you may get unexpected problems elsewhere.


>
> So perhaps the question boils down to whether or not there _is_ a
> reliable way to change the value of the class property for polymodel
> records? I'm guessing the answer is "no", but I'd like to check.
>

You could use the low level datastore API to modify the class property in
the datastore.

If I understand correctly, you want the behavior of a class's methods to
depend on the 'type' of entity being handled, and that 'type' may change
over the lifetime of an entity. Let me suggest an alternative way to do what
you're trying to do:

- Create a "DeveloperBehavior" base class, which encapsulates the behaviors
that change between types
- Create subclasses for each type of behavior.
- Create a 'behaviour' property on your model class, which fetches or
instantiates the appropriate behavior for the current entity.
- Either call the behavior methods directly, or wrap them with methods on
your entity.

This will allow you to change the behavior at runtime, without messing with
Python and DB internals.

-Nick Johnson




>
> Thanks
>
> Patrick
>
> --
> You received this message because you are subscribed to the Google Groups
> "Google App Engine" group.
> To post to this group, send email to google-appengine@googlegroups.com.
> To unsubscribe from this group, send email to
> google-appengine+unsubscr...@googlegroups.com.
> For more options, visit this group at
> http://groups.google.com/group/google-appengine?hl=en.
>
>


-- 
Nick Johnson, Developer Programs Engineer, App Engine

-- 
You received this message because you are subscribed to the Google Groups 
"Google App Engine" group.
To post to this group, send email to google-appengine@googlegroups.com.
To unsubscribe from this group, send email to 
google-appengine+unsubscr...@googlegroups.com.
For more options, visit this group at 
http://groups.google.com/group/google-appengine?hl=en.

Reply via email to