Create variable name for table - sql

I'm wondering if it is possible to create a variable name when copying a table to another.
Here's my sort-of algorithm/code
DECLARE #NewTableName VARCHAR(50)
SET #NewTableName = 'MyTable_'+GETDATE() --MyTable_12282010 (for example)
SELECT *
INTO #NewTableName
FROM MyTable
I'm wondering if this is possible. I tried it before, but it failed. Any suggestions guys?

It is possible, but only using dynamic TSQL.
See sp_executesql (or the 2000 version sp_executesql)
Be aware of The Curse and Blessings of Dynamic SQL

Related

SQL OpenQuery variable tablename

I need to transfer data from a linked server to our main SQL server. The issue is, that the table name changes everyday.
I have looked around this site to find out if it is even possible to have a variable database name, which it is, but also to see if it is possible to have variables in a OPENQUERY, which it also is.
But i am struggling to combine those needs, so i have a variable table name in a OPENQUERY.
I need something like this:
Declare #LinkedServer as varchar(max) = 'LinkedServer'
Declare #TName as varchar(max) = 'TName'+substring(cast(cast(getdate() as date) as
varchar(50)),1,4)+substring(cast(cast(getdate() as date) as
varchar(50)),6,2)+substring(cast(cast(getdate() as date) as
varchar(50)),9,2)
SELECT * FROM OPENQUERY(#LinkedServer, 'SELECT * FROM dbo.#TName')
Is there any way i can make a variable table name in a OPENQUERY ?
Thank you for your help.
/Mikkel
I'd write a synonym which gets updated every day before you kick off your data extraction job. Then you don't need to be updating (potentially a tonne of) references.
CREATE SYNONYM LinkedTableA
FOR
ServerName.DBName.dbo.TName20170331
SELECT * FROM LinkedTableA
The answer i have, is this:
USE [DataBase]
GO
DROP SYNONYM [dbo].[eCallByCallStat]
GO
declare #tablename varchar(50)
set #tablename = 'Server1..dbo.eCallByCallStat'+substring(cast(cast(getdate()-1 as date) as varchar(50)),1,4)+substring(cast(cast(getdate()-1 as date) as varchar(50)),6,2)+substring(cast(cast(getdate()-1 as date) as varchar(50)),9,2)
declare #sql varchar(500)
set #sql = 'CREATE SYNONYM [dbo].[eCallByCallStat] FOR ' + #tablename
exec (#sql)
This will run everymorning updating the table name in the synonym, and then we will insert that data into a prober table so we have all the data.

SQL how to update table not referencing it by its name? [duplicate]

This question already has answers here:
Column-name and/or table-name as parameters
(2 answers)
Closed 8 years ago.
I need to create procedure that accepts #TableName and #ColumnName as parameters and updates the table depending on a supplied table/column name
create My_Procedure (#TableName varchar(50), #ColumnName varchar(50))
as
update #TableName
set #ColumnName = '2013-01-01'
go
But the update statement in the procedure won't work.
Please help me to find a way to rewrite the statement so it will work without using dynamic SQL. Maybe using object_id of the table and column somehow?
Assuming that you use SQL Server, you must use dynamic SQL to do this sort of things:
create My_Procedure (#TableName varchar(50), #ColumnName varchar(50))
as
begin
declare #sql nvarchar(max)
set #sql = 'update '+#TableName +' set '+#ColumnName+' = ''2013-01-01'''
exec #sql
end
However, note that this can basically can do anything to the database, so while there are legitimate uses for dynamic sql, this kind of general approach might not be the best idea.
looks like you will need to look into dynamic sql, check this SO related question.
Column-name and/or table-name as parameters

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

Using Parameter Values In SQL Statement

I am trying to write a database script (SQL Server 2008) which will copy information from database tables on one server to corresponding tables in another database on a different server.
I have read that the correct way to do this is to use a sql statement in a format similar to the following:
INSERT INTO <linked_server>.<database>.<owner>.<table_name> SELECT * FROM <linked_server>.<database>.<owner>.<table_name>
As there will be several tables being copied, I would like to declare variables at the top of the script to allow the user to specify the names of each server and database that are to be used. These could then be used throughout the script. However, I am not sure how to use the variable values in the actual SQL statements. What I want to achieve is something like the following:
DECLARE #SERVER_FROM AS NVARCHAR(50) = 'ServerFrom'
DECLARE #DATABASE_FROM AS NVARCHAR(50) = 'DatabaseTo'
DECLARE #SERVER_TO AS NVARCHAR(50) = 'ServerTo'
DECLARE #DATABASE_TO AS NVARCHAR(50) = 'DatabaseTo'
INSERT INTO #SERVER_TO.#DATABASE_TO.dbo.TableName SELECT * FROM #SERVER_FROM.#DATABASE_FROM.dbo.TableName
...
How should I use the # variables in this code in order for it to work correctly?
Additionally, do you think my method above is correct for what I am trying to achieve and should I be using NVARCHAR(50) as my variable type or something else?
Thanks
There is probably a better way to do this, but what you are probably trying to do in your example is what's called dynamic SQL where you treat the statement as a string and the execute it. This would be section #2 here:
http://www.mssqltips.com/tip.asp?tip=1160
There are some major downsides to dynamic SQL. You see a couple other approaches that might be better in that article.
If you want to execute a dynamically generated query then you have to use sp_ExecuteSQL
HTH
For the nvarchar(50) - you'd be better using sysname. This is a synonym in SQL Server (for nvarchar(128)) and represents the maximum length of an object identifier.
have a look at http://msdn.microsoft.com/en-us/library/ms188001.aspx - sp_executesql takes a parameter that is a string and executes the sql in that string. so you'd need to concatenate #SERVER_FROM and other params with the INSERT INTO part to make the entire sql statement, and then pass to sp_executesql.
nvarchar(50) is fine, unless your server/database names are longer than that :)
You can create the select statement by concatenating all the information together and then use sp_executesql
so:
sp_executesql 'INSERT INTO ' + #SERVER_TO + '.' + #DATABASE_TO +
'.dbo.TableName SELECT * FROM ' + #SERVER_FROM + '.' +
#DATABASE_FROM+'.dbo.TableName'
I like to make templates for dynamic SQL things like this - it's a lot easier to maintain complex statements and also sometimes easier to handle nested quotes - and definitely easier when terms need to be repeated in multiple places (like column lists):
DECLARE #sql AS nvarchar(max);
SET #sql = 'INSERT INTO {#SERVER_TO}.{#DATABASE_TO}.dbo.TableName
SELECT *
FROM {#SERVER_FROM}.{#DATABASE_FROM}.dbo.TableName'
SET #sql = REPLACE(#sql, '{#SERVER_TO}', QUOTENAME(#SERVER_TO))
SET #sql = REPLACE(#sql, '{#DATABASE_TO}', QUOTENAME(#DATABASE_TO))
SET #sql = REPLACE(#sql, '{#SERVER_FROM}', QUOTENAME(#SERVER_FROM))
SET #sql = REPLACE(#sql, '{#DATABASE_FROM}', QUOTENAME(#DATABASE_FROM))
EXEC(#sql)

SQL Update columns passing into the query the column name and value

I have the following code:
UPDATE myTable
SET Col1 = #Value
However, I have a table that has over a 100 columns and want to be able to specify a column name by passing the name into the query similar to:
UPDATE myTable
SET #ColName = #Value
When I do this I get an error. Is there a good solution to this? Its probably something simple!
Thank you in advanced.
You'll have to use dynamic SQL, and write it to make sure you don't let Little Bobby Tables in. Something like this:
DECLARE #sql NVARCHAR(500)
SET #sql = N'UPDATE myTable SET ' + QUOTENAME(#colName) + ' = #pUpdateVal'
EXEC sp_ExecuteSQL #sql, '#pUpdateVal NVARCHAR(20)', #value
Make sure you change the type of #pUpdateVal to something appropriate for your environment, but this will mitigate the risk of injection attacks.
You'd have to revert to dynamic SQL to do this.
Agreed with the others, you'll need dynamic SQL for this; you can't define object names at run time in native SQL. For a full discussion on dynamic SQL see http://www.sommarskog.se/dynamic_sql.html