I would like to split my database into two databases, a quick check showed that I can easily query, join, update tables across databases.
My main problem now is that to do this, I will have to do something like this.
SELECT *
FROM Database1.dbo.Table1,
Database2.dbo.Table2
As you can see I have to explicit mentioned database names, which means that if database name is deployed with a different name, this code will not work anymore.
Any ideas to overcome this problem?
You can use db_name() to get the current database name and dynamic sql to build a dynamic query.
Something like:
declare #databaseName nvarchar(max) = db_name()
declare #dynamicSql nvarchar(max) = 'SELECT * FROM '+ #databaseName + '.dbo.Table1'
exec sp_executesql #dynamicSql
Related
I need a way to compare a stored procedure across multiple (hundreds and hundreds) of databases. Not just compare two at a time. It looks like ApexSQL only does two at a time (unless I am mistaken). This won't work because it will take forever. I need to group by the stored procedure so I can identify which groups I can make certain changes to.
I tried the following code solution:
select
'select OBJECT_NAME(object_id), OBJECT_DEFINITION(object_id) from ' +
name + '.sys.procedures where name like ''sp_someProcedure%'' union'
from
master.sys.databases
I then tried to throw the scripts that outputted into a sub select where I do a group by the stored procedure. This doesn't work because for some reason you can't union between multiple databases for sys stuff (unless I am mistaken). Each select statement stays in the context of what you are using. So use databaseOne stays in databaseOne even though the following select statement is select blah blah blah from databaseTwo.
Any thoughts?
Firstly, let's start off topic with a useful article: Is the sp_ prefix still a no-no?. Don't start your SP's name with sp_, it's reserved by Microsoft for system stored procedures. The article discusses further as to why it's a bad idea; but simply put, your SP could just (suddenly) stop working one day, and also it can have a performance hit.
Now, more on topic. You could instead use the undocumented sp sp_msforeachdb. This results in something like:
CREATE TABLE #Procs (ObjectName sysname, ObjectDefination nvarchar(MAX));
DECLARE #SQL nvarchar(MAX);
SET #SQL = N'SELECT OBJECT_NAME(object_id), OBJECT_DEFINITION(object_id)' + NCHAR(10) +
N'FROM [?].sys.procedures' + NCHAR(10) +
N'WHERE [name] LIKE ''sp_someProcedure%'';';
INSERT INTO #Procs
EXEC sp_msforeachdb #SQL;
SELECT *
FROM #Procs;
DROP TABLE #Procs;
I have been researching this for a couple of days and feel like I am going around in circles. I have basic knowledge of SQL but there are many areas I do not understand.
I have a table that stores the names and fields of all the other tables in my database.
tblFields
===================================================
TableName FieldName BookmarkName
---------------------------------------------------
Customer FirstName CustomerFirstName
Customer LastName CustomerLastName
Customer DOB CustomerDOB
I want to write a SELECT statement like the following but i am unable to get it work:
SELECT (SELECT [FieldName] FROM [TableName]) FROM tblFields
Is this possible? The application I have developed requires this for user customization of reports.
If i understand what you are trying to do, i think this will help you. It is not pretty and it works for SQL Server 2005 and above, but maybe this is what you are looking for:
declare #tableName nvarchar(100)
declare #sqlQuery nvarchar(max)
declare #fields varchar(500)
set #tableName = 'YourTableName'
set #fields = ''
select #fields = #fields + QUOTENAME(t.fieldname) + ',' from (
select distinct fieldname from tblfields where tablename = #tableName)t
set #sqlQuery = 'select ' + left(#fields, LEN(#fields)-1) + ' from ' + QUOTENAME(#tableName)
execute sp_executesql #sqlQuery
Edit: As Martin suggested, i edited so that the columns and tablename are using QUOTENAME
If I understand correctly what you are trying to do, you are probably better off doing this as two separate queries from your program. One which gets the fields you want to select which you then use in your program to build up the second query which actually gets the data.
If it must be done entirely in SQL, then you will need to tell us what database you are using. If it is SQL Server, you might be able to user a cursor over the first query to build up the second query which you then execute with the sp_executesql stored procedure. But doing doing it outside of SQL would be recommended.
I'm trying to make a simple select query on several databases on the same server, the server has 104 databases where 52 have the same schema so that is 2 different schemas (this are being generated by equipment on production floor, is a mistake that I have to handle until the equipment vendor figures how to create a single database for each scheme).
So I have a query like
select *
from TB_AOIResult
where serialnumber = 'snx'
At first I use this, it retrieves the data, but also a lot of errors as several databases on the server do not have that table .
[exec sp_MSforeachdb 'use ?;SELECT * FROM \[TB_AOIResult\] where barcode ="102564AG1710200018476"'
go]1
then
so far the only way that I have found is to declare all the 52 databases (at this moment, the machines will generate a new db per week) in this statement, that is severally impractical
declare #sql1 as VARCHAR(4000)
SET #sql1 ='IF ''?''IN(''KY_Result_201715'',''KY_Result_201714'',''KY_Result_201713'',''KY_Result_201712''[enter image description here][2])
EXECUTE(''USE [?]
SELECT * FROM [TB_AOIResult] where barcode ="102564AG1710200018476" '')'
EXEC sp_MSforeachdb #command1 = #sql1
Could someone help me and explain me if there is any other way to do this query in all the databases with the same schema and avoid to run in the ones that does not have the table, without write the name of each database?
Thanks
Finally I solve it as follows:
exec sp_MSforeachdb #command1 = 'USE ?;
IF EXISTS (SELECT * FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_NAME = N''TB_AOIResult'') BEGIN SELECT * FROM TB_AOIResult where barcode like ''102564AG171020001847%'' END'
go
I need to TRIM databases as per requirement. So, I'm using below script and giving database names manually. All I need is to automate the script to get database names automatically. Can anyone please suggest how to get the database name automatically.
Use [Sales_backup_2015_05_31_230001_7137975]
Exec [spMaint_TrimTestDB] 1
Go
for Eg:
instead of giving manually Sales_backup_2015_05_31_230001_7137975 I need to get db name automatically
Thanks.
There is a function DB_NAME() that would return the name of the current database if no parameters are passed. Check this.
I guess dynamic SQL might help you to run SP in different databases:
DECLARE #sql nvarchar(max)
SELECT #sql = (
SELECT N'Use '+QUOTENAME([name]) +' Exec [spMaint_TrimTestDB] 1;'
FROM sys.databases
WHERE database_id >= 5 AND [name] like 'Sales_backup%'
FOR XML PATH('')
)
EXEC sp_executesql #sql
This script will create and execute dynamic statement like:
Use [sales_backup_2015] Exec [spMaint_TrimTestDB] 1;
Use [sales_backup_2016] Exec [spMaint_TrimTestDB] 1;
etc...
I have a SQL 2008 database that is stored on the same instance, but this database is created by the user and name is stored in SQL table. How do I write a select statement using dynamic sql or is there a another way
So for example:
Main database - myDB
User database - userDB (this is stored in a myDB.dbo.tblUserDatabase)
userDB has a table called tblUserReports
I want to write something like this in dynamic sql:
SELECT * FROM userDB.dbo.tblUserReports
So tried:
declare #dbUser varchar(50)
set #dbUser = (SELECT strDBName FROM myDB.dbo.tblUserDatabase)
SELECT * FROM #dbUser.dbo.tblUserReports
You can do this... dynamic sql can become unmanageable very quickly so be careful.
declare #dbUser varchar(50)
set #dbUser = (SELECT strDBName FROM myDB.dbo.tblUserDatabase)
DECLARE #sql NVARCHAR(1000)
SET #sql = 'SELECT * FROM ' + QUOTENAME(#dbUser) + '.dbo.tblUserReports'
EXEC sp_executesql #sql
You cannot parameterise the table name. You will have to use dynamic SQL in your client or stored procedures. It's a very unusual thing to want to do so think long & hard about if this is a good design. Maybe if you share what you are doing then you'll get some additional ideas as to how to approach your problem.