表输入参数和标量输出参数

时间:2019-01-03 18:42:50

标签: python sql stored-procedures hana python-db-api

我有下表和以下存储过程(简化为演示问题所需的基本知识):

CREATE TABLE T(C INT);
CREATE PROCEDURE PROC(IN T TABLE(C INT), OUT X INT) AS BEGIN
X = 5;
END;

从HANA Studio中,我可以CALL PROC(T, ?)并获得5。但是,我还没有找到从hdbcli Python driver中进行此操作的任何好方法。

callproc似乎没有任何方法可以接受表参数。将表名作为字符串传递不起作用:

>>> from hdbcli import dbapi
>>> conn = dbapi.connect(userkey='testkey')
>>> cur = conn.cursor()
>>> cur.callproc('PROC', ('T', '?'))
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/usr/local/lib/python3.6/site-packages/hdbcli/dbapi.py", line 498, in callproc
    ret = self.__callproc(callproc, parameters)
  File "/usr/local/lib/python3.6/site-packages/hdbcli/dbapi.py", line 257, in __callproc
    return self.__cursor.callproc(operation, parameters)
hdbcli.dbapi.Error: (8, 'invalid argument: Input parameter is inadequate as table parameter: line 1 col 13 (at pos 12)')

execute可以执行该过程,但是似乎没有提供任何访问输出参数的方法。没有设置结果:

>>> cur.execute('CALL PROC(T, ?)')
True
>>> cur.fetchone()
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/usr/local/lib/python3.6/site-packages/hdbcli/dbapi.py", line 434, in fetchone
    raise ProgrammingError(0,"No result set")
hdbcli.dbapi.ProgrammingError: (0, 'No result set')

我找到了一个非常尴尬的解决方法,我将其发布为答案,但是它非常冗长,并且无法与默认参数值很好地交互。是否有访问输出参数的好方法?

1 个答案:

答案 0 :(得分:1)

我发现的一种解决方法是将过程包装在一个匿名块中,然后将标量放入匿名块中的SELECT中:

>>> cur.execute('''
... DO BEGIN
... DECLARE X INT;
... T_VAR = SELECT * FROM T;
... CALL PROC(:T_VAR, X);
... SELECT :X FROM DUMMY;
... END''')
True
>>> cur.fetchone()
(5,)

这是很多额外的输入。我们可以保存一个包装程序来为我们做这件事,而不是每次都重复匿名块,但这会导致很多包装程序,如果您要包装的程序很多。另外,它不能与默认值一起很好地使用。如果您执行以下步骤:

CREATE PROCEDURE PROC2(OUT X INT, IN T TABLE(C INT) DEFAULT T) AS BEGIN
X = 5;
END;

您通常可以将其称为CALL PROC2(?),但是如果没有传递T的显式值,则不能从匿名块或存储过程中调用它:

>>> cur.execute('''
... DO BEGIN
... DECLARE X INT;
... CALL PROC2(X);
... SELECT :X FROM DUMMY;
... END''')
Traceback (most recent call last):
  File "<stdin>", line 6, in <module>
  File "/usr/local/lib/python3.6/site-packages/hdbcli/dbapi.py", line 363, in execute
    ret = self.__execute(operation)
  File "/usr/local/lib/python3.6/site-packages/hdbcli/dbapi.py", line 249, in __execute
    ret = self.__cursor.execute(operation, parameters=parameters, iscall=iscall, scrollable=self._scrollable)
hdbcli.dbapi.Error: (7, 'feature not supported: Only table variable is allowed in input parameter in a nested call: line 1 col 15 (at pos 14)')

由于默认值T,该异常发生了。