Skip to content

Commit

Permalink
add support for positional parameters in stored procedures
Browse files Browse the repository at this point in the history
  • Loading branch information
damoxc committed Apr 30, 2010
1 parent f58c385 commit b3bbb7b
Show file tree
Hide file tree
Showing 3 changed files with 26 additions and 10 deletions.
2 changes: 2 additions & 0 deletions ChangeLog
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@ Thu Apr 29 16:20:00 2010 Damien Churchill <[email protected]>
* _mssql.py:
+ feature: add support for nullable ints and nullable bits in
stored procedure parameters.
+ feature: add support for positional parameters in stored
procedures.
* version 1.9.909

Wed Apr 28 11:10:00 2010 Damien Churchill <[email protected]>
Expand Down
3 changes: 2 additions & 1 deletion _mssql.pxd
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
from sqlfront cimport DBPROCESS, BYTE


cdef void log(char *, ...)

cdef struct _mssql_parameter_node:
Expand Down Expand Up @@ -49,5 +48,7 @@ cdef class MSSQLStoredProcedure:
cdef MSSQLConnection conn
cdef DBPROCESS *dbproc
cdef char *procname
cdef int param_count
cdef bool had_positional
cdef dict params
cdef _mssql_parameter_node *params_list
31 changes: 22 additions & 9 deletions _mssql.pyx
Original file line number Diff line number Diff line change
Expand Up @@ -1049,14 +1049,15 @@ cdef class MSSQLStoredProcedure:
# We firstly want to check if tdsver is >= 8 as anything less
# doesn't support remote procedure calls.
if connection.tds_version < 7:
raise MSSQLDriverException("Stored Procedures aren't " \
raise MSSQLDriverException("Stored Procedures aren't "
"supported with a TDS version less than 7.")

self.conn = connection
self.dbproc = connection.dbproc
self.procname = name
self.params = dict()
self.params_list = NULL
self.param_count = 0
self.had_positional = False

with nogil:
rtc = dbrpcinit(self.dbproc, self.procname, 0)
Expand Down Expand Up @@ -1087,6 +1088,7 @@ cdef class MSSQLStoredProcedure:
cdef int length = -1
cdef RETCODE rtc
cdef BYTE status, *data
cdef char *param_name
cdef _mssql_parameter_node *pn
log("_mssql.MSSQLStoredProcedure.bind()")

Expand All @@ -1096,10 +1098,6 @@ cdef class MSSQLStoredProcedure:
# Convert the PyObject to the db type
data = self.conn.convert_python_value(value, &dbtype, &length)

# Store the value in the parameters dictionary for returning
# later.
self.params[name] = value

# We support nullable parameters by just not binding them
if dbtype in (SQLINTN, SQLBITN) and data == NULL:
return
Expand Down Expand Up @@ -1142,16 +1140,31 @@ cdef class MSSQLStoredProcedure:
if status != DBRPCRETURN:
max_length = -1

if name:
param_name = name
if self.had_positional:
raise MSSQLDriverException('Cannot bind named parameter after positional')
else:
param_name = ''
self.had_positional = True

IF PYMSSQL_DEBUG == 1:
fprintf(stderr, "\n--- rpc_bind(name = '%s', status = %d, " \
"max_length = %d, data_type = %d, data_length = %d, "
"data = %x)\n", <char *>name, status, max_length, dbtype,
"data = %x)\n", param_name, status, max_length, dbtype,
length, data)

with nogil:
rtc = dbrpcparam(self.dbproc, name, status, dbtype,
rtc = dbrpcparam(self.dbproc, param_name, status, dbtype,
max_length, length, data)
return check_cancel_and_raise(rtc, self.conn)
check_cancel_and_raise(rtc, self.conn)

# Store the value in the parameters dictionary for returning
# later, by name if that has been supplied.
if name:
self.params[name] = value
self.params[self.param_count] = value
self.param_count += 1

def execute(self):
cdef RETCODE rtc
Expand Down

0 comments on commit b3bbb7b

Please sign in to comment.