[Catalyst] Duplicate entries with C::P::Session::Store::DBIC and MySQL

Matt S Trout dbix-class at trout.me.uk
Mon Jul 28 22:33:44 BST 2008


On Mon, Jul 28, 2008 at 01:03:52PM +0200, Tobias Kremer wrote:
> Hi list,
> 
> I've written about this at least once in the past and still haven't been able to
> figure out a proper solution to the problem.
> 
> We're getting loads (up to 30-40 per day) of the following fatal error:
> 
> Duplicate entry 'flash:***' for key 1 [for Statement "INSERT INTO sessions2 (id)
> VALUES (?)" with ParamValues: 0='flash:***'] at
> /usr/local/lib/perl5/site_perl/5.8.8/Catalyst/Plugin/Session/Store/DBIC/Delegate.pm
> line 52"
> 
> I suppose that most of you are never seeing this error because you're using
> 
> a) a sane database with proper transactions (although I'm
>    unsure DBICs find_or_create makes use of them transparently). I'm
>    (at least for the moment) stuck with MySQL and a MyISAM session table.
>    Yeah, I know ...
> 
> b) a storage backend that doesn't bother if there are duplicate
>    entries (FastMmap, Memcached, File, etc) and just overwrites.
> 
> The cause obviously seems to be concurrent requests by the same user - mostly
> the impatient "F5-hitter"-type :)) So what happens is basically:
> 
> 1) Request 1 comes in, selects for a flash-entry in the
>    session table and doesn't find anything.
> 
> 2) Request 2 comes in, does the same and comes back with empty hands, too.
> 
> 3) Request 1 inserts its flash values into the table.
> 
> 4) Request 2 tries to do the same, fails and the user gets a fatal error message
> although nothing _that_ bad happened :(
> 
> Now, I know that the time window for this to happen is supposed to be quite
> small but the amount of errors I'm getting is worrying. So, IMHO the error
> should be handled by the application in a more gentle way (as opposed to
> throwing a fatal error) because AFAICT nothing bad will happen if the session
> data is just overwritten (which is what most other P::Session backends will do
> anyway).
> 
> Is there anything speaking against wrapping line 52 of the DBIC backend class
> with an eval to trap this duplicate error and ignore it silently (or just warn
> about it) except the fact that it's trying to fix something that probably
> should be the database's task?

Don't see why not.

The interesting question i how we make a test for it.

Mm ... ah. How about a debugcb sub that checks for the SELECT and does the
insert in the background so the row's there when the DBIC-driven INSERT
happens?

-- 
      Matt S Trout       Need help with your Catalyst or DBIx::Class project?
   Technical Director                    http://www.shadowcat.co.uk/catalyst/
 Shadowcat Systems Ltd.  Want a managed development or deployment platform?
http://chainsawblues.vox.com/            http://www.shadowcat.co.uk/servers/



More information about the Catalyst mailing list