[Zope-dev] zope generations updating objects with method name change

Tres Seaver tseaver at palladion.com
Mon Mar 11 03:32:41 UTC 2013


-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

On 03/10/2013 04:19 PM, Joshua Immanuel wrote:

> My application is based on Grok. Whenver, I change a method-name or
> add a method to a Model, Grok fails to load the previous version from
> the ZODB. I resorted to writing simple generations (zope.generations)
> to update the stored model objects.
> 
> For 'method name' changes, this basically means: 1. create new object 
> 2. copy every single attribute of old-object to the new-object 3.
> delete old-object 4. save new-object
> 
> How does everyone else do this? Or is there a way to make
> grok/zope/zodb not persist the method-names and signatures in a
> content component (grok Model)?

Method names are not stored in the ZODB at all:  only the instance
attributes are stored.

What you report doesn't correspond with how ZODB is designed, nor with
how Zope has been using it forever.  For instance, I can create a class
inside a module:, derived from Persistent:

  # foo.py, v1
  from persistent import Persistent
  class Foo(Persistent):
      def __init__(self, bar, baz):
          self.bar = bar
          self.baz = baz

and make instances of it, adding them to another persistent object:

  from ZODB.DB import DB
  from ZODB.FileStorage import FileStorage
  db = DB(FileStorage('/tmp/data.fs'))
  conn = db.open()
  root = db.root()
  from foo import Foo
  root.foo = Foo('bar 1', 0)
  import transaction
  transation.commit()

and then later modify 'foo.py', adding methods to the Foo class

  # foo.py, v2
  from persistent import Persistent
  class Foo(Persistent)
      def __init__(self, bar, baz):
          self.bar = bar
          self.baz = baz
      def spam(self):
          return self.bar * self.baz

and still load the previously created object from the database::

  from ZDOB.DB import DB
  from ZODB.FileStorage import FileStorage
  db = DB(FileStorage('/tmp/data.fs'))
  conn = db.open()
  root = db.root()
  from foo import Foo
  assert isinstance(root.foo, Foo)
  print root.foo.spam()

If that isn't working for your models, you must be doing something very
weird.  Possible issues:

- - Do your model classes derive from Persistent?

- - Do they have attributes with multable values (e.g., native Python dict
  or list)?  If so, does your code mutate those values without telling the
  containing object it has changed?

- - Are you remembering to commit the transaction?



Tres.
- -- 
===================================================================
Tres Seaver          +1 540-429-0999          tseaver at palladion.com
Palladion Software   "Excellence by Design"    http://palladion.com
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.4.11 (GNU/Linux)
Comment: Using GnuPG with undefined - http://www.enigmail.net/

iEYEARECAAYFAlE9UFkACgkQ+gerLs4ltQ6euQCeORe7UvO3a4VK8oAP+pvd7Rce
lL8An1TxxJcb48YjFa9Ih67U7N1Y57cl
=2eUa
-----END PGP SIGNATURE-----



More information about the Zope-Dev mailing list