Kartikeya Khosla
Kartikeya Khosla

Reputation: 18873

Dynamic SQL Result INTO Temporary Table

I need to store dynamic sql result into a temporary table #Temp.

Dynamic SQL Query result is from a pivot result, so number of columns varies(Not fixed).

SET @Sql = N'SELECT ' + @Cols + ' FROM 
        (
           SELECT ResourceKey, ResourceValue 
           FROM LocaleStringResources where StateId ='
+ LTRIM(RTRIM(@StateID)) + ' AND FormId =' + LTRIM(RTRIM(@FormID))
+ ' AND CultureCode =''' + LTRIM(RTRIM(@CultureCode)) + '''
         ) x
        pivot 
        (
            max(ResourceValue)
            for ResourceKey IN (' + @Cols + ')
        ) p ;'

     --@Cols => Column Names which varies in number

Now I have to insert dynamic sql result to #Temp Table and use this #Temp Table with another existing table to perform joins or something else.

(#Temp table should exist there to perform operations with other existing tables)

How can I Insert dynamic SQL query result To a Temporary table?

Thanks

Upvotes: 4

Views: 8279

Answers (5)

Amnesh Goel
Amnesh Goel

Reputation: 2655

Here is step by step solution for your problem.

  1. Check for your temporary tables if they exist, and delete them.
IF OBJECT_ID('tempdb..#temp') IS NOT NULL
DROP TABLE #temp

IF OBJECT_ID('tempdb..##abc') IS NOT NULL
DROP TABLE ##abc
  1. Store your main query result in first temp table (this step is for simplicity and more readability).
SELECT * 
INTO   #temp 
FROM   (SELECT ResourceKey, ResourceValue 
FROM LocaleStringResources 
where StateId ='+ LTRIM(RTRIM(@StateID)) + ' AND FormId =' + LTRIM(RTRIM(@FormID))
+ ' AND CultureCode =' + LTRIM(RTRIM(@CultureCode)) + ') AS S


  1. Write below query to create your pivot and store result in another temp table.
DECLARE @str NVARCHAR(1000) 
DECLARE @sql NVARCHAR(1000)      
SELECT @str = COALESCE(@str+',', '') + ResourceKey FROM   #temp 

SET @sql = N'select * into ##abc from (select ' + @str + ' from (SELECT ResourceKey, ResourceValue FROM #temp) as A 
Pivot 
(   
  max(ResourceValue)
  for ResourceKey in (' + @str + ')  
)as pvt) as B'
  1. Execute below query to get the pivot result in your next temp table ##abc.

EXECUTE sp_executesql @sql

  1. And now you can use ##abc as table where-ever you want like

select * from ##abc

Hope this will help you.

Upvotes: 0

user1216435
user1216435

Reputation: 11

IF OBJECT_ID('tempdb..##TmepTable') IS NOT NULL DROP TABLE ##TmepTable
     CREATE TABLE ##TmepTable (TmpCol CHAR(1))
DECLARE @SQL NVARCHAR(max) =' IF OBJECT_ID(''tempdb..##TmepTable'') IS NOT 
NULL DROP TABLE ##TmepTable 
SELECT * INTO ##TmepTable  from [MyTableName]'
    EXEC sp_executesql @SQL
SELECT  Alias.* FROM ##TmepTable as Alias

IF OBJECT_ID('tempdb..##TmepTable') IS NOT NULL DROP TABLE ##TmepTable 

Upvotes: 0

PK.Shrestha
PK.Shrestha

Reputation: 120

Alternative to create a temporary table is to use the subquery

select t1.name,t1.lastname from(select * from table)t1.

where "select * from table" is your dyanmic query. which will return result which you can use as temp table t1 as given in example .

Upvotes: 0

Vladimir Baranov
Vladimir Baranov

Reputation: 32685

As was answered in (https://social.msdn.microsoft.com/Forums/sqlserver/en-US/144f0812-b3a2-4197-91bc-f1515e7de4b9/not-able-to-create-hash-table-inside-stored-proc-through-execute-spexecutesql-strquery?forum=sqldatabaseengine),

you need to create a #Temp table in advance:

CREATE TABLE #Temp(columns definition);

It seems that the task is impossible, if you know nothing about the dynamic list of columns in advance. But, most likely you do know something.

You do know the types of dynamic columns, because they come from PIVOT. Most likely, you know the maximum possible number of dynamic columns. Even if you don't, SQL Server has a limit of 1024 columns per (nonwide) table and there is a limit of 8060 bytes per row (http://msdn.microsoft.com/en-us/library/ms143432.aspx). So, you can create a #Temp table in advance with maximum possible number of columns and use only some of them (make all your columns NULLable).

So, CREATE TABLE will look like this (instead of int use your type):

CREATE TABLE #Temp(c1 int NULL, c2 int NULL, c3 int NULL, ..., c1024 int NULL);

Yes, column names in #Temp will not be the same as in @Cols. It should be OK for your processing.

You have a list of columns in your @Cols variable. You somehow make this list of columns in some external code, so when @Cols is generated you know how many columns there are. At this moment you should be able to generate a second list of columns that matches the definition of #Temp. Something like:

@TempCols = N'c1, c2, c3, c4, c5';

The number of columns in @TempCols should be the same as the number of columns in @Cols. Then your dynamic SQL would look like this (I have added INSERT INTO #Temp (@TempCols) in front of your code):

SET @Sql = N'INSERT INTO #Temp (' + @TempCols + N') SELECT ' + @Cols + N' FROM 
        (
           SELECT ResourceKey, ResourceValue 
           FROM LocaleStringResources where StateId ='
+ LTRIM(RTRIM(@StateID)) + ' AND FormId =' + LTRIM(RTRIM(@FormID))
+ ' AND CultureCode =''' + LTRIM(RTRIM(@CultureCode)) + '''
         ) x
        pivot 
        (
            max(ResourceValue)
            for ResourceKey IN (' + @Cols + ')
        ) p ;'

Then you execute your dynamic SQL:

EXEC (@Sql) OR sp_executesql @Sql

And then do other processing using the #Temp table and temp column names c1, c2, c3, ...

MSDN says:

A local temporary table created in a stored procedure is dropped automatically when the stored procedure is finished.

You can also DROP the #Temp table explicitly, like this:

IF OBJECT_ID('tempdb..#Temp') IS NOT NULL
DROP TABLE #Temp'

All this T-SQL code (CREATE TABLE, EXEC, ...your custom processing..., DROP TABLE) would naturally be inside the stored procedure.

Upvotes: 0

Hitesh
Hitesh

Reputation: 3498

Can you please try the below query.

SET @Sql = N'SELECT ' + @Cols + ' 
    into ##TempTable
    FROM 
    (
       SELECT ResourceKey, ResourceValue 
       FROM LocaleStringResources where StateId ='
       + LTRIM(RTRIM(@StateID)) + ' AND FormId =' + LTRIM(RTRIM(@FormID))
       + ' AND CultureCode =''' + LTRIM(RTRIM(@CultureCode)) + '''
     ) x
    pivot 
    (
        max(ResourceValue)
        for ResourceKey IN (' + @Cols + ')
    ) p ;'

You can then use the ##TempTable for further operations.

However, do not forget to drop the ##TempTable at the end of your query as it will give you error if you run the query again as it is a Global Temporary Table

Upvotes: 1

Related Questions