Insertar resultados de un procedimiento almacenado en una tabla temporal

Resuelto Ferdeen asked hace 15 años • 0 respuestas

¿ Cómo hago un SELECT * INTO [temp table] FROM [stored procedure]? ¿ No FROM [Table]y sin definir [temp table]?

SelectTodos los datos desde BusinessLinedentro tmpBusLinefuncionan bien.

select *
into tmpBusLine
from BusinessLine

Estoy intentando lo mismo, pero usar un stored procedureque devuelve datos no es exactamente lo mismo.

select *
into tmpBusLine
from
exec getBusinessLineHistory '16 Mar 2009'

Mensaje de salida:

Mensaje 156, nivel 15, estado 1, línea 2 Sintaxis incorrecta cerca de la palabra clave 'exec'.

He leído varios ejemplos de creación de una tabla temporal con la misma estructura que el procedimiento almacenado de salida, que funciona bien, pero sería bueno no proporcionar ninguna columna.

Ferdeen avatar Mar 17 '09 17:03 Ferdeen
Aceptado

Puedes usar OPENROWSET para esto. Echar un vistazo. También incluí el código sp_configure para habilitar las consultas distribuidas ad hoc, en caso de que aún no esté habilitado.

CREATE PROC getBusinessLineHistory
AS
BEGIN
    SELECT * FROM sys.databases
END
GO

sp_configure 'Show Advanced Options', 1
GO
RECONFIGURE
GO
sp_configure 'Ad Hoc Distributed Queries', 1
GO
RECONFIGURE
GO

SELECT * INTO #MyTempTable FROM OPENROWSET('SQLNCLI', 'Server=(local)\SQL2008;Trusted_Connection=yes;',
     'EXEC getBusinessLineHistory')

SELECT * FROM #MyTempTable
Aaron Alton avatar Aug 04 '2009 15:08 Aaron Alton

Si desea hacerlo sin declarar primero la tabla temporal, puede intentar crear una función definida por el usuario en lugar de un procedimiento almacenado y hacer que esa función definida por el usuario devuelva una tabla. Alternativamente, si desea utilizar el procedimiento almacenado, pruebe algo como esto:

CREATE TABLE #tmpBus
(
   COL1 INT,
   COL2 INT
)

INSERT INTO #tmpBus
Exec SpGetRecords 'Params'
Gavin avatar Mar 17 '2009 14:03 Gavin

En SQL Server 2005 se puede utilizar INSERT INTO ... EXECpara insertar el resultado de un procedimiento almacenado en una tabla. De la documentación de MSDNINSERT (para SQL Server 2000, de hecho):

--INSERT...EXECUTE procedure example
INSERT author_sales EXECUTE get_author_sales
Matt Hamilton avatar Mar 17 '2009 10:03 Matt Hamilton

Esta es una respuesta a una versión ligeramente modificada de su pregunta. Si puede abandonar el uso de un procedimiento almacenado para una función definida por el usuario, puede utilizar una función definida por el usuario con valores de tabla en línea. Se trata esencialmente de un procedimiento almacenado (tomará parámetros) que devuelve una tabla como conjunto de resultados; y por lo tanto quedará muy bien con una declaración INTO.

Aquí hay un buen artículo rápido sobre esto y otras funciones definidas por el usuario. Si todavía necesita un procedimiento almacenado, puede envolver la función definida por el usuario con valores de tabla en línea con un procedimiento almacenado. El procedimiento almacenado simplemente pasa parámetros cuando llama a select * desde la función definida por el usuario con valores de tabla en línea.

Entonces, por ejemplo, tendría una función definida por el usuario con valores de tabla en línea para obtener una lista de clientes para una región en particular:

CREATE FUNCTION CustomersByRegion 
(  
    @RegionID int  
)
RETURNS TABLE 
AS
RETURN 
  SELECT *
  FROM customers
  WHERE RegionID = @RegionID
GO

Luego puede llamar a esta función para obtener resultados como estos:

SELECT * FROM CustomersbyRegion(1)

O hacer un SELECCIONAR EN:

SELECT * INTO CustList FROM CustomersbyRegion(1)

Si aún necesita un procedimiento almacenado, ajuste la función como tal:

CREATE PROCEDURE uspCustomersByRegion 
(  
    @regionID int  
)
AS
BEGIN
     SELECT * FROM CustomersbyRegion(@regionID);
END
GO

Creo que este es el método menos pirateado para obtener los resultados deseados. Utiliza las funciones existentes tal como fueron diseñadas para ser utilizadas sin complicaciones adicionales. Al anidar la función definida por el usuario con valores de tabla en línea en el procedimiento almacenado, tiene acceso a la funcionalidad de dos maneras. ¡Más! Sólo tiene un punto de mantenimiento para el código SQL real.

Se ha sugerido el uso de OPENROWSET, pero esta no es la finalidad para la que se pretendía utilizar la función OPENROWSET (De Libros en línea):

Incluye toda la información de conexión necesaria para acceder a datos remotos desde una fuente de datos OLE DB. Este método es una alternativa al acceso a tablas en un servidor vinculado y es un método ad hoc único para conectarse y acceder a datos remotos mediante OLE DB. Para referencias más frecuentes a fuentes de datos OLE DB, utilice servidores vinculados.

El uso de OPENROWSET hará el trabajo, pero generará una sobrecarga adicional para abrir conexiones locales y ordenar datos. También puede que no sea una opción en todos los casos, ya que requiere un permiso de consulta ad hoc que plantea un riesgo de seguridad y, por lo tanto, puede no ser deseable. Además, el enfoque OPENROWSET impedirá el uso de procedimientos almacenados que devuelvan más de un conjunto de resultados. Esto se puede lograr envolviendo múltiples funciones definidas por el usuario con valores de tabla en línea en un único procedimiento almacenado.

Christian Loris avatar Aug 04 '2009 17:08 Christian Loris
Select @@ServerName
EXEC sp_serveroption @@ServerName, 'DATA ACCESS', TRUE

SELECT  *
INTO    #tmpTable
FROM    OPENQUERY(YOURSERVERNAME, 'EXEC db.schema.sproc 1')
Quassnoi avatar Mar 17 '2009 10:03 Quassnoi