[ZODB-Dev] Re: session problems
Florent Guillaume
fg at nuxeo.com
Sun Jan 1 22:23:52 EST 2006
Could folks have a look and tell me what they think of the proposed
patch? Actually it is my belief this is a concern of DB or Connection,
not MountedObject, and the code shouldn't be in MountedObject but that's
the easiest workaround for now.
Florent
Florent Guillaume wrote:
> Ok I've dug deeper and now understand the problem. The root cause is in
> the multi-databases support.
>
> The problem is that the Zope startup only closes the main connection it
> had on the root database. The first connection to the TemporaryStorage,
> created and opened during Zope startup, is never closed, so still is a
> synchronizer in its original transaction, but is nevertheless reused in
> other transactins, without a proper synchronizer set up.
>
> When a MountedObject needs to be traversed, it tries to find an
> existing connection for the new database by doing:
> conn = anyjar.get_connection(db_name)
> where anyjar is the "parent" connection. If there's a linked connection
> for that database, it's returned, otherwise if the multi- database
> already has seen the wanted database, it opens a connection from it,
> then adds it to the "linked" connections attribute (conn.connections)
> and shares this attribute between the two connections.
>
> I that fails, because the connection has never been linked to the new
> database (which is the case during startup code), then the
> MountedObject code does:
> conn = self._getDB().open()
> Here _getDB() correctly returns a newly instanciated database, which
> has been linked to the other ones in the multi-databases setup (shared
> "databases" dictionnary attribute, ultimately coming from
> Zope2.Startup.datatypes.DBTab.databases).
>
> Then open() returns a new opened connection for that database. *BUT*
> this new connection is not "linked" to the others (using their
> .connections attribute). This code from get_connections is needed:
> self.connections.update(new_con.connections)
> new_con.connections = self.connections
> which would be written, in the context of code executing in
> MountedObject (in _getMountedConnection):
> except KeyError:
> conn = self._getDB().open()
> anyjar.connections.update(conn.connections)
> conn.connections = anyjar.connections
> return conn
> But of course really this code doesn't belong to MountedObject. This is
> just the simplest way I could find, if others want to test it.
>
>
> The ".connections" sharing is really funky, apparently all the
> connections opened in the context of the same multi-databases support
> are intended to be present in it. Why is this access not indirected
> through the multi-databases support in DB itself? Also I don't
> understand why open()'s "delegate" attribute is not stored as a
> connection attribute, and close() should reuse it instead of obeying a
> "primary" attribute. Anyway, I guess historical code, etc.
>
> I'll let specialistst of the multi-databases decide what to do :)
>
> Florent
>
--
Florent Guillaume, Nuxeo (Paris, France) Director of R&D
+33 1 40 33 71 59 http://nuxeo.com fg at nuxeo.com
More information about the ZODB-Dev
mailing list