[Zope-dev] RE: Why missing connection._storage.load?
Loren Stafford
lstaffor@dynalogic.com
Mon, 28 Feb 2000 08:31:36 -0800
I didn't know anything about this connection stuff. I'll give it a try.
-- Thanks
-- Loren
From: Martijn Pieters <mj@digicool.com>
Sent: February 28, 2000 08:12 AM
> From: Loren Stafford [mailto:lstaffor@dynalogic.com]
> >
> > My product's initialize(context) procedure creates a ZCatalog if that
> > catalog doesn't already exist. I've defined an additional method
> > armed_event() for the Catalog object. Later, the same product
> > _init_.py
> > module calls armed_event() (OK -- it's called from a thread spawned by
> > initialize(context)).
>
> Do you create a new DB connection?
>
> >
> > When the catalog is created in the same product load process,
> > the call to
> > the catalog method armed_event() yields this output from pdb:
> >
> > >
> > C:/Zope214\lib\python\Products\ZScheduler\ZSchedule.py(47)arme
> > d_event()
> >
> > ...which is what I would expect.
> >
> > However, when the catalog already exists (from a previous
> > product load),
> > the call to the catalog method yields this output:
> >
> > > C:\Zope214\lib\python\ZODB\Connection.py(386)setstate()
> >
> > I didn't write any setstate methods, so I presume this is
> > extension class or
> > persistence voodoo. If so, the fact that pdb doesn't show how
> > it got to
> > setstate must be due to the fact that that logic is written
> > in C. Somewhere,
> > somehow, (perhaps via an inherited __setstate__ method) Zope
> > has figured out
> > that the catalog object has to be loaded from the ZOSB before it can
> > proceed, and calls on Connection.py\setstate to help do so.
> > Right, so far?
> >
>
> Indeed, via the Persistence class, the ZODB is asked to retrieve the
> object. How do you access the Catalog? You should obtain a new Root
> object for your new thread, and traverse to the Catalog via that
> reference.
>
> When you use the ZServer Monitor, you have to do the same thing:
>
> import Zope
> app=Zope.app()
>
> You then have your own connection to the database. When you are done
> with it (basically every time you go to sleep in the thread), you close
> it again:
>
> app._p_jar.close()
> del app
>
> This way you keep conflicts down, performance up.
>
> > OK, tracing along in setstate(), we get to this statement and
> > exception:
> >
> > > C:\Zope214\lib\python\ZODB\Connection.py(391)setstate()
> > -> p, serial = self._storage.load(oid, self._version)
> > (Pdb) s
> > AttributeError: "'None' objec...ribute 'load'"
> > > C:\Zope214\lib\python\ZODB\Connection.py(391)setstate()
> > -> p, serial = self._storage.load(oid, self._version)
> > (Pdb)
> >
> > OOps! This connection's storage object has no load method.
> > How can that
> > happen? Because pdb isn't showing how it got here, it's hard
> > to see what the
> > cause is. Can someone who's been here before help me out?
> >
> > Was the Catalog object not defined properly or not
> > initialized properly? If
> > not, how is the Catalog storage object supposed to be initialized?
>
> The storage is not defined. Probably because the Conection has been
> closed in the meantime, which is what happens as soon as initialisation
> of products is done. See lib/python/Zope/__init__.py
>
> HTH
>
> Martijn Pieters, Software Engineer