我有一个运行DB2 SQL文件的Bash Shell脚本。这个SQL文件的工作是用这个SQL文件的任何内容完全替换数据库表的内容。
但是,如果在接收的文件中发现错误,我还需要保留数据库表的内容。例如,假设我的表当前如下所示:
| 我的_表格|C1|C2|
| - ------|- ------|- ------|
| 第0行|十五|二十七|
| 行1|十九|二十个|
假设我有一个输入文件,看起来像这样:
15,28
34,90
"a string that's obviously not supposed to be here"
54,23
如果我用这个输入文件运行脚本,那么表应该和以前完全一样,根本不使用文件的内容。
但是,当我运行脚本时,我观察到的行为不是这样的:相反,MY_TABLE的内容将被替换为输入文件的所有有效行,因此表的新内容变为:
| 我的_表格|C1|C2|
| - ------|- ------|- ------|
| 第0行|十五|二十八|
| 行1|三十四|九十|
| 行2|五十四|二十三|
在我的脚本逻辑中,我显式地禁用脚本中接收文件的部分的自动提交,并且只有在检查sql执行没有返回错误之后才调用提交;如果它确实导致了错误,我就调用rollback,尽管如此,当错误发生时,表的内容会被替换,就好像根本没有调用rollback命令,而是调用了commit一样。
我的剧本哪里有问题?
脚本.ksh
SQL_FILE=/app/scripts/script.db2
LOG=/app/logs/script.log
# ...
# Boilerplate to setup the connection to the database server
# ...
# +c: autocommit off
# -v: echo commands
# -s: Stop if errors occur
# -p: Show prompt for interactivity (for debugging)
# -td@: use '@' as the statement delimiter in the file
db2 +c -s -v -td@ -p < $SQL_FILE >> $LOG
if [ $? -gt 2 ];
then echo "An Error occurred; rolling back the data" >> $LOG
db2 "ROLLBACK" >> $LOG
exit 1
fi
# No errors, commit the changes
db2 "COMMIT" >> $LOG
脚本. db2
ingest from file '/app/temp/values.csv'
format delimited by ','
(
$C1 INTEGER EXTERNAL,
$C2 INTEGER EXTERNAL
)
restart new 'SCRIPT_JOB'
replace into DATA.MY_TABLE
(
C1,
C2
)
values
(
$C1,
$C2
)@
2条答案
按热度按时间bvjveswy1#
根据OP的建议,添加以下内容作为回答:
根据ingest command的db2文档,
+c: autocommit off
似乎无法正常工作:xpcnnkqh2#
您可能需要设置
warningcount 1
option,这将导致命令在第一次出现错误或警告后终止。默认行为是忽略所有错误(warningcount 0
)继续处理。