gpt4 book ai didi

perl - DBD::SQLite:数据库被锁定:如何重试?

转载 作者:行者123 更新时间:2023-12-03 16:30:26 26 4
gpt4 key购买 nike

我并行使用 SQLite 数据库。主要用于阅读——这意味着一切都很好。但也用于写入和删除表格。然后突然我在随机时间得到这个(这表明一个竞争条件 - 这是预期并行运行的东西):

Error: near line 1: database is locked

现在我知道在 10 毫秒内数据库不会被锁定,所以我想等待 10 毫秒再试一次,但我找不到捕获该错误的方法。

我怎样才能发现这个错误?

最佳答案

更新
请注意Georg Mavridis' comment多于
听起来您的子进程正在共享相同的数据库连接并相互锁定
如果您想要真正的并行性,那么您需要与数据库建立多个连接。 SQLite 将对来自不同连接的请求进行排队并为您解决冲突,除非该行为被禁用。

您需要设计 DBI 应用程序的错误处理。 connect 中可以指定三个选项。称呼

  • PrintError - 默认情况下 - 如果出现错误,这将导致发出警告
  • RaiseError — 默认关闭 — 如果出现错误,这将导致进程终止
  • HandleError — 默认未设置 — 此选项必须设置为子程序引用,如果出现错误,将调用该子程序

  • 如果您希望没有数据库错误,那么最好使用
    my $dbh = DBI->connect( ..., { PrintError => 0, RaiseError => 1 } )
    然后,您可以为可能出错的部分代码启用错误处理,并且您想尝试修复它
    DBI documentation for the RaiseError option说这个

    If you want to temporarily turn RaiseError off (inside a library function that is likely to fail, for example), the recommended way is like this:

    {
    local $h->{RaiseError}; # localize and turn off for this block
    ...
    }

    这样, RaiseError选项在右大括号处隐式重新打开,并且在 block 中您可以检查 execute 返回的值,表示操作是否成功, errstr ,它提供了持续错误类型的详细信息。然后你可以在 Perl 中编写重试代码来做任何你想做的事情
    标准 sleep call 将暂停一个进程,但粒度为一秒。如果您无法让程序在重试之间等待那么长时间,请查看 usleep来自 Time::HiRes 的函数模块,它需要一微秒的倍数

    关于perl - DBD::SQLite:数据库被锁定:如何重试?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41143514/

    26 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com