我们在Xamarin应用程序中使用SQLite.NET PCL。
当通过插入多个表来使数据库处于压力之下时,我们看到抛出了BUSY异常。
任何人都可以解释BUSY和LOCKED之间的区别吗?是什么导致数据库忙?
我们的代码使用与使用以下代码创建的数据库的单个连接:
var connectionString = new SQLiteConnectionString(GetDefaultConnectionString(),
_databaseConfiguration.StoreTimeAsTicks);
var connectionWithLock = new SQLiteConnectionWithLock(new SQLitePlatformAndroid(), connectionString);
return new SQLiteAsyncConnection (() => { return connectionWithLock; });
答案 0 :(得分:5)
所以我们的问题结果是,虽然我们已经确保在课堂上我们写了它只创建了与数据库的单一连接,但我们没有确保这个类是单身,因此我们仍在创建与数据库的多个连接。一旦我们确定它是单身,那么繁忙的错误就会停止
我从中得到的是:
锁定意味着你有多个线程试图访问数据库,代码本质上不是线程安全的。
忙碌意味着你有一个线程正在等待另一个线程完成,你的代码是线程安全的,但你看到使用数据库的争论。
答案 1 :(得分:3)
...当前操作无法继续,因为所需资源已锁定 ...
我假设你正在使用异步样式的插入并且在不同的线程上,因此插入超时等待不同插入的锁定完成。您可以使用同步插入来避免这种情况。我个人在需要时通过创建FIFO队列并在专用线程上同步使用该队列来避免这种情况。您还可以通过在让Exception
起作用之前重试X事务X次来处理此情况。
每当SQLite返回SQLITE_BUSY或SQLITE_IOERR_BLOCKED错误代码时,SQLiteBusyException都会抛出一个特殊异常。这些代码意味着当前操作无法继续,因为所需资源已被锁定。
当通过SQLiteConnection.setBusyTimeout(long)设置超时时,SQLite将在返回此错误之前尝试在指定的超时期间获取锁定。