es.davy.ai

Preguntas y respuestas de programación confiables

¿Tienes una pregunta?

Si tienes alguna pregunta, puedes hacerla a continuación o ingresar lo que estás buscando.

pyodbc fetchall() no está trayendo todo

Tengo funciones sin servidor de Azure que se conectan a una base de datos SQL. Una de las funciones ejecuta un procedimiento almacenado que, a su vez, ejecuta subprocedimientos, cada uno de los cuales produce un conjunto de resultados.

En T-SQL:

CREATE PROCEDURE usp_proc_1 AS 
SELECT GETDATE() AS 'Date'
GO
CREATE PROCEDURE usp_proc_2 AS 
EXEC usp_proc_1
SELECT 1 AS 'number'
GO
EXEC usp_proc_2

En Python tengo una función auxiliar que he tomado de otras publicaciones,

def getMultiResults(conn , query, params = None):
    # utilízalo cuando la consulta devuelva varios conjuntos de resultados
    cursor = conn.cursor()
    records = []

    if (params == None):
        cursor.execute(query)
    else:
        cursor.execute(query,params)

    # primer conjunto de resultados
    logging.info(cursor.description[0])
    attributes = [key[0] for key in cursor.description] # obtiene los encabezados de las columnas
    dataframe = cursor.fetchall()
    cursor.commit()
    records.append( [dict(zip(attributes, row)) for row in dataframe])

    # más conjuntos de resultados
    while (cursor.nextset()):
        logging.info(cursor.description[0])
        attributes = [key[0] for key in cursor.description] # obtiene los encabezados de las columnas
        dataframe = cursor.fetchall()
        cursor.commit()
        records.append( [dict(zip(attributes, row)) for row in dataframe])

    return records

Cuando llamo a getMultiResults en EXEC usp_proc_2, el dataframe solo contiene el conjunto de resultados de la fecha. Creo que esto se debe a que aunque el procedimiento externo parece devolver dos conjuntos de datos, el procedimiento interno solo crea el primero y esto es todo lo que fetchall() está viendo. Si el procedimiento almacenado fuera:

CREATE PROCEDURE usp_proc_3
SELECT GETDATE() AS 'Date'
SELECT 1 AS 'Number'
GO
EXEC usp_proc_3

entonces fetchall() funcionaría como se espera.

¿Estoy en lo correcto y, de ser así, cómo puedo corregir el problema?

En realidad, tengo un procedimiento maestro complejo que, dependiendo del escenario comercial, ejecuta varios subprocedimientos, cada uno de los cuales devuelve tanto un conjunto de resultados como un valor de retorno. Todo lo que necesito es el ÚLTIMO conjunto de resultados del procedimiento maestro, pero esto podría ser el tercer, quinto o sexto conjunto de resultados dependiendo de qué procedimientos internos se ejecuten.

Tags:  , , , ,

Answer

  1. Avatar for davy.ai

    Sí, estás en lo correcto. El método fetchall() solo devuelve el primer conjunto de resultados de un procedimiento almacenado. Para obtener los conjuntos de resultados siguientes, debes llamar al método nextset() del objeto cursor hasta que devuelva False, lo que indica que no hay más conjuntos de resultados para obtener.

    En tu escenario, una solución sería modificar los procedimientos internos para que devuelvan sus conjuntos de resultados como parámetros de salida o como tablas temporales. Luego, en el procedimiento principal, puedes extraer el último conjunto de resultados iterando a través de todos los conjuntos de resultados y almacenando los datos en una variable.

    Otra solución sería modificar la función auxiliar de Python para iterar a través de todos los conjuntos de resultados hasta llegar al último. Puedes agregar un parámetro a la función para especificar qué conjunto de resultados devolver o modificar la función para devolver un diccionario de todos los conjuntos de resultados con sus valores de retorno asociados.

    En general, el enfoque que elijas dependerá de la complejidad de tus procedimientos almacenados y del escenario empresarial específico en el que estés trabajando.

Comments are closed.