PL/Tcl 函数内部或从 PL/Tcl 函数调用的 Tcl 代码可能会引发错误,这可能是通过执行某些无效操作,或者使用 Tcl 的 error 命令或 PL/Tcl 的 elog 命令生成错误。可以使用 Tcl 的 catch 命令在 Tcl 中捕获此类错误。如果错误未被捕获,而是允许传播到 PL/Tcl 函数执行的顶层,则会将其报告为函数调用查询中的 SQL 错误。
相反,PL/Tcl 的 spi_exec、spi_prepare 和 spi_execp 命令中发生的 SQL 错误会被报告为 Tcl 错误,因此可以使用 Tcl 的 catch 命令捕获它们。(每个 PL/Tcl 命令都会在其子事务中运行 SQL 操作,并在错误时回滚,以便自动清理任何部分完成的操作。)同样,如果错误在没有被捕获的情况下传播到顶层,则会再次变成 SQL 错误。
Tcl 提供了一个 errorCode 变量,它可以以易于 Tcl 程序解释的形式表示有关错误的其他信息。内容采用 Tcl 列表格式,第一个词标识报告错误的子系统或库;除此之外,内容的具体含义由各个子系统或库自行决定。对于 PL/Tcl 命令报告的数据库错误,第一个词是 POSTGRES,第二个词是 PostgreSQL 版本号,其他词是提供有关错误的详细信息的字段名称/值对。始终会提供 SQLSTATE、condition 和 message 字段(前两个表示错误代码和条件名称,如 附录 A 中所示)。可能存在的字段包括 detail、hint、context、schema、table、column、datatype、constraint、statement、cursor_position、filename、lineno 和 funcname。
处理 PL/Tcl 的 errorCode 信息的便捷方法是将其加载到数组中,以便字段名称成为数组下标。用于执行此操作的代码可能如下所示
if {[catch { spi_exec $sql_command }]} {
if {[lindex $::errorCode 0] == "POSTGRES"} {
array set errorArray $::errorCode
if {$errorArray(condition) == "undefined_table"} {
# deal with missing table
} else {
# deal with some other type of SQL error
}
}
}
(双冒号明确指定 errorCode 是一个全局变量。)
如果您发现文档中的任何内容不正确、与您使用特定功能的经验不符或需要进一步澄清,请使用此表格报告文档问题。