views:

1759

answers:

3

I'm trying to write a stored procedure that will read an Excel file into a temp table, then massage some of the data in that table, then insert selected rows from that table into a permanent table.

So, it starts like this:

SET @SQL = "select * into #mytemptable FROM OPENROWSET('Microsoft.Jet.OLEDB.4.0', 'Excel 8.0;Database="+@file+";HDR=YES', 'SELECT * FROM [Sheet1$]')"

EXEC (@SQL)

That much seems to work.

However, if I then try something like this:

Select * from #mytemptable

I get an error:

Invalid object name '#mytemptable'

Why isn't #mytemptable recognized? Is there a way to have #mytemptable accessible to the rest of the stored procedure?

Many thanks in advance!

+2  A: 

I don't have time to mock this up, so I don't know if it'll work, but try calling your table '##mytemptable' instead of '#mytemptable'

I'm guessing your issue is that your table isn't in scope anymore after you exec() the sql string. Temp tables preceded with two pound symbols are globally accessible.

Don't forget to drop it when you're done with it!

Lunchy
Lunchy - this works perfectly - many thanks! However, what will happen if two or more users run the stored proc at the same time? Does the fact that ##mytemptable has a global scope cause problems? Or, does SQL Server create distinct instances, even though the temp tables have the same name?
mattstuehler
Yea, they'll clash, so you'll have to come up with a way to avoid this, and unfortunately, I don't have much good advice on how to do that. I understand that you need to exec() that string because you're concatenating the filename into the query, but is that really necessary? If you can avoid it, then it's not an issue because you can run the query without exec() and return to using a locally scoped temp table.In my experience, exec()ing strings always leads to pain at some point. :)
Lunchy
Lunchy - thanks again. Unfortunately, I'm not sure how to work around the exec(), since the file name will always be different. Using a globally scoped temp table is also a no-go, since it's possible that more than one user will call this stored proc at the same time. I also considered using a table variable instead of a temp table, but I dont' want to define the table structure in advance - I want that to be dynamic, and come from the Excel spreadsheet. So, back to square 1, I guess...
mattstuehler
A: 

The way I've done this in the past was to: First, create the #temp_table using CREATE TABLE. Second, build the dynamic query as usual inserting into the #temp_table Third, use exec sp_executesql @sql.

With this method you won't need the globally scoped ##temp_table.

PPC-Coder
A: 

You can use it in the same scope including the whole script in the dynamic query:

DECLARE @strSQL nvarchar(max)
DECLARE @file varchar(100)

SET @file='c:\myfile.xls'
SET @strSQL=N'SELECT * INTO #mytemptable FROM OPENROWSET(''Microsoft.Jet.OLEDB.4.0'', ''Excel 8.0;Database='+@file+';HDR=YES'', ''SELECT * FROM [Sheet1$]'');'
SET @strSQL=@strSQL+N'SELECT * FROM #mytemptable'

EXECUTE sp_executesql @strSQL
tricat