1- # $Id: back_sqlite.py,v 1.35 2004-10-16 12:52:53 a1s Exp $
1+ # $Id: back_sqlite.py,v 1.36 2004-10-31 09:57:10 a1s Exp $
22'''Implements a backend for SQLite.
33
44See https://pysqlite.sourceforge.net/ for pysqlite info
@@ -55,6 +55,21 @@ class Database(rdbms_common.Database):
5555 hyperdb .Multilink : lambda x : x , # used in journal marshalling
5656 }
5757
58+ def sqlite_busy_handler (self , data , table , count ):
59+ """invoked whenever SQLite tries to access a database that is locked"""
60+ if count == 1 :
61+ # use a 30 second timeout (extraordinarily generous)
62+ # for handling locked database
63+ self ._busy_handler_endtime = time .time () + 30
64+ elif time .time () > self ._busy_handler_endtime :
65+ # timeout expired - no more retries
66+ return 0
67+ # sleep adaptively as retry count grows,
68+ # starting from about half a second
69+ time_to_sleep = 0.01 * (2 << min (5 , count ))
70+ time .sleep (time_to_sleep )
71+ return 1
72+
5873 def sql_open_connection (self ):
5974 '''Open a standard, non-autocommitting connection.
6075
@@ -70,7 +85,7 @@ def sql_open_connection(self):
7085 conn = sqlite .connect (db = db )
7186 # set a 30 second timeout (extraordinarily generous) for handling
7287 # locked database
73- conn .db .sqlite_busy_timeout ( 30 * 1000 )
88+ conn .db .sqlite_busy_handler ( self . sqlite_busy_handler )
7489 cursor = conn .cursor ()
7590 return (conn , cursor )
7691
0 commit comments