store procedure in trans sql vs pl sql - sql

In oracle (pl-sql) I have
s as (select * from ruleassigns$all where [snapshot] = p_Id);
inside a stored procedure. I want to port it into sql server (trans-sql), but when I write the same it gives me error on the structure of the statement. Please help!
I am wondering something like
declare #s = (select * from ruleassigns$all where [snapshot] = p_Id);
but that's not correct either.

Since this query is returning multiple values you'd probably want to use a Declare #table.
The syntax will be
Declare #s Table (p_id SomeDataType(probably int?))
You can use #s just like any other table.
SELECT * FROM #s
Note: I personally like the feel of temporary tables. They feel like normal tables.
You'd write:
CREATE TABLE #tableName (p_id SomeDataType)
and at the end of your SP you'd do DROP TABLE #tableName

Related

sql server - fill results from executed query string in a temp table dynamically

I'm writing a stored procedure. I have a string which contains an sql query. For example:
DECLARE #sql nvarchar(max)
SET #sql = (N'SELECT pkOrderID FROM Orders')
(Just to note: this isn't what the select statement looks like. This is just an example of what I mean) I then want to execute the string and put the result in a temporary table E.g. #tempTable. I know EXEC(#sql) exists but not sure if it will do me any good in this situation. The other twist is that I do not know the names of all the columns in the returned #sql so the temp table #tempTable needs to be created dyanmically based off the return from #sql. Thanks for any help.
I think you could use SELECT INTO to do what you want but it would mean updating your string:
DECLARE #sql nvarchar(max)
SET #sql = (N'SELECT frompkOrderID INTO #tmporders FROM Orders')
then you should be able to run EXEC #sql to create the table
more information about SELECT INTO here : http://msdn.microsoft.com/en-au/library/ms188029.aspx
There is no simple way to do this. The problem with #JanR's solution is that the #tmporders table will be out of scope to the script that calls your stored procedure (ie It will produce an error like "Invalid object name '#rtmporders'"
One alternative is to use a global temp table (eg ##tmporders).
So your SP might look like this:
CREATE PROCEDURE TestSP
AS
BEGIN
SELECT pkOrderID INTO ##tmporders FROM Orders
END
GO
And the calling script might be like:
EXEC TestSP
SELECT * FROM ##temporders

Creating a dynamic table from dynamic SQL

First of all I'm using ms SQL server 2012. I' trying to use a table based on a string value passed in as a string into a procedure. I found out that you can't use strings are table names when writing a query so I'm trying to find a way around that. The only lead I'm kind of onto is using dynamic SQL which I also am not sure how to make work. Here is what I have:
DECLARE #q AS NVARCHAR(MAX)
SET #q = 'SELECT * FROM ' + #tableName
DECLARE #tableCopy AS EXECUTE(#q)
How can I get the executed #q into #tableCopy? Or is there a better way to access my table when all I know is the tables name as a string?
You can create the temporary table and then insert into that table inside the dynamic sql. There's an example here:
http://smehrozalam.wordpress.com/2009/10/14/t-sql-using-result-of-a-dynamic-sql-query-in-a-variable-or-table/
Unfortunately, you would need to know the schema. The following does not work:
declare #query varchar(max) =
'select * into #t from table'
EXEC(#query)
select * FROM #t

Put the servername, database name and schema automatically before the tablename in a select statement

I have a stored procedure that is responsible to import data from database A to database B. I have customers, they all have their own database B (with the same tables etc.) They also have their own database A. The stored procedure will be executed (deployed) on database B.
The problem:
Each customer have another database name for A and B. I found also that database A can be on a different server/instance. I need a generic way to put automatically the server/instance name and the database name from A in my stored procedure to select data from there. Every customer has a connectstring to database A which is already exists in database B. So from the connecstring, I can get the server/instance name and the databasename of A. (I already created a linked server)
1. What is the best way to put the server/instance name and the database name before the table name??
Stored procedure
In my stored procedure I have used a lot of variable (declare) tables to insert the data from database A. There are many articles about using dynamic sql but, I cant find an example with a declare table.
My solution
I am thinking about inserting all the data from database A to variable tables. I am importing data from 7 tables, so I need to declare 7 tables and further in my SP I can select data from my declare tables. Note that the hole stored procedure is very huge.
Questions
2.What do you think about my solution?
3.Do you have another solution?
4.How can I insert into my declare table using dynamic sql?
**note that I am using sql server 2005.
I have a few statements like below:
declare #Temp table (Id int, etc
insert into #Temp (Id, etc)
Select Id, etc
From [databasename].dbo.TableName //hardcoded
Where .......
// doing staff like selecting from the #Temp table etc.
I also have subqueries, but I can change if it is necessary.
You can't use dynamic sql to enter into declare tables as the temporary table is only available in the session. Executing any new sql i.e. through dynamic sql will create a new session.
You can get around it by not using any declared or temp tables but instead using a normal table. The dynamic sql will have access to this and anything you do to it isnt lost.
You can prefix your normal tables with something like Temp_ just to note they are temp tables and then make sure you drop them at the beginning of each query i.e.
DROP TABLE TEMP_Table
You can call multiple local databases by doing
SELECT * FROM [DatabaseName].dbo.[TableName]
Instead of creating #temp, create it as [TempDB].[DBO].[Temp] and it will be accessible outside the dynamic SQL. However, remember to explicitly drop the table, once you are done
DECLARE #sql VARCHAR(200)
SET #sql = 'CREATE TABLE tempdb.dbo.temp(id INT IDENTITY(1,1), DESCRIPTION VARCHAR(100))
INSERT INTO tempdb.dbo.temp SELECT ''1'' SELECT * FROM tempdb.dbo.temp'
PRINT (#sql)
EXEC (#sql)
SELECT * FROM tempdb.dbo.temp
DROP TABLE tempdb.dbo.temp
Raj
Check this for creating temporary table in dynamic query
DECLARE #sql VARCHAR(200)
SET #sql = 'CREATE TABLE #temp(id INT IDENTITY(1,1), DESCRIPTION VARCHAR(100))
INSERT INTO #temp SELECT ''1'' SELECT * FROM #temp'
PRINT (#sql)
EXEC (#sql)
SQLFiddle
to be precise
DECLARE #sql VARCHAR(1000)
SET #sql =
'DECLARE #Temp TABLE (
Id INT,
etc
INSERT INTO #Temp (Id, etc)
SELECT Id,
etc
FROM [databasename].dbo.TableName / / hardcoded
WHERE ....... SELECT * FROM #temp'
PRINT (#sql)
EXEC (#sql)

Insert result of executing dynamic query into a table

I have a dynamic query #strQuery which on executing gives a result with lots of column.
I want to insert the result from this dynamic query into a temporary table .
I am doing this because I want to perform some filtering on the temporary table and get required result .
A similar question was asked on previous thread HERE
in which a temporary table is created first and then data inserted using INSERT INTO.
I want to avoid this step due to long list of columns and also the datatypes of fields is not known to me.
select * into #tmh from
exec(#strQuery)
Error Message
Incorrect syntax near the keyword 'exec'.
How to do this ? Is it possible to be done in this way ? If not , please specify some other alternative to get store the result on executing dynamic query into a table.
Thanks.
I have faced this situation before and here is what I did:
DECLARE #strQuery nVarchar(100)
SET #strQuery='SELECT * into [tempdb].[dbo].[temptable] FROM YourTable'
EXECUTE sp_executesql #strQuery
SELECT * FROM [tempdb].[dbo].[temptable]
DROP TABLE [tempdb].[dbo].[temptable]
It works fine. Don't ask me why a FQ table name and not #temptable. I have no idea. It does not work. The only way I could get it working was using [tempdb].[dbo].[temptable]
proceed like this
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 .
You can use variables in your current execution context, set by the Dynamic SQL with the OUTPUT option. Sample code below.
DECLARE #Amount AS MONEY
DECLARE #SQL AS NVARCHAR(1000)
SET #Amount = NULL
SET #SQL = ('SELECT #amt=100' )
EXECUTE sp_executeSQL #SQL, N'#amt MONEY OUTPUT', #amt=#Amount OUTPUT
SELECT #Amount
Yes you can make a new dynamic query containing the original query with the insert like this:
declare #strNewQuery varchar(max)
set #strNewQuery ='select * into #tmh from ('+#strQuery+') as t'
exec(#strNewQuery)
I used this to work around - with out dynamic query
This uses a table variable to receive data to procedure
Even joins can be applied to it
select * into #itemPhantom from #tbl_items_upload
select * from #itemPhantom
select #itemPhantom.itemreference from #itemPhantom left join phantom on phantom.name=#itemPhantom.PhantomName

How to query from a stored procedure in SQL Server?

Let say I have a simple Stored Procedure:
ALTER PROCEDURE [dbo].[myProc]
AS
BEGIN
SELECT * FROM myTable
END
How can I do a WHERE statement in Microsoft SQL Server Management Studio to the stored procedure? Something like that:
SELECT * FROM myProc WHERE x = 'a'; -- But that doesn't work...
It sounds like you're trying to make a "dynamic" stored procedure.
Something you might want to do is:
1) Insert the contents of your stored procedure into a temporary table
2) Use dynamic sql to apply a where condition to that temporary table.
Something like:
declare #as_condition varchar(500); --Your condition
create table #a
(
id bigint
)
insert into #a
execute sproc
declare #ls_sql varchar(max);
set #ls_sql = "select * from #a where " + #as_condition;
execute (#ls_sql);
SQL Server allows you to use INSERT INTO to grab a stored procedure's output. For example, to grab all processes with SPID < 10, use:
create table #sp_who (
spid smallint,
ecid smallint,
status nchar(30),
loginame nchar(128),
hostname nchar(128),
blk char(5),
dbname nchar(128),
cmd nchar(16),
request int)
insert into #sp_who execute sp_who
select * from #sp_who where spid < 10
You can't add a WHERE clause to a stored procedure like this.
You should put the clause in the sproc, like this:
ALTER PROCEDURE [dbo].[myProc]
#X VARCHAR(10)
AS
BEGIN
SELECT * FROM myTable WHERE x=#X
END
GO
The syntax for calling a stored procedure is through the use of EXECUTE not SELECT(e.g.):
EXECUTE dbo.myProc 'a'
I think you can't do that.
The command to execute a stored procedure is EXECUTE.
See some more examples of the EXECUTE usage.
I think its better to use a view or a table valued function rather than the suggested approach. Both allow you to pass parameters to the function
If you want the WHERE clause to be something you can "turn off" you can do this, passing in a predetermined value (e.g. -1) if the WHERE limitation is to be bypassed:
ALTER PROCEDURE [dbo].[myProc]
#X VARCHAR(10)
AS
BEGIN
SELECT * FROM myTable WHERE x=#X or #X = -1
END
GO
You must declare a variable in the store procedure which will be necessary to pass to run the stored procedure. Here is an example. Keep this in mind: Before AS you can simply declare any variable by using the # character, but after the AS you must write Declare to declare any variable, e.g., Declare #name nvarchar (50).
ALTER PROCEDURE [dbo].[myProc]
#name varchar (50)
AS
BEGIN
SELECT * FROM myTable
where name= #name
END