我尝试将transactions
与prepared statements
一起使用,以更新表INVENTORY
,其中:
CREATE TABLE "INVENTORY" (
"product" VARCHAR NOT NULL,
"version" VARCHAR NOT NULL,
"lot" VARCHAR,
"barcode" VARCHAR,
"quantity" INTEGER,
PRIMARY KEY ("barcode")
);
我想要做的是插入一个新行,但如果在我的表中存在具有相同主键的行,则通过添加旧值+新行来更新它。
String sqInsert = "INSERT INTO INVENTORY VALUES ('100541026044','01','301610101','10054102604401301610101','5000')";
String sqUpdate = "UPDATE INVENTORY set quantity = quantity + 5000 where barcode='10054102604401301610101'";
// transaction block start
c.setAutoCommit(false);
stm = c.prepareStatement(sqInsert);
System.out.println("try to insert");
result = stm.executeUpdate();
System.out.println("try to update");
stm = c.prepareStatement(sqUpdate);
result = stm.executeUpdate();
c.commit(); //transaction block end
System.out.println("Done!");
在我的表中存在barcode=10054102604401301610101
的行,所以我希望执行更新。但是,我得到了
try to insert
Error inserting products :[SQLITE_CONSTRAINT] Abort due to constraint violation (UNIQUE constraint failed: INVENTORY.barcode)
注意:(我没有设置查询中的值,但使用stm.setString(1, "string");
)我只想缩短此处的代码
答案 0 :(得分:2)
当然,由于条形码上的重复主键,它将失败。 首先进行更新
stm = c.prepareStatement(sqUpdate);
result = stm.executeUpdate();
然后检查结果的值,该值将是受更新影响的行数。如果它为零,则具有给定条形码的产品不存在,因此在更新后
if (0==result) {
stm = c.prepareStatement(sqInsert);
stm.executeUpdate();
}
您希望将所有内容放在try {} catch {}下,以避免资源泄漏或使连接无法使用
try {
c.setAutoCommit(false);
stm = c.prepareStatement(sqUpdate);
result = stm.executeUpdate();
if (0==result) {
stm.close();
stm = null;
stm = c.prepareStatement(sqInsert);
stm.executeUpdate();
stm.close();
stm = null;
}
c.commit();
} catch (SQLException e) {
if (stm!=null) stm.close();
c.rollback();
}