在线文档教程
Sqlite
其他 | Miscellaneous

The Error And Warning Log

错误和警告日志

1.设置错误记录回调

2.接口细节

3.各种错误消息

4.总结

概观

SQLite 可以配置为在出现异常时调用包含错误代码和简洁错误消息的回调函数。这种机制对跟踪在现场很少发生的模糊问题非常有用。鼓励应用程序开发人员在他们的产品中利用 SQLite 的错误日志记录功能,因为它非常低的 CPU 和内存成本,但对调试有很大的帮助。

1.设置错误记录回调

每个进程只能有一个错误记录回调。错误记录回调在开始时使用类似于以下内容的 C 代码进行注册:

sqlite3_config(SQLITE_CONFIG_LOG, errorLogCallback, pData

错误记录器回调函数可能如下所示:

void errorLogCallback(void *pArg, int iErrCode, const char *zMsg){ fprintf(stderr, "(%d) %s\n", iErrCode, zMsg }

上面的例子说明了错误记录器回调的签名。但是,在嵌入式应用程序中,通常不会在 stderr 上打印消息。相反,可以将消息存储在预分配的循环缓冲区中,在调试期间需要诊断信息时可以访问它们。或者也许这些消息可以发送到 Syslog。不知何故,消息需要存储在开发人员可访问的位置,而不是向最终用户显示。

不要误解:将错误记录器消息显示给最终用户在技术上没有任何问题。这些消息不包含敏感或私人信息,必须防止未经授权的查看。相反,这些消息本质上是技术性的,对典型的最终用户来说没有用处或意义。来自错误记录器的消息适用于数据库爱好者。相应地显示它们。

2.接口细节

sqlite3_config(SQLITE_CONFIG_LOG,...)接口的第三个参数(上例中的 “pData” 参数)是指向任意数据的指针。SQLite 将该指针传递给错误记录器回调的第一个参数。如果需要,指针可用于传递应用程序特定的设置或状态信息。或者它可以只是一个被回调忽略的 NULL 指针。

错误记录器回调的第二个参数是整数扩展错误代码。错误记录器的第三个参数是错误消息的文本。错误消息文本存储在调用函数中的固定长度堆栈缓冲区中,因此仅在错误记录器回调函数的持续时间内有效。如果需要保留消息,错误记录器应将此消息的副本保存到永久存储器中。

错误记录器回调应该像信号处理程序一样处理。应用程序应该保存或以其他方式处理错误,然后尽快返回。不应该直接或间接地从错误记录器调用其他 SQLite API。SQLite 不能通过错误记录器回调重入。特别是,当内存分配失败时,会调用错误记录器回调函数,因此尝试在错误记录器内分配内存通常是一个坏主意。甚至不要考虑尝试将错误消息存储在另一个 SQLite 数据库中。

如果需要,应用程序可以使用 sqlite3_log(E,F,..)API 将新消息发送到日志,但不鼓励。sqlite3_log()接口仅供扩展使用,而不是由应用程序使用。

3.各种错误消息

可能发送到错误记录器的错误消息及其确切格式可能会因发行版的不同而发生变化。所以应用程序不应该依赖于任何特定的错误消息文本格式或错误代码。事情并不反复改变,但他们有时会改变。

以下是可能出现在错误记录器回调中的消息种类的部分列表。

  • 任何时候编译 SQL 语句(使用 sqlite3_prepare_v2()或其同级)或运行 SQL 语句(使用 sqlite3_step())都会记录错误。

  • 当发生模式更改时需要重新准备和重新编写准备好的语句时,会使用错误代码 SQLITE_SCHEMA 记录该事件。reparse 和 reprepare 通常是自动的(假设最初使用 sqlite3_prepare_v2()来准备语句,这是推荐的),所以这些记录事件通常是知道正在发生的唯一方法。

  • 无论何时必须恢复数据库,都会记录 SQLITE_NOTICE 消息,因为先前的作者在没有完成其事务的情况下崩溃。在恢复预写日志时恢复回滚日志和 SQLITE_NOTICE_RECOVER_WAL 时,错误代码为 SQLITE_NOTICE_RECOVER_ROLLBACK。

  • 当数据库文件以可能导致数据库损坏的方式重命名或别名时,会记录 SQLITE_WARNING 消息。(请参阅1和2了解更多信息。)

  • 内存不足(OOM)错误条件使用 SQLITE_NOMEM 错误代码生成错误记录事件,并显示一条消息,指出失败的分配请求了多少字节的内存。

  • OS 界面中的 I / O 错误会生成错误记录事件。发送到这些事件的消息给出源代码中产生错误的行号以及存在相应文件时与事件关联的文件名。

  • 当检测到数据库损坏时,调用 SQLITE_CORRUPT 错误记录器回调。与 I / O 错误一样,错误消息文本包含首次检测到错误时原始源代码中的行号。

  • 在 SQLITE_MISUSE 错误上调用错误记录器回调。当在应用程序代码中不一致地检查返回码时,这对于检测应用程序设计问题非常有用。

SQLite 努力保持错误记录器流量低,并且只在真正出现问题时才将消息发送到错误记录器。应用程序可能会通过故意忽略某些他们不关心的错误消息来进一步剔除错误消息流量。例如,频繁更改数据库模式的应用程序可能希望忽略所有 SQLITE_SCHEMA 错误。

4.总结

强烈建议使用错误记录器回调。错误记录器提供的调试信息已被证明在追踪应用程序进入现场后发生的模糊问题时非常有用。错误记录器回调也被证明在捕获错误中很有用,因为 API 返回代码的不一致检查导致应用程序错过了偶尔的错误。鼓励开发人员在开发周期的早期实现错误记录器回调,以便快速发现意外行为,并通过部署保持错误记录器回调的开启。如果错误记录器从未发现问题,则不会造成任何损害。但是,如果未能设置合适的错误记录器,则可能会在稍后影响诊断功能。