Return a row from all tables and all databases? - sql

How would be the SQL SELECT statement for returning a row from all data bases on the server, but just from a specific table and some of the columns of the table.
Or, in pseudo code, something like this:
for each(database)
{
return database.column.row;
}

This was not tested, but it should be enough to get you started.
DECLARE #name as NVARCHAR(128);
DECLARE #sql AS NVARCHAR(max);
DECLARE c_Cursor CURSOR FOR
SELECT databases.name
FROM sys.databases
WHERE databases.database_id > 4
ORDER BY databases.name;
OPEN c_Cursor;
FETCH NEXT FROM c_Cursor
INTO #name;
WHILE ##FETCH_STATUS = 0
BEGIN
SET #sql = N'SELECT table.* FROM ' + QUOTENAME(#name) + N'.dbo.table';
EXEC #sql
FETCH NEXT FROM c_Cursor
INTO #name;
END;
CLOSE c_Cursor;
DEALLOCATE c_Cursor;

Related

Delete multiple records from table through cursor in sql server

there are number of test IP's which I would like to remove through system defined sp
exec sp_delete_firewall_rule from sys.firewall_rules table in sql server
I am using below cursor but its not working
declare #name nvarchar(max)
declare cur CURSOR LOCAL for
select #name from sys.firewall_rules where [name] like '%TestIP%'
open cur
fetch next from cur into #name
while ##FETCH_STATUS = 0 BEGIN
exec sp_delete_firewall_rule #name
fetch next from cur into #name
END
close cur
deallocate cur
It worked for me, you just need to change a couple of things in your code.
In the select list include the table ColumnName [name] instead of variable. You did not pass any value to the variable so this gives a NULL result.
Include SP parameter while executing exec sp_delete_firewall_rule #name = #name1;
I have these IP’s in my firewall rules:
With the below code I am deleting the IP’s which has a name like TestIP1.
DECLARE #name1 nvarchar(128);
DECLARE MyCursor CURSOR FOR
SELECT [name] from sys.firewall_rules where [name] like '%TestIP1%';
OPEN MyCursor;
FETCH FROM MyCursor into #name1
WHILE ##FETCH_STATUS = 0 BEGIN
EXEC sp_delete_firewall_rule #name = #name1 ;
FETCH next from MyCursor into #name1
END
CLOSE MyCursor;
DEALLOCATE MyCursor;
GO
Now the result shows only 1 IP which is not included in the above delete list.

Only fetching first value in column

CREATE PROC [dbo].[usp_InsertGenerator]
AS
BEGIN
DECLARE #tablename varchar(max)
DECLARE cursCol1 CURSOR FOR
SELECT name FROM sys.tables
OPEN cursCol1
FETCH NEXT FROM cursCol1 INTO #tablename
DECLARE cursCol CURSOR FOR
SELECT column_name, data_type
FROM information_schema.columns
WHERE table_name = #tableName
OPEN cursCol
DECLARE #string nvarchar(3000)
DECLARE #stringData nvarchar(3000)
DECLARE #dataType nvarchar(1000)
SET #string='INSERT '+#tableName+'('
SET #stringData=''
DECLARE #colName nvarchar(50)
FETCH NEXT FROM cursCol INTO #colName,#dataType
IF ##fetch_status<>0
BEGIN
PRINT 'Table '+#tableName+' not found, processing skipped.'
--FETCH NEXT FROM cursCol1 INTO #tablename
CLOSE curscol
DEALLOCATE curscol
RETURN
END
WHILE ##FETCH_STATUS=0
--FETCH NEXT FROM cursCol1 INTO #tablename
BEGIN
IF #dataType in ('varchar','char','nchar','nvarchar')
BEGIN
SET #stringData=#stringData+'''''''''+
isnull('+#colName+','''')+'''''',''+'
END
ELSE
BEGIN
SET #stringData=#stringData+'''''''''+
isnull(cast('+#colName+' as varchar(200)),''0'')+'''''',''+'
END
SET #string=#string+#colName+','
FETCH NEXT FROM cursCol INTO #colName ,#dataType
END
BEGIN
DECLARE #Query nvarchar(4000)
SET #query ='SELECT '''+substring(#string,0,len(#string)) + ')
VALUES(''+ ' + substring(#stringData,0,len(#stringData)-2)+'''+'')''
FROM '+#tableName
PRINT (#query)
CLOSE cursCol1
DEALLOCATE cursCol1
CLOSE cursCol
DEALLOCATE cursCol
END
END
GO
When executing the procedure I am only getting first value(Row) from name column in sys.tables.
I want it for all the rows in the sys.tables.
Query should take each table name one by one then execute the query for every table so that I can get insert statement for all the tables.
Thanks in advance .
Please try using cursor to get name, cursCol1 Should be closed at last after cursCol. FETCH NEXT is also missing for cursCol1
CREATE PROC [dbo].[usp_InsertGenerator]
AS
BEGIN
DECLARE #tablename varchar(max)
DECLARE #tbl table (insertVal varchar(max))
DECLARE cursCol1 CURSOR FOR
SELECT name FROM sys.tables
OPEN cursCol1
FETCH NEXT FROM cursCol1 INTO #tablename
WHILE ##FETCH_STATUS=0
begin
DECLARE cursCol CURSOR FOR
SELECT column_name, data_type
FROM information_schema.columns
WHERE table_name = #tableName
OPEN cursCol
DECLARE #string nvarchar(3000)
DECLARE #stringData nvarchar(3000)
DECLARE #dataType nvarchar(1000)
SET #string='INSERT '+#tableName+'('
SET #stringData=''
DECLARE #colName nvarchar(50)
FETCH NEXT FROM cursCol INTO #colName,#dataType
IF ##fetch_status<>0
BEGIN
PRINT 'Table '+#tableName+' not found, processing skipped.'
FETCH NEXT FROM cursCol1 INTO #tablename
CLOSE curscol
DEALLOCATE curscol
RETURN
END
WHILE ##FETCH_STATUS=0
--FETCH NEXT FROM cursCol1 INTO #tablename
BEGIN
IF #dataType in ('varchar','char','nchar','nvarchar')
BEGIN
SET #stringData=#stringData+'''''''''+
isnull('+#colName+','''')+'''''',''+'
END
ELSE
BEGIN
SET #stringData=#stringData+'''''''''+
isnull(cast('+#colName+' as varchar(200)),''0'')+'''''',''+'
END
SET #string=#string+#colName+','
FETCH NEXT FROM cursCol INTO #colName ,#dataType
END
BEGIN
DECLARE #Query nvarchar(4000)
SET #query ='SELECT '''+substring(#string,0,len(#string)) + ')
VALUES(''+ ' + substring(#stringData,0,len(#stringData)-2)+'''+'')''
FROM '+#tableName
INSERT INTO #tbl (insertVal) EXEC (#query)
-- PRINT (#query)
END
CLOSE cursCol
DEALLOCATE cursCol
FETCH NEXT FROM cursCol1 INTO #tablename
END
CLOSE cursCol1
DEALLOCATE cursCol1
SELECT * FROM #tbl
END

Create an ms sql query to get data from tables belonging to different schemas

I have a table named 'tbl_user' and this table exists under many schemas for example :
schema1.tbl_user
schema2.tbl_user
and so on. I would like to union all the data in these tables and get a single result and I cannot use any programming language because the environment I need to run it doesn't allow for it. Is there a way to accomplish this on sql server 2008 using stored procedures?
Edit : There are over a thousand schemas and schemas can be added and deleted as time goes.
using cursor, create the query dynamic and execute at when completed.
You can add additional filter if you want to filter out the schema.
DECLARE #NAME VARCHAR(100)
DECLARE #SQL NVARCHAR(300)
DECLARE #TABLE_NAME NVARCHAR(300)='userMaster'
DECLARE CUR CURSOR FOR
SELECT S.name
from sys.schemas s
inner join sys.sysusers u
on u.uid = s.principal_id
order by s.name
OPEN CUR
FETCH NEXT FROM CUR INTO #NAME
WHILE ##FETCH_STATUS = 0
BEGIN
IF (EXISTS (SELECT *
FROM INFORMATION_SCHEMA.TABLES
WHERE TABLE_SCHEMA =#NAME
AND TABLE_NAME =#TABLE_NAME))
BEGIN
IF(LEN(#SQL)>0)
begin
SET #SQL =#SQL+' UNION ALL SELECT * FROM ['+#NAME+'].['+#TABLE_NAME+']'
end
ELSE
begin
SET #SQL ='SELECT * FROM ['+#NAME+'].['+#TABLE_NAME+']'
end
--PRINT #SQL
END
FETCH NEXT FROM CUR INTO #NAME
END
CLOSE CUR
DEALLOCATE CUR
PRINT #SQL
exec(#SQL)
Try this and remember Tables should have the same structure.
SELECT *
FROM schema1.tbl_user
UNION
SELECT *
FROM schema2.tbl_user
And for large number of schemas you can use the following stored procedure. This will generate the UNION query dynamically and you can add the conditions to filter out the schema and table names.
DECLARE #table_name NVARCHAR(100)
DECLARE #schema_name NVARCHAR(100)
DECLARE #gettable CURSOR
DECLARE #query NVARCHAR(100)
SET #query=''
SET #gettable = CURSOR FOR
SELECT name,
schema_name(schema_id)
FROM sys.tables
OPEN #gettable
FETCH NEXT
FROM #gettable INTO #table_name, #schema_name
WHILE ##FETCH_STATUS = 0
BEGIN
SET #query = #query + 'SELECT * FROM ' + #schema_name + '.'+ #table_name + ' UNION ';
FETCH NEXT
FROM #gettable INTO #table_name, #schema_name
END
CLOSE #gettable
DEALLOCATE #gettable
print #query;

SQL -Query to find specific column in all the tables of the database but having no null values

I am not an SQL Expertise. I need to search for the column which is present in all the tables of the database but which does not has null values stored for that specific record.
Below is the query that fetches me all the tables that has my column name:
SELECT TABLE_NAME, COLUMN_NAME
FROM INFORMATION_SCHEMA.COLUMNS
WHERE column_name LIKE 'classPK'
Try this...
declare #q nvarchar(1000);
declare cur_Select cursor for
select 'select * from ['+tab.name+'] where ['+col.name+'] is not null'
from sys.tables tab
join sys.columns col
on tab.object_id = col.object_id
where col.name like 'name'
open cur_Select
fetch next from cur_Select into #q
while ##FETCH_STATUS = 0
begin
exec sp_executesql #q
fetch next from cur_Select into #q
end
close cur_Select
deallocate cur_Select
Try with this statement:
DECLARE #TABLE_NAME NVARCHAR(MAX);
DECLARE #COLUMN_NAME NVARCHAR(MAX);
DECLARE #crs CURSOR;
DECLARE #query NVARCHAR(MAX);
set #crs = CURSOR FOR
SELECT TABLE_NAME, COLUMN_NAME
FROM INFORMATION_SCHEMA.COLUMNS
WHERE column_name LIKE 'CD_CIC_PROD%'
BEGIN TRY
OPEN #crs
END TRY
BEGIN CATCH
END CATCH
FETCH NEXT FROM #crs INTO
#TABLE_NAME, #COLUMN_NAME
WHILE (##FETCH_STATUS = 0)
BEGIN
set #query = 'SELECT * FROM ['+#TABLE_NAME+'] WHERE ['+#COLUMN_NAME+'] IS NOT NULL'
EXEC sp_executesql #query
FETCH NEXT FROM #crs INTO
#TABLE_NAME, #COLUMN_NAME
END

How to get the row count for views from a database?

I'm trying to make a customized view that gets me the row count for all the views and tables of a database.
Getting the count of table is damn in SQL Server
SELECT TABLE_SCHEMA,
TABLE_NAME = TABLES.TABLE_NAME,
RECORD_COUNT = MAX(SYSINDEXES.ROWS)
FROM SYS.SYSINDEXES "SYSINDEXES",
INFORMATION_SCHEMA.TABLES "TABLES"
WHERE TABLES.TABLE_NAME = OBJECT_NAME(SYSINDEXES.ID)
AND TABLES.TABLE_TYPE = 'BASE TABLE'
GROUP BY TABLES.TABLE_SCHEMA,
TABLES.TABLE_NAME
Now, I need to get the rowcount for VIEWS
I feel the only way is to count the number of rows from the views
i.e. count(*) from view_name
But, I could not find a way to have the rowcount for view along with view_name, table_schema and so on.
Any advance on this would be helpful.
Well, it isn't very pretty, but this should do the trick.
This applies to a single database because I'm using the system view 'all_views' to get the data. I'm sure it could be adapted if you wanted something else.
I've also limited the views I'm returning counts for, via the 'schema_id'. You can look at this and determine what would be best for you.
Lastly, I've just spit the results out so that you can view them if you run this in Management Studio. You would probably want to insert the results into a table or something instead. If so, it's simply a matter of changing the dynamic query from a select to an insert.
So without further adieu:
SET NOCOUNT ON
DECLARE #ViewName AS nVarChar(128)
, #Query AS nVarChar(500)
/* Declare Cursor */
DECLARE Cur_Views CURSOR
FOR
SELECT name
FROM [sys].[all_views] x
WHERE x.schema_id = 1
-- Loop through the views.
OPEN Cur_Views
-- Fetch the first view
FETCH NEXT FROM Cur_Views
INTO #ViewName
WHILE ##Fetch_Status = 0 BEGIN
-- Set up our dynamic sql
SELECT #Query = 'SELECT COUNT(*) AS [Count] FROM ' + #ViewName
-- Print the query we're executing for debugging purposes
-- PRINT #Query
-- Execute the dynamic query
EXECUTE(#Query)
-- Fetch subsequent views
FETCH NEXT FROM Cur_Views
INTO #ViewName
-- Loop back to the beginning
END -- WHILE ##Fetch_Status = 0 BEGIN
-- Close the cursor
CLOSE Cur_Views
-- Dispose of the cursor
DEALLOCATE Cur_Views
GO
Here , is the final solution:
SET NOCOUNT ON
DECLARE #ViewName AS nVarChar(128)
, #TmpQuery AS nVarChar(500)
, #Out3 as int
DECLARE Cur_Views CURSOR FOR
SELECT schema_name(schema_id)+'.'+name as "Table_Name" FROM [sys].[all_views]
OPEN Cur_Views
FETCH NEXT FROM Cur_Views INTO #ViewName
WHILE ##Fetch_Status = 0 BEGIN
--SELECT #Query = 'SELECT COUNT(*) AS [Count] FROM ' + #ViewName
--EXECUTE(#Query)
CREATE TABLE #Data (var int)
SELECT #TmpQuery = 'SELECT COUNT(*) AS [Count] FROM ' + #ViewName
INSERT #Data exec (#TmpQuery)
SELECT #Out3 = var from #Data
--PRINT #ViewName
--PRINT #Out3
insert into Person.ViewCountTracker values(#ViewName,#Out3)
DROP TABLE #Data
FETCH NEXT FROM Cur_Views INTO #ViewName
END
CLOSE Cur_Views
DEALLOCATE Cur_Views
GO
--create table Person.ViewCountTracker
--(
-- ViewName varchar(255),
-- RowValue int
--)
--select * from Person.ViewCountTracker
I know this is an old post and I do not intend to take credit from the marked answer but wanted to add to it.
SELECT #Query = 'SELECT ''' + #ViewName + ''' AS Name, COUNT(*) AS [Count] FROM ' + #ViewName
I added the View name to help distinguish the numbers more.
SET NOCOUNT ON
DECLARE #ViewName AS nVarChar(128), #TmpQuery AS nVarChar(384)
CREATE TABLE #Results (Name nVarChar(128), Cnt BigInt)
DECLARE Cur_Views CURSOR FOR SELECT schema_name(schema_id) + '.' + name AS Name FROM [sys].[all_views] WHERE is_ms_shipped = 0
OPEN Cur_Views
WHILE (1=1)
BEGIN
FETCH NEXT FROM Cur_Views INTO #ViewName
If ##Fetch_Status != 0 BREAK
SELECT #TmpQuery = 'SELECT ''' + #ViewName + ''' AS Name, COUNT_BIG(*) AS Cnt FROM ' + #ViewName + ' (NoLock)'
PRINT #TmpQuery
INSERT #Results EXEC (#TmpQuery)
END
CLOSE Cur_Views
DEALLOCATE Cur_Views
SET NOCOUNT OFF
SELECT * FROM #Results
DROP TABLE #Results
GO