Compartir a través de


Asociación y transferencia de datos de parámetros y valores de columna de Table-Valued

Los parámetros con valores de tabla, al igual que otros parámetros, deben enlazarse antes de pasarse al servidor. La aplicación enlaza los parámetros con valores de tabla de la misma manera que enlaza otros parámetros: mediante SQLBindParameter o llamadas equivalentes a SQLSetDescField o SQLSetDescRec. El tipo de datos de servidor para un parámetro con valores de tabla es SQL_SS_TABLE. El tipo C se puede especificar como SQL_C_DEFAULT o SQL_C_BINARY.

En SQL Server 2008 o posterior, solo se admiten parámetros con valores de tabla de entrada. Por lo tanto, cualquier intento de establecer SQL_DESC_PARAMETER_TYPE en un valor distinto de SQL_PARAM_INPUT devolverá SQL_ERROR con SQLSTATE = HY105 y el mensaje "Tipo de parámetro no válido".

Se pueden asignar valores predeterminados a las columnas de parámetros con valores de tabla completos mediante el atributo SQL_CA_SS_COL_HAS_DEFAULT_VALUE. Sin embargo, los valores de columna de parámetros con valores de tabla individuales no se pueden asignar valores predeterminados mediante SQL_DEFAULT_PARAM en StrLen_or_IndPtr con SQLBindParameter. Los parámetros con valores de tabla como un todo no se pueden establecer en un valor predeterminado mediante SQL_DEFAULT_PARAM en StrLen_or_IndPtr con SQLBindParameter. Si no se siguen estas reglas, SQLExecute o SQLExecDirect devolverán SQL_ERROR. Se generará un registro de diagnóstico con SQLSTATE=07S01 y el mensaje "Uso no válido del parámetro predeterminado para el parámetro <p>", donde <p> es el ordinal del TVP en la instrucción de consulta.

Después de enlazar el parámetro con valores de tabla, la aplicación debe enlazar cada columna de parámetro con valores de tabla. Para ello, la aplicación llama primero a SQLSetStmtAttr para establecer SQL_SOPT_SS_PARAM_FOCUS en el ordinal de un parámetro con valores de tabla. A continuación, la aplicación enlaza las columnas del parámetro con valores de tabla mediante llamadas a las siguientes rutinas: SQLBindParameter, SQLSetDescRec y SQLSetDescField. Al establecer SQL_SOPT_SS_PARAM_FOCUS en 0 se restaura el efecto habitual de SQLBindParameter, SQLSetDescRec y SQLSetDescField en funcionamiento en parámetros de nivel superior normales.

No se envía ni recibe ningún dato real para el propio parámetro con valores de tabla, pero los datos se envían y reciben para cada una de sus columnas constituyentes. Dado que el parámetro con valores de tabla es una pseudo columna, los parámetros de SQLBindParameter se usan para hacer referencia a atributos diferentes que otros tipos de datos, como se indica a continuación:

Parámetro Atributo relacionado para los tipos de parámetros que no son con valores de tabla, incluidas las columnas Atributo relacionado para parámetros con valores de tabla
InputOutputType SQL_DESC_PARAMETER_TYPE en IPD.

En el caso de las columnas de parámetros con valores de tabla, debe ser igual que la configuración del propio parámetro con valores de tabla.
SQL_DESC_PARAMETER_TYPE en IPD.

Debe ser SQL_PARAM_INPUT.
ValueType SQL_DESC_TYPE, SQL_DESC_CONCISE_TYPE en APD. SQL_DESC_TYPE, SQL_DESC_CONCISE_TYPE en APD.

Debe ser SQL_C_DEFAULT o SQL_C_BINARY.
ParameterType SQL_DESC_TYPE, SQL_DESC_CONCISE_TYPE en IPD. SQL_DESC_TYPE, SQL_DESC_CONCISE_TYPE en IPD.

Debe ser SQL_SS_TABLE.
ColumnSize SQL_DESC_LENGTH o SQL_DESC_PRECISION en IPD.

Esto depende del valor de ParameterType.
SQL_DESC_ARRAY_SIZE

También se puede establecer mediante SQL_ATTR_PARAM_SET_SIZE cuando el foco del parámetro se establece en el parámetro con valores de tabla.

Para un parámetro con valores de tabla, este es el número de filas de los búferes de columnas de parámetros con valores de tabla.
DecimalDigits SQL_DESC_PRECISION o SQL_DESC_SCALE en IPD. No usado. Debe ser 0.

Si este parámetro no es 0, SQLBindParameter devolverá SQL_ERROR y se generará un registro de diagnóstico con SQLSTATE= HY104 y el mensaje "Precisión o escala no válidos".
ParameterValuePtr SQL_DESC_DATA_PTR en APD. SQL_CA_SS_TYPE_NAME.

Esto es opcional para las llamadas a procedimientos almacenados y se puede especificar NULL si no es necesario. Debe especificarse para instrucciones SQL que no sean llamadas a procedimiento.

Este parámetro también actúa como un valor único que la aplicación puede usar para identificar este parámetro con valores de tabla cuando se usa el enlace de fila variable. Para obtener más información, vea la sección "Enlace de filas de parámetros Table-Valued variable", más adelante en este tema.

Cuando se especifica un nombre de tipo de parámetro con valores de tabla en una llamada a SQLBindParameter, debe especificarse como un valor Unicode, incluso en las aplicaciones compiladas como aplicaciones ANSI. El valor usado para el parámetro StrLen_or_IndPtr debe ser SQL_NTS o la longitud de cadena del nombre multiplicado por sizeof(WCHAR).
bufferLength SQL_DESC_OCTET_LENGTH en APD. Longitud del nombre del tipo de parámetro con valores de tabla en bytes.

Esto puede ser SQL_NTS si el nombre de tipo termina en null o 0 si no se requiere el nombre del tipo de parámetro con valores de tabla.
StrLen_or_IndPtr SQL_DESC_OCTET_LENGTH_PTR en APD. SQL_DESC_OCTET_LENGTH_PTR en APD.

En el caso de los parámetros con valores de tabla, se trata de un recuento de filas en lugar de una longitud de datos.

Se admiten dos modos de transferencia de datos para parámetros con valores de tabla: enlace fijo de fila y enlace de fila variable.

Se corrigió Table-Valued enlace de fila de parámetros

Para el enlace de fila fijo, una aplicación asigna búferes (o matrices de búferes) lo suficientemente grande como para todos los valores de columna de entrada posibles. La aplicación hace lo siguiente:

  1. Enlaza todos los parámetros mediante llamadas SQLBindParameter, SQLSetDescRec o SQLSetDescField.

    1. Establece SQL_DESC_ARRAY_SIZE en el número máximo de filas que se pueden transferir para cada parámetro con valores de tabla. Esto se puede hacer en la llamada a SQLBindParameter.
  2. Llama a SQLSetStmtAttr para establecer SQL_SOPT_SS_PARAM_FOCUS en el ordinal de cada parámetro con valores de tabla.

    1. Para cada parámetro con valores de tabla, enlaza columnas de parámetro con valores de tabla mediante llamadas SQLBindParameter, SQLSetDescRec o SQLSetDescField.

    2. Para cada columna de parámetro con valores de tabla que es tener valores predeterminados, llama a SQLSetDescField para establecer SQL_CA_SS_COL_HAS_DEFAULT_VALUE en 1.

  3. Llama a SQLSetStmtAttr para establecer SQL_SOPT_SS_PARAM_FOCUS en 0. Esto debe hacerse antes de llamar a SQLExecute o SQLExecDirect. De lo contrario, se devuelve SQL_ERROR y se genera un registro de diagnóstico con SQLSTATE=HY024 y el mensaje "Valor de atributo no válido, SQL_SOPT_SS_PARAM_FOCUS (debe ser cero en tiempo de ejecución)".

  4. Establece StrLen_or_IndPtr o SQL_DESC_OCTET_LENGTH_PTR en SQL_DEFAULT_PARAM para un parámetro con valores de tabla sin filas, o el número de filas que se van a transferir en la siguiente llamada de SQLExecute o SQLExecDirect si el parámetro con valores de tabla tiene filas. StrLen_or_IndPtr o SQL_DESC_OCTET_LENGTH_PTR no se pueden establecer en SQL_NULL_DATA para un parámetro con valores de tabla, ya que los parámetros con valores de tabla no admiten valores NULL (aunque las columnas constituyentes de parámetros con valores de tabla pueden ser nullables). Si se establece en un valor no válido, SQLExecute o SQLExecDirect devuelve SQL_ERROR, y se genera un registro de diagnóstico con SQLSTATE=HY090 y el mensaje "Cadena o longitud de búfer no válidas para el parámetro <p>", donde p es el número de parámetro.

  5. Llama a SQLExecute o SQLExecDirect.

Los valores de columna de parámetro con valores de tabla de entrada se pueden pasar en partes si StrLen_or_IndPtr está establecido en SQL_LEN_DATA_AT_EXEC(length) o SQL_DATA_AT_EXEC para la columna. Esto es similar a pasar valores en partes cuando se usan matrices de parámetros. Al igual que con todos los parámetros de datos en ejecución, SQLParamData no indica a qué fila de la matriz solicita datos el controlador; la aplicación debe ocuparse de esto. La aplicación no puede realizar ninguna suposición sobre el orden en el que el controlador solicitará valores.

Enlace de fila de parámetros de Table-Valued variable

Para el enlace de fila variable, las filas se transfieren en lotes en tiempo de ejecución y la aplicación pasa filas al controlador a petición. Esto es similar a los datos en ejecución para los valores de parámetro individuales. Para el enlace de fila variable, la aplicación hace lo siguiente:

  1. Enlaza parámetros y columnas de parámetros con valores de tabla como se describe en los pasos 1 a 3 de la sección anterior, "Fixed Table-Valued Parameter Row Binding".

  2. Establece StrLen_or_IndPtr o SQL_DESC_OCTET_LENGTH_PTR para los parámetros con valores de tabla que se van a pasar en tiempo de ejecución a SQL_DATA_AT_EXEC. Si no se establece ninguno, el parámetro se procesará como se describe en la sección anterior.

  3. Llama a SQLExecute o SQLExecDirect. Esto devolverá SQL_NEED_DATA si hay parámetros SQL_PARAM_INPUT o SQL_PARAM_INPUT_OUTPUT que se van a controlar como parámetros de datos en ejecución. En este caso, la aplicación hace lo siguiente:

    • Llama a SQLParamData. Esto devuelve el valor ParameterValuePtr de un parámetro data-at-execution y un código devuelto de SQL_NEED_DATA. Cuando se han pasado todos los datos de parámetro al controlador, SQLParamData devuelve SQL_SUCCESS, SQL_SUCCESS_WITH_INFO o SQL_ERROR. Para los parámetros de datos en ejecución, ParameterValuePtr, que es el mismo que el campo descriptor SQL_DESC_DATA_PTR, se puede considerar un token para identificar de forma única un parámetro para el que se requiere un valor. Este "token" se pasa de la aplicación al controlador en tiempo de enlace y, a continuación, se pasa a la aplicación en tiempo de ejecución.
  4. Para enviar datos de fila de parámetros con valores de tabla para parámetros con valores de tabla NULL, si el parámetro con valores de tabla no tiene filas, una aplicación llama a SQLPutData con StrLen_or_Ind establecido en SQL_DEFAULT_PARAM.

    En el caso de TVPs que no son NULL, una aplicación:

    • Establece Str_Len_or_Ind para todas las columnas de parámetro con valores de tabla en los valores adecuados y rellena los búferes de datos para las columnas de parámetros con valores de tabla que no deben ser parámetros de datos en ejecución. Puede usar los datos en ejecución para las columnas de parámetros con valores de tabla de forma similar a la que se pueden pasar parámetros normales al controlador en partes.

    • Llama a SQLPutData con Str_Len_or_Ind establecido en el número de filas que se enviarán al servidor. Cualquier valor fuera del intervalo comprendido entre 0 y SQL_DESC_ARRAY_SIZE o SQL_DEFAULT_PARAM es un error y devolverá SQLSTATE HY090, con el mensaje "Cadena o longitud de búfer no válidas". 0 indica que se han enviado todas las filas y no hay más datos para un parámetro con valores de tabla (como se indica en el segundo elemento de viñeta de esta lista). SQL_DEFAULT_PARAM solo se puede usar la primera vez que el controlador solicita datos para un parámetro con valores de tabla (como se describe en el primer elemento de viñeta de esta lista).

  5. Cuando se han enviado todas las filas, llama a SQLPutData para el parámetro con valores de tabla con un valor de Str_Len_or_Ind de 0 y, a continuación, continúa con el paso 3a anterior.

  6. Llama a SQLParamData de nuevo. Si hay parámetros de datos en ejecución entre las columnas de parámetro con valores de tabla, se identificarán mediante el valor ValuePtrPtr devuelto por SQLParamData. Cuando todos los valores de columna estén disponibles, SQLParamData devolverá de nuevo el valor ParameterValuePtr para el parámetro con valores de tabla y la aplicación comienza de nuevo.

Véase también

Parámetros con valores de tabla (ODBC)