I am trying to set the lastupdated timestamp in db2 to current timestamp everytime the section of my script runs
datetimes = datetime.now()
datetime1 = datetimes.strftime("%Y-%m-%d %H:%M:%S")
datetime2 = datetime.strptime(datetime1,'%Y-%m-%d %H:%M:%S')
print(type(datetime2))
print(datetime2)
sql = "update salesorder set LASTUPDATEUSER = 'Testing' and LASTUPDATEDATETIME = ? where code ='0888' "
prepared = ibm_db.prepare(conn, sql)
returnCode = ibm_db.bind_param(prepared,1,datetime2, ibm_db.SQL_PARAM_INPUT,ibm_db.SQL_CHAR)
if returnCode == False:
print("unable to bind")
#ibm_db.execute(upstmt)
#param = param1
returnCode = ibm_db.execute(prepared)
if returnCode == False:
print("unable to execut")
on running this script I get the error
Traceback (most recent call last):
File "new.py", line 27, in <module>
returnCode = ibm_db.execute(prepared)
SQLCODE=-420atement Execute Failed: [IBM][CLI Driver][DB2/LINUXX8664] SQL0420N Invalid character found in a character string argument of the function "BOOLEAN". SQLSTATE=22018
I have tried multiple resolutions like passing the datetime as a string as well but no luck with solving the issue this is the timestamp format used in db2 '2020-02-21 13:37:37'
If someone can please provide a way to resolve this that would be really helpful
Your update stmt is wrong. Change:
update salesorder
set LASTUPDATEUSER = 'Testing' and LASTUPDATEDATETIME = ?
where code ='0888'
to:
update salesorder
set LASTUPDATEUSER = 'Testing'
, LASTUPDATEDATETIME = ?
where code ='0888'
or:
update salesorder
set (LASTUPDATEUSER, LASTUPDATEDATETIME) = ('Testing', ?)
where code ='0888'
The error message you get is puzzling, but is due to the fact that you are trying to evaluate a Boolean from a string:
db2 "values 'testing' and current_timestamp = current_timestamp"
1
--
SQL0420N Invalid character found in a character string argument of the
function "BOOLEAN". SQLSTATE=22018
compare with
db2 "values true and current_timestamp = current_timestamp"
1
--
1
even if that succeded you would get an error trying to assign a timestamp column a boolean value.
I guess older versions of Db2 would have objected during prepare, but nowadays type checking is much more relaxed, which leads to very counter intuitive error messages from time to time
That said, you may want to look into doing:
update salesorder
set (LASTUPDATEUSER, LASTUPDATEDATETIME) = ('Testing', current_timestamp)
where code ='0888'
Your code would then be reduced to:
sql = """update salesorder
set (LASTUPDATEUSER, LASTUPDATEDATETIME) = ('Testing', current_timestamp)
where code ='0888'"""
prepared = ibm_db.prepare(conn, sql)
returnCode = ibm_db.execute(prepared)
if returnCode == False:
print("unable to execut")
As a side node, I find it a bit cumbersome to explicitly bind parameters and usually just do:
ibm_db.execute(prepared, (param1, ...))
If the purpose is just to update the timestamp whenever the row is changed, concider a trigger:
create trigger trg1
no cascade before update on salesorder
referencing new as n
for each row
set n.LASTUPDATEDATETIME = current_timestamp
If you change your update statement to:
update salesorder
set LASTUPDATEUSER = 'Testing'
where code ='0888'
the trigger will do that for you:
db2 "select * from salesorder"
LASTUPDATEUSER LASTUPDATEDATETIME CODE
-------------------- -------------------------- -----
Testing 2020-04-11-11.51.22.055602 0888
1 record(s) selected.
./aa.py
db2 "select * from salesorder"
LASTUPDATEUSER LASTUPDATEDATETIME CODE
-------------------- -------------------------- -----
Testing 2020-04-11-11.58.50.222753 0888
1 record(s) selected.
Dependent on your version of Db2, you may also look into declaring the column as:
FOR EACH ROW ON UPDATE AS ROW CHANGE TIMESTAMP
You probably want GENERATED ALWAYS, but I don't think you can alter the column to that, so you will have to do a bit more work to get that in place.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.