ibm_db.callprocedure throwing UnicodeDecodeError: 'utf-8' codec can't decode byte
c-muncan opened this issue · 10 comments
- Operating System Name: z/OS 2.4
- db2level output from clidriver if in use:
- Target Db2 Server Version: V12 & V13
- Python Version: 3.11.5
- ibm_db version:
- TST1:/u/a463:->py -m pip list
Package Version
cffi 1.14.6
cryptography 3.3.2
dateutils 0.6.12
ebcdic 1.1.1
ibm-db 3.2.0
numpy 1.23.4.post0
pandas 1.5.1.post3
pip 23.2.1
pycparser 2.20
python-dateutil 2.8.2
pytz 2022.4
regex 2023.6.3
setuptools 65.6.3
six 1.16.0
XlsxWriter 3.1.2
zoautil-py 1.2.3
zos-util 1.0.1
- For non-Windows, output of below commands:
uname
OS/390
uname -m
8562 - Value of below environment variables if set:
IBM_DB_HOME=SFDB.DSN124
PATH=/bin:/usr/lpp/Printsrv/bin:/usr/lpp/java/current_31/bin:/usr/lpp/ixm/IBM/xml4c-5_7/bin:/usr/lpp/IBM/zoautil/bin:/usr/lpp/Rocket/rsusr/ported/bin:/usr/lpp/c
yp/v3r11/pyz/bin:.
CLASSPATH=.:/usr/lpp/mqm:/usr/lpp/smp/classes:/usr/lpp/IBM/zoautil/lib
LIBPATH=/lib:/usr/lib:/usr/lpp/mqm/:/usr/lpp/Printsrv/lib:/usr/lpp/ixm/IBM/xml4c-5_7/lib:/usr/lpp/IBM/zoautil/lib:/usr/lpp/Rocket/rsusr/ported/lib:/usr/lpp/cyp/
v3r11/pyz/lib:.
_CEE_RUNOPTS=FILETAG(AUTOCVT,AUTOTAG) POSIX(ON)
DSNAOINI=/u/a463/odbc_tst1.ini
ls -laT $DSNAOINI
b binary T=off -rw-r----- 1 A463 USSDFTG 209 Apr 1 14:20 odbc_tst1.ini
file contents
[COMMON]
MVSDEFAULTSSID=T2D2
CONNECTTYPE=1
MULTICONTEXT=2
FLOAT=IEEE
CURRENTAPPENSCH=ASCII
DIAGTRACE=1
DIAGTRACE_NO_WRAP=0
DIAGTRACE_BUFFER_SIZE=2000000
[T2D2]
AUTOCOMMIT=1
MVSATTACHTYPE=CAF
PLANNAME=DSNACLI
I am having errors for a few of the functions. I don't get this in my mainframe zDT ADCD environment. We are just rolling out Python and I'm having these new issues in this environment which I didn't have before.
ibm_db.tables sample code
import sys
import traceback
import os
import ibm_db
try:
ibm_db.connect('','','')
except Exception:
print(traceback.format_exc())
print("------")
try:
db2_conn = ibm_db.connect('','','')
except Exception:
print(traceback.format_exc())
print("------")
exit(-1)
print("------------------------------------------------------")
print('FETCH ASSOC')
print("------------------------------------------------------")
schemaName = "ZBQSTSOT"
resultSet = ibm_db.tables(db2_conn, None, schemaName, '%', None)
dataRecord = ibm_db.fetch_assoc(resultSet)
while dataRecord:
# print("Table schema : {}" .format(dataRecord['TABLE_SCHEM']))
print("Table name : {}" .format(dataRecord['TABLE_NAME']))
print("Table type : {}" .format(dataRecord['TABLE_TYPE']))
dataRecord = ibm_db.fetch_assoc(resultSet)
print("------------------------------------------------------")
ibm_db.close(db2_conn)
output
------------------------------------------------------
FETCH ASSOC
------------------------------------------------------
UnicodeDecodeError: 'utf-8' codec can't decode byte 0x85 in position 40: invalid start byte
The above exception was the direct cause of the following exception:
Traceback (most recent call last):
File "/u/a463/db2fetch_assoc.py", line 25, in <module>
resultSet = ibm_db.tables(db2_conn, None, schemaName, '%', None)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
SystemError: <built-in function tables> returned a result with an exception set
whenever calling stored procedures via the ibm_db.callprocedure
fetch_both works just fine. so does field_name, but callprocedure seems to be failing me always. I've even tried other scripts which yield similar results.
db2util.py
import sys
import traceback
import os
import ibm_db
conn=ibm_db.connect('','','')
stmtTxt='LISTDEF LIST_TS INCLUDE TABLESPACE ZBQSTSDZ.BQDMYTS RUNSTATS TABLESPACE LIST LIST_TS TABLE (ALL) INDEX(ALL) SHRLEVEL CHANGE UPDATE ALL'
utility_id = 'PYTHUTIL'
restart = 'NO'
retcode = 0
stmt1=None
stmt1, utility_id,restart,stmtTxt,retcode = \
ibm_db.callproc(conn, 'SYSPROC.DSNUTILU', (utility_id,restart,stmtTxt,retcode) )
output
TST1:/u/a463:->py db2util.py
Traceback (most recent call last):
File "/u/a463/db2util.py", line 15, in <module>
ibm_db.callproc(conn, 'SYSPROC.DSNUTILU', (utility_id,restart,stmtTxt,retcode) )
Exception: Describe Param Failed:
db2zparm.py
import sys
import traceback
import os
import ibm_db
conn=ibm_db.connect('','','')
stmt1 =''
db2_member=None
retcode=0
message ='-'
spParms = (db2_member, retcode, message)
stmt1, db2_member, retcode, message = ibm_db.callproc(conn, "SYSPROC.ADMIN_INFO_SYSPARM", spParms)
if (stmt1):
result = ibm_db.fetch_tuple(stmt1)
print(result)
output
TST1:/u/a463:->py db2zparm.py
Traceback (most recent call last):
File "/u/a463/db2zparm.py", line 13, in <module>
stmt1, db2_member, retcode, message = ibm_db.callproc(conn, "SYSPROC.ADMIN_INFO_SYSPARM", spParms)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
Exception: Describe Param Failed:
ultimately it seems to fail whenever calling a stored procedure.
now this does look similar to #852 but I've confirmed my settings quite a fair bit too and am fairly confident it isn't the same problem.
I captured the trace output by updating my ini file to include
DIAGTRACE=1
DIAGTRACE_NO_WRAP=0
DIAGTRACE_BUFFER_SIZE=2000000
It generated a lovely file called "DD:DSNAOTRC" in the directory where I ran my script. ran
./dsnao64t fmt DD\:DSNAOTRC trace.txt
set |grep BPX;set |grep CEE;set |grep STEPLIB;set |grep TAG;set |grep DSNAOINI
_BPXK_AUTOCVT="ON"
_BPX_SHAREAS="YES"
_BPX_SPAWN_SCRIPT="YES"
_BPX_TERMPATH="OMVS"
_CEE_DMPTARG="SYSOUT(7)"
_CEE_RUNOPTS="FILETAG(AUTOCVT,AUTOTAG) POSIX(ON)"
STEPLIB="T2D2.X00T.DSNEXIT:T2D2.X00T.SDSNLOD2:T2D2.X00T.DSNLOAD:TSAPF.TS1.MQ.SCSQAUTH:TSAPF.TS1.MQ.SCSQANLE"
_CEE_RUNOPTS="FILETAG(AUTOCVT,AUTOTAG) POSIX(ON)"
_TAG_REDIR_ERR="txt"
_TAG_REDIR_IN="txt"
_TAG_REDIR_OUT="txt"
DSNAOINI="/u/a463/odbc_tst1.ini"
please take a look and let me know if there's anything else I'm missing?
@jthyssenrocket Please have your comment on this issue. It seems upgrade to python 3.11.5 on z/OS is causing UnicodeDecodeError: 'utf-8' codec can't decode byte 0x85 in position 40: invalid start byte
. Thanks.
I don't have IBM Python 3.11.5, but @c-muncan's programs run fine for me with Python 3.11.4 + ibm_db 3.2.0.
Thanks for checking @jthyssenrocket. If you have a PAX install of 3.11.4 handy, I'd love that.
I've asked our systems folks to see if we can install 3.11.4 or to provide me with the installs so I can install it on our zDT ADCD environment. Presently it is working in our ADCD environment, but there we have Python 3.11.0 + ibm_db 3.2.0
no luck on 3.11.4. we ordered from ShopZ so we get the latest and greatest. can't pick the version you want.
@Earammak not sure if you maybe had a chance to look further into this? Any advice from anyone? it is a huge show stopper for us
Hello @c-muncan
Can you please try to set below content in your odbc_tst1.ini file
[COMMON]
MVSDEFAULTSSID=T2D2
CURRENTAPPENSCH=UNICODE
FLOAT=IEEE
APPLTRACE=1
APPLTRACEFILENAME=u/a463/odbc_appl_trace
DIAGTRACE=0
DIAGTRACE_NO_WRAP=0
DIAGTRACE_BUFFER_SIZE=60000000
[T2D2]
MVSATTACHTYPE=RRSAF
MULTICONTEXT=0
PLANNAME=DSNACLI
[database name of "T2D2" Subsystem]
AUTOCOMMIT=1
CURSORHOLD=1
Also in your .profile file try to set
export _BPXK_AUTOCVT='ON'
export _CEE_RUNOPTS='FILETAG(AUTOCVT,AUTOTAG) POSIX(ON) XPLINK(ON)'
export PATH=/rsusr/python/bin:$PATH
export LIBPATH=/rsusr/python/lib:$PATH
export STEPLIB=T2D2.X00T.DSNEXIT:T2D2.X00T.SDSNLOD2:T2D2.X00T.DSNLOAD:TSAPF.TS1.MQ.SCSQAUTH:TSAPF.TS1.MQ.SCSQANLE
export IBM_DB_HOME=SFDB.DSN124
export DSNAOINI=$/u/a463/odbc_tst1.ini
Please refer the below link to install ibm_db on zos and try to set all the environment variables properly
https://github.com/ibmdb/python-ibmdb/blob/master/INSTALL.md#inszos
Also you can upgrade your ibm_db from 3.2.0 to 3.2.3 and try.
Thank you
I found the problem! My issue was 2-fold.
First, I updated encoding scheme from EBCDIC to UNICODE as per @bchoudhary6415
--> CURRENTAPPENSCH=UNICODE
This then actually output an error message. It turns out, it was a -805 reason code 03 (no matching dbrm) for package DSNCLIMS. I went to bind the package as per DSNTIJCL but was getting -189 explicitly for DSNCLIMS. This is apparently a known issue and has its own KB https://www.ibm.com/support/pages/sqlcode189-rebind-package-dsnaoclidsnclims
Bind with SQLERROR(CONTINUE) to bypass this error.
I did that and then magically everything was working!!!
Just an FYI, in my ADCD environment, I did not have to do any of this, in fact, my CURRENTAPPENCH is set to EBCDIC.
Thank you @jthyssenrocket, @bchoudhary6415 & @bimalkjha ... this saved our project!
@c-muncan I think the root cause for the error message is the missing bind.
We have a known issue with error messages sometimes being returned in an unexpected code page (see #876 (comment)). This issue is still unresolved (CC @bchoudhary6415 ).
Can you retry with CURRENTAPPENCH=ASCII after having done the missing bind? It should work...
@jthyssenrocket yes it does work using CURRENTAPPENSCH=ASCII
now...but is this correct? should I be using ASCII instead of UNICODE? Can you help explain the difference as I would have thought UNICODE was correct rather than ASCII?
Unfortunately, we inconsistently use the regular ODBC APIs which are affected by CURRENTAPPENSCH and the "W" (wide, UTF-16) ODBC APIs which are not affected by CURRENTAPPENSCH.
Where we use the regular APIs we implicitly assume that ODBC returns ASCII, so I strongly recommend CURRENTAPPENSCH=ASCII. For a North American customer it probably doesn't matter if you're using UNICODE (UTF-8) or ASCII.
We have an internal requirement open to switch to consistently use of the ODBC "W" (UTF-16) APIs, but it is a large development item, so no delivery date at this point.
Reference: https://www.ibm.com/docs/en/db2-for-zos/13?topic=data-db2-odbc-unicode-support.