I have just joined this mailing list, because searching the archives I have not found much related to locking. I am not completely new to SQLite, having previously used it when I wrote my latest version of a chat program, where I migrated the database over to from mysql.
In my first attempt to do this, I tried to completely manage a single users transaction (write a message, move between rooms etc) in the apache thread which handled the original page or subsequent ajax requests and thought, but was subsquently proven wrong that SQLlite would queue when there was contention for a lock. In the end I implemented a loop on BEGIN EXCLUSIVE which failed with a SQLITE_BUSY by sleeping for a random period of a few milliseconds and trying again. However once I got up to a few online test users (about 40 each speaking every 30 seconds or so) , interaction between the threads became too much. I ended up in almost continual busy mode backing off and retrying when the locks were taken. In the end I implemented a Server Process based approach to get round that (and it worked extremely well). I am about to try and port two more web/ajax php/javascript applications from postgres to sqlite - the rationale being that having the local database file accessible directly rather than some amorphous set behind a server will be easier to manage. Also both of these have the characteristic that there will be a lot less parallelism. However there will not be none, and I will still have to allow for the fact that users will be looking at the database in parallel. In fact both of the applications have the property that they will do quite a bit of querying of the database to build up the web pages they look at and that normally a single user will conduct the majority of the update transactions. One of these applications is a personal financial planning package where I expect normally a single user to update the data, although I don't want to rule out maybe a couple of people doing it. I already have application level checks to check the integrity of data related to parallel updates but I need to plan for potentially the database clashing when two people attempt an update transaction at the same time. I think the answers related to the more complex application discussed below will enable me to do this. The other is an (American) football results picking competition. In this the majority of the update transactions are the performed by a (single) administrator with the majority of the users just performing queries to check for matches and past results. Once a week (or maybe a two or three times if they decide the initial picks are wrong) each user in the competition will do a single transaction to update all their picks for the week. I want to design an optimal locking strategy and a series of simple middleware functions to handle the occassional requirements to back off and retry. However I am not sure from the documentation exactly when I might receive a SQL_BUSY failure in the cases where a) The administrator commits a change he has setup on his web page. I would expect to him (or rather the ajax request resulting from him hitting the SAVE button) to do a BEGIN TRANSACTION (not yet sure if its optimal to do an IMMEDIATE or EXCLUSIVE at this point). What happens to i) This request if there are users still completing queries to read the data. IE does it immediately fail SQLITE_BUSY or will it wait a short period whilst any current SELECT statements complete ii) Users who are performing a series of SELECT statements (with complex joins) and for which the Administrators BEGIN TRANSACTION occurs in the middle of the series. And as a follow on iii) Should I really be doing a BEGIN TRANSACTION before that series of SELECTS to hold off the administrator here and ensure the user gets the entire page displayed. When would the administrator see the SQLITE_BUSY if he did a BEGIN IMMEDIATE b) As the user submits his picks I would again do a BEGIN TRANSACTION (or may be a BEGIN EXLUSIVE or BEGIN IMMEDIATE and other users and the administrator are doing their things in parallel. I am aware of the staged locking process, what I am unclear about is that does failure to get the locks at ANY of these stages cause an SQLITE_BUSY to occur? I am actually not using C, but the php routines for this. I have my suspicions, but I can't find it explicity stated anywhere that the PHP::SQLITE3 module behaves exactly like the C routines but that using PHP::PDO abstraction layer handles the lock detection and retry itself (my only evidence is that the php manual for bool *PDO::setAttribute* ( int $attribute , mixed <http://uk.php.net/manual/en/language.pseudo-types.php#language.types.mixed> $value ) ... /PDO::ATTR_TIMEOUT/: Specifies the timeout duration in seconds. Not all drivers support this option, and it's meaning may differ from driver to driver. For example, sqlite will wait for up to this time value before giving up on obtaining an writable lock, but other drivers may interpret this as a connect or a read timeout interval. Requires int <http://uk.php.net/manual/en/language.types.integer.php> . which sort of implies that it does). I presume many people have experience of the sort of application pattern I am describing. What approach to managing locking do you take? -- Alan Chandler http://www.chandlerfamily.org.uk _______________________________________________ sqlite-users mailing list sqlite-users@sqlite.org http://sqlite.org:8080/cgi-bin/mailman/listinfo/sqlite-users