One of the things I was worried about in using one connection per
application is that things like last_insert_id() aren't guaranteed to work
anymore. Since multiple people could be sharing the same connection, if
they both insert something at the same time, the results of last_insert_id()
are not predictable. One connection per user solves this problem (I
think...Hopefully MySQL handles this properly), but also one connection per
transaction works (using ConnectionPools).
I'm going to try out the ConnectionPools idea, but wouldn't writing a
wrapper class for the db connection work (to solve the sweepSession
problem)? One that overrides the methods that pickle calls to get state
----- Original Message -----
From: "Chuck Esterbrook" <echuck@...>
Sent: Wednesday, November 22, 2000 11:25 AM
Subject: Re: [Webware-discuss] Non-pickleable objects in session
> At 09:58 PM 11/21/00 -0500, Chris AtLee wrote:
> >Hey there,
> >The code that I'm writing makes extensive use of MySQL connections. My
> >first implementation had one connection per class, but then I realized
> >that this was probably not a good idea since if multiple people were
> >viewing the page at one time, I could run into syncronization problems.
> >(My understanding is that the Page classes are instatiated once per
> >server, not once per user.) Then I thought about putting the database
> >connection into the session, since that is user-specific. Unfortunately,
> >this has the problem that MySQL connection objects aren't picklable, so
> >sweepSessions dies.
> >What can I do about this? Can I mark some parts of the session
> >non-pickleable (why is it pickling the sessions anyway?) Or is there a
> >better way to handle per-user database connections?
> Sessions get pickled as a means of backup, so that if the app crashes, or
> is brought down on purpose, the next freshly started app can load the
> sessions and continue like nothing happened.
> Gee, we thought this was a feature. :-)
> The quickest, but hackiest way would be to open
> WebKit/SessionMemoryStory.py and comment out the implementation of
> storeAllSessions() (and put a 'pass' in there). You might also want to
> remove all files in WebKit/Sessions/.
> I think that was basically what Vladimir was saying.
> You can also accomplish the same thing without hacking on
> SessionMemoryStory. You can create a subclass of SessionMemoryStore and
> override storeAllSessions() as 'pass'. If your class name is
> "SessionAtLeeStore", then you'll need to set Application.config's
> 'SessionStore' setting to 'AtLee' and add SessionAtLeeStore to the list of
> classes found in Application.py (search for SessionMemoryStore and you'll
> find it).
> We should eliminate that last part since we could load the module with the
> class name instead of requiring the list of available classes appearing in
> Application.py (e.g., hard coding). Then you could really do this without
> modifying the original source at all.
> And finally, if you wanted one connection per app (instead of per user),
> you could do this in SitePage:
> def __init__(self):
> self._conn = None
> def conn(self):
> if self._conn is None:
> app = self.application()
> if not hasattr(app, 'conn'):
> app.conn = MySQLdb(db='whatever')
> self._conn = app.conn
> return self._conn
> Now all pages can say self.conn() to get the connection, but it's always
> the same instance. The above method still caches the reference per Page
> This assumes all your pages ultimately inherit from some common page
> often called SitePage. This is a really good practice to follow as you can
> put utility methods and even common look-and-feel things in SitePage as
> your site grows.
> In a future WebKit, it will be easier to create custom subclasses of
> Application, which would make the above code cleaner. Valdimir submitted a
> patch for this recently, but I haven't had a chance to look at it yet.
> Hope that helped,
> Webware-discuss mailing list