How to delete all rows from all tables in Azure SQL Database? - sql

I tried to use the answer given Here. But Azure SQL does not have 'sp_MSForEachTable'.
Any help would be appreciated

sp_MSForEachTable is a not documented stored procedure.
We can manually create it in Azure SQL database.
Bellow is the whole statement of the full sp_MSForEachTable:
Step 1: create [dbo].[sp_MSforeach_worker]:
CREATE proc [dbo].[sp_MSforeach_worker]
#command1 nvarchar(2000), #replacechar nchar(1) = N'?', #command2 nvarchar(2000) = null, #command3 nvarchar(2000) = null, #worker_type int =1
as
create table #qtemp ( /* Temp command storage */
qnum int NOT NULL,
qchar nvarchar(2000) COLLATE database_default NULL
)
set nocount on
declare #name nvarchar(517), #namelen int, #q1 nvarchar(2000), #q2 nvarchar(2000)
declare #q3 nvarchar(2000), #q4 nvarchar(2000), #q5 nvarchar(2000)
declare #q6 nvarchar(2000), #q7 nvarchar(2000), #q8 nvarchar(2000), #q9 nvarchar(2000), #q10 nvarchar(2000)
declare #cmd nvarchar(2000), #replacecharindex int, #useq tinyint, #usecmd tinyint, #nextcmd nvarchar(2000)
declare #namesave nvarchar(517), #nametmp nvarchar(517), #nametmp2 nvarchar(258)
declare #local_cursor cursor
if #worker_type=1
set #local_cursor = hCForEachDatabase
else
set #local_cursor = hCForEachTable
open #local_cursor
fetch #local_cursor into #name
while (##fetch_status >= 0) begin
select #namesave = #name
select #useq = 1, #usecmd = 1, #cmd = #command1, #namelen = datalength(#name)
while (#cmd is not null) begin /* Generate #q* for exec() */
select #replacecharindex = charindex(#replacechar, #cmd)
while (#replacecharindex <> 0) begin
/* 7.0, if name contains ' character, and the name has been single quoted in command, double all of them in dbname */
/* if the name has not been single quoted in command, do not doulbe them */
/* if name contains ] character, and the name has been [] quoted in command, double all of ] in dbname */
select #name = #namesave
select #namelen = datalength(#name)
declare #tempindex int
if (substring(#cmd, #replacecharindex - 1, 1) = N'''') begin
/* if ? is inside of '', we need to double all the ' in name */
select #name = REPLACE(#name, N'''', N'''''')
end else if (substring(#cmd, #replacecharindex - 1, 1) = N'[') begin
/* if ? is inside of [], we need to double all the ] in name */
select #name = REPLACE(#name, N']', N']]')
end else if ((#name LIKE N'%].%]') and (substring(#name, 1, 1) = N'[')) begin
/* ? is NOT inside of [] nor '', and the name is in [owner].[name] format, handle it */
/* !!! work around, when using LIKE to find string pattern, can't use '[', since LIKE operator is treating '[' as a wide char */
select #tempindex = charindex(N'].[', #name)
select #nametmp = substring(#name, 2, #tempindex-2 )
select #nametmp2 = substring(#name, #tempindex+3, len(#name)-#tempindex-3 )
select #nametmp = REPLACE(#nametmp, N']', N']]')
select #nametmp2 = REPLACE(#nametmp2, N']', N']]')
select #name = N'[' + #nametmp + N'].[' + #nametmp2 + ']'
end else if ((#name LIKE N'%]') and (substring(#name, 1, 1) = N'[')) begin
/* ? is NOT inside of [] nor '', and the name is in [name] format, handle it */
/* j.i.c., since we should not fall into this case */
/* !!! work around, when using LIKE to find string pattern, can't use '[', since LIKE operator is treating '[' as a wide char */
select #nametmp = substring(#name, 2, len(#name)-2 )
select #nametmp = REPLACE(#nametmp, N']', N']]')
select #name = N'[' + #nametmp + N']'
end
/* Get the new length */
select #namelen = datalength(#name)
/* start normal process */
if (datalength(#cmd) + #namelen - 1 > 2000) begin
/* Overflow; put preceding stuff into the temp table */
if (#useq > 9) begin
close #local_cursor
if #worker_type=1
deallocate hCForEachDatabase
else
deallocate hCForEachTable
return 1
end
if (#replacecharindex < #namelen) begin
/* If this happened close to beginning, make sure expansion has enough room. */
/* In this case no trailing space can occur as the row ends with #name. */
select #nextcmd = substring(#cmd, 1, #replacecharindex)
select #cmd = substring(#cmd, #replacecharindex + 1, 2000)
select #nextcmd = stuff(#nextcmd, #replacecharindex, 1, #name)
select #replacecharindex = charindex(#replacechar, #cmd)
insert #qtemp values (#useq, #nextcmd)
select #useq = #useq + 1
continue
end
/* Move the string down and stuff() in-place. */
/* Because varchar columns trim trailing spaces, we may need to prepend one to the following string. */
/* In this case, the char to be replaced is moved over by one. */
insert #qtemp values (#useq, substring(#cmd, 1, #replacecharindex - 1))
if (substring(#cmd, #replacecharindex - 1, 1) = N' ') begin
select #cmd = N' ' + substring(#cmd, #replacecharindex, 2000)
select #replacecharindex = 2
end else begin
select #cmd = substring(#cmd, #replacecharindex, 2000)
select #replacecharindex = 1
end
select #useq = #useq + 1
end
select #cmd = stuff(#cmd, #replacecharindex, 1, #name)
select #replacecharindex = charindex(#replacechar, #cmd)
end
/* Done replacing for current #cmd. Get the next one and see if it's to be appended. */
select #usecmd = #usecmd + 1
select #nextcmd = case (#usecmd) when 2 then #command2 when 3 then #command3 else null end
if (#nextcmd is not null and substring(#nextcmd, 1, 2) = N'++') begin
insert #qtemp values (#useq, #cmd)
select #cmd = substring(#nextcmd, 3, 2000), #useq = #useq + 1
continue
end
/* Now exec() the generated #q*, and see if we had more commands to exec(). Continue even if errors. */
/* Null them first as the no-result-set case won't. */
select #q1 = null, #q2 = null, #q3 = null, #q4 = null, #q5 = null, #q6 = null, #q7 = null, #q8 = null, #q9 = null, #q10 = null
select #q1 = qchar from #qtemp where qnum = 1
select #q2 = qchar from #qtemp where qnum = 2
select #q3 = qchar from #qtemp where qnum = 3
select #q4 = qchar from #qtemp where qnum = 4
select #q5 = qchar from #qtemp where qnum = 5
select #q6 = qchar from #qtemp where qnum = 6
select #q7 = qchar from #qtemp where qnum = 7
select #q8 = qchar from #qtemp where qnum = 8
select #q9 = qchar from #qtemp where qnum = 9
select #q10 = qchar from #qtemp where qnum = 10
truncate table #qtemp
exec (#q1 + #q2 + #q3 + #q4 + #q5 + #q6 + #q7 + #q8 + #q9 + #q10 + #cmd)
select #cmd = #nextcmd, #useq = 1
end
fetch #local_cursor into #name
end /* while FETCH_SUCCESS */
close #local_cursor
if #worker_type=1
deallocate hCForEachDatabase
else
deallocate hCForEachTable
return 0
GO
Step 2: Create proc [dbo].[sp_MSforeachtable]
CREATE proc [dbo].[sp_MSforeachtable]
#command1 nvarchar(2000), #replacechar nchar(1) = N'?', #command2 nvarchar(2000) = null,
#command3 nvarchar(2000) = null, #whereand nvarchar(2000) = null,
#precommand nvarchar(2000) = null, #postcommand nvarchar(2000) = null
AS
declare #mscat nvarchar(12)
select #mscat = ltrim(str(convert(int, 0x0002)))
if (#precommand is not null)
exec(#precommand)
exec(N'declare hCForEachTable cursor global for select ''['' + REPLACE(schema_name(syso.schema_id), N'']'', N'']]'') + '']'' + ''.'' + ''['' + REPLACE(object_name(o.id), N'']'', N'']]'') + '']'' from dbo.sysobjects o join sys.all_objects syso on o.id = syso.object_id '
+ N' where OBJECTPROPERTY(o.id, N''IsUserTable'') = 1 ' + N' and o.category & ' + #mscat + N' = 0 '
+ #whereand)
declare #retval int
select #retval = ##error
if (#retval = 0)
exec #retval = dbo.sp_MSforeach_worker #command1, #replacechar, #command2, #command3, 0
if (#retval = 0 and #postcommand is not null)
exec(#postcommand)
return #retval
GO
Then you won't get the message: "The module 'sp_MSforeachtable' depends on the missing object 'dbo.sp_MSforeach_worker'. The module will still be created; however, it cannot run successfully until the object exists".
Ref: A Copy Of sp_MSforeachtable Stored Procedure For Azure, Uses sp_MSforeach_worker
I tested and it works in Azure SQL database:
Delete all the table data:
--Delete all the table data.
EXEC sp_msforeachtable 'DELETE FROM ?'
Data check:
Hope this helps.

Related

Search a string in whole mysql database

I wrote this query for searching a string in whole database . Earlier it was working properly now it doesn't fetch full result at all . I don't get what is wrong with this query . Please help
QUERY
/*
- Search through tables to find specific text
- Written by Luis Chiriff (with help from SQL Server Central)
- luis.chiriff#gmail.com # 24/11/2008 # 11:54
*/
-- Variable Declaration
Declare #StringToFind VARCHAR(200), #Schema sysname, #Table sysname, #FullTable int, #NewMinID
int, #NewMaxID int,
#SQLCommand VARCHAR(8000), #BaseSQLCommand varchar(8000), #Where VARCHAR(8000), #CountCheck
varchar(8000) , #FieldTypes varchar(8000),
#cursor VARCHAR(8000), #columnName sysname, #SCn int, #SCm int
Declare #TableList table (Id int identity(1,1) not null, tablename varchar(250))
Declare #SQLCmds table (id int identity(1,1) not null, sqlcmd varchar(8000))
Declare #DataFoundInTables table (id int identity(1,1) not null, sqlcmd varchar(8000))
-- Settings
SET #StringToFind = 'abcdef'
SET NOCOUNT ON
SET #StringToFind = '%'+#StringToFind+'%'
-- Gathering Info
if ((select count(*) from sysobjects where name = 'tempcount') > 0)
drop table tempcount
create table tempcount (rowsfound int)
insert into tempcount select 0
-- This section here is to accomodate the user defined datatypes, if they have
-- a SQL Collation then they are assumed to have text in them.
SET #FieldTypes = ''
select #FieldTypes = #FieldTypes + '''' + rtrim(ltrim(name))+''',' from systypes where collation
is not null or xtype = 36
select #FieldTypes = left(#FieldTypes,(len(#FieldTypes)-1))
insert into #TableList (tablename)
select name from sysobjects
where xtype = 'U' and name not like 'dtproperties'
order by name
-- Start Processing Table List
select #NewMinID = min(id), #NewMaxID = max(id) from #TableList
while(#NewMinID <= #NewMaxID)
Begin
SELECT #Table = tablename, #Schema='dbo', #Where = '' from #TableList where id = #NewMinID
SET #SQLCommand = 'SELECT * FROM ' + #Table + ' WHERE'
-- removed ' + #Schema + '.
SET #cursor = 'DECLARE col_cursor CURSOR FOR SELECT COLUMN_NAME
FROM [' + DB_NAME() + '].INFORMATION_SCHEMA.COLUMNS
WHERE TABLE_SCHEMA = ''' + #Schema + '''
AND TABLE_NAME = ''' + #Table + '''
AND DATA_TYPE IN ('+#FieldTypes+')'
--Original Check, however the above implements user defined data types --AND DATA_TYPE IN
(''char'',''nchar'',''ntext'',''nvarchar'',''text'',''varchar'')'
EXEC (#cursor)
SET #FullTable = 0
DELETE FROM #SQLCmds
OPEN col_cursor
FETCH NEXT FROM col_cursor INTO #columnName
WHILE ##FETCH_STATUS = 0
BEGIN
SET #Where = #Where + ' [' + #columnName + '] LIKE ''' + #StringToFind + ''''
SET #Where = #Where + ' OR'
--PRINT #Table + '|'+ cast(len(isnull(#Where,''))+len(isnull(#SQLCommand,'')) as varchar(10))+'|'+#Where
if (len(isnull(#Where,''))+len(isnull(#SQLCommand,'')) > 3600)
Begin
SELECT #Where = substring(#Where,1,len(#Where)-3)
insert into #SQLCmds (sqlcmd) select #Where
SET #Where = ''
End
FETCH NEXT FROM col_cursor INTO #columnName
END
CLOSE col_cursor
DEALLOCATE col_cursor
if (#Where <> '')
Begin
SELECT #Where = substring(#Where,1,len(#Where)-3)
insert into #SQLCmds (sqlcmd)
select #Where --select #Table,count(*) from #SQLCmds
End
SET #BaseSQLCommand = #SQLCommand
select #SCn = min(id), #SCm = max(id) from #SQLCmds
while(#SCn <= #SCm)
Begin
select #Where = sqlcmd from #SQLCmds where ID = #SCn
if (#Where <> '')
Begin
SET #SQLCommand = #BaseSQLCommand + #Where
SELECT #CountCheck = 'update tempcount set rowsfound = (select count(*) '+ substring(#SQLCommand,10,len(#SQLCommand)) + ')'
EXEC (#CountCheck)
if ((select rowsfound from tempcount) > 0)
Begin
PRINT '--- ['+cast(#NewMinID as varchar(15))+'/'+cast(#NewMaxID as varchar(15))+'] '+#Table + ' ----------------------------------[FOUND!]'
--PRINT '--- [FOUND USING:] ' +#SQLCommand
insert into #DataFoundInTables (sqlcmd) select #SQLCommand
EXEC (#SQLCommand)
update tempcount set rowsfound = 0
End
else
Begin
PRINT '--- ['+cast(#NewMinID as varchar(15))+'/'+cast(#NewMaxID as varchar(15))+'] '+#Table
End
End
SET #SCn = #SCn + 1
End
set #NewMinID = #NewMinID + 1
end
if ((select count(*) from sysobjects where name = 'tempcount') > 0)
drop table tempcount
/*
This will now return all the sql commands you need to use
*/
select #NewMinID = min(id), #NewMaxID = max(id) from #DataFoundInTables
if (#NewMaxID > 0)
Begin
PRINT ' '
PRINT ' '
PRINT '-----------------------------------------'
PRINT '----------- TABLES WITH DATA ------------'
PRINT '-----------------------------------------'
PRINT ' '
PRINT 'We found ' + cast(#NewMaxID as varchar(10)) + ' table(s) with the string '+#StringToFind
PRINT ' '
while(#NewMinID <= #NewMaxID)
Begin
select #SQLCommand = sqlcmd from #DataFoundInTables where ID = #NewMinID
PRINT #SQLCommand
SET #NewMinID = #NewMinID + 1
End
PRINT ' '
PRINT '-----------------------------------------'
End
This query was working fine one month ago but now it doesn't fetch the results . Can anyone tell me what is wrong in this query .

Dynamic SQL - parametrized query

I use dynamic sql with parameters and have problem :)
In block of code it works, but when I call procedure I have error that I need to declare scalar variable #name_dummy
So:
DECLARE #START_TIME DATETIME = GETDATE()
DECLARE #TMP_NAMES TABLE (
SCHEMA_N VARCHAR(500),
TABLE_N VARCHAR(500),
CONDITION VARCHAR(MAX),
TARGETDB VARCHAR(500),
SOURCEDB VARCHAR(500),
COLUMN_LIST VARCHAR(MAX)
)
DECLARE #SCHEMA_N VARCHAR(500)
DECLARE #TABLE_N VARCHAR(500)
DECLARE #CONDITION VARCHAR(MAX)
DECLARE #COLUMN_LIST VARCHAR(MAX)
DECLARE #TARGETDB VARCHAR(500)
DECLARE #SOURCEDB VARCHAR(500)
INSERT INTO #TMP_NAMES
SELECT
o.SCHEMA_N
,o.TABLE_N
,o.Condition
,o.TargetDB
,o.SourceDB
,STUFF((SELECT
', ' + c.name
FROM sys.columns c
WHERE c.object_id = o.object_id
AND c.system_type_id <> 189 /* Pomijam timestamp*/
ORDER BY c.column_id
FOR XML PATH (''))
, 1, 1, '')
FROM Table_A o
ORDER BY 1,
2
SELECT
SCHEMA_N
,TABLE_N
,CONDITION
,TARGETDB
,SOURCEDB
,COLUMN_LIST
FROM #TMP_NAMES
DECLARE KUR CURSOR
FOR
SELECT
SCHEMA_N
,TABLE_N
,CONDITION
,TARGETDB
,SOURCEDB
,COLUMN_LIST
FROM #TMP_NAMES
OPEN KUR
FETCH NEXT
FROM KUR
INTO #SCHEMA_N,
#TABLE_N,
#CONDITION,
#TARGETDB,
#SOURCEDB,
#COLUMN_LIST
WHILE ##FETCH_STATUS = 0
BEGIN
DECLARE #TOP VARCHAR(100)
SET #TOP = ( SELECT CAST(Wartosc AS VARCHAR) FROM Table_B WHERE Id = 3 )
IF #TOP < 40000
SET #TOP = 40000
WHILE ( 1 = 1 )
BEGIN
DECLARE #CHECK BIT = 0
DECLARE #sqlCMD NVARCHAR(MAX) = 'SELECT TOP 1 #check_exists = 1 FROM '
+ #SOURCEDB + '.' + #SCHEMA_N + '.' + #TABLE_N + ' WHERE ' + #CONDITION
exec sp_executesql #sqlCMD, N'#check_exists bit OUTPUT, #START_TIME DATE', #check_exists = #CHECK OUTPUT, #START_TIME = #START_TIME;
SELECT #sqlCMD , #CHECK
END
END
FETCH NEXT
FROM KUR
INTO #SCHEMA_N,
#TABLE_N,
#CONDITION,
#TARGETDB,
#SOURCEDB,
#COLUMN_LIST
CLOSE KUR;
DEALLOCATE KUR
And when I execute this it's compiling and works ( returns values ) for example sql which I want to execute.
SELECT TOP 1 #check_exists = 1 FROM MSSF15_WarstwaPosrednia.KatalogZdarzen.MSSF_RaportZdarzenPLKB2CS2K WHERE StatusPrzetwarzania = 4 AND DataWpisu < DATEADD(MONTH, -3, #START_TIME)
Parameters work here ( #check_exists which is output and #START_TIME condition param ) , but when I execute this in procedure I'm getting error
Must declare the scalar variable "#START_TIME". 137
SP definition:
USE xxxx
/****** Object: StoredProcedure dbo.dummy Script Date: 06/09/2018 13:40:22 ******/
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
ALTER PROCEDURE dbo.dummy
AS
BEGIN
/*
PRZENIESIENIE DANYCH
*/
DECLARE #START_TIME DATETIME = GETDATE()
DECLARE #TMP_NAMES TABLE (
SCHEMA_N VARCHAR(500),
TABLE_N VARCHAR(500),
CONDITION VARCHAR(MAX),
TARGETDB VARCHAR(500),
SOURCEDB VARCHAR(500),
COLUMN_LIST VARCHAR(MAX)
)
DECLARE #SCHEMA_N VARCHAR(500)
DECLARE #TABLE_N VARCHAR(500)
DECLARE #CONDITION VARCHAR(MAX)
DECLARE #COLUMN_LIST VARCHAR(MAX)
DECLARE #TARGETDB VARCHAR(500)
DECLARE #SOURCEDB VARCHAR(500)
INSERT INTO #TMP_NAMES
SELECT o.SCHEMA_N,
o.TABLE_N,
o.Condition,
o.TargetDB,
o.SourceDB,
STUFF((
SELECT ', ' + c.NAME
FROM sys.columns c
WHERE c.object_id = o.object_id
AND c.system_type_id <> 189 /* Pomijam timestamp*/
ORDER BY c.column_id
FOR XML PATH('')
), 1, 1, '')
FROM dbo.Table_A o
ORDER BY 1,
2
SELECT SCHEMA_N,
TABLE_N,
CONDITION,
TARGETDB,
SOURCEDB,
COLUMN_LIST
FROM #TMP_NAMES
DECLARE KUR CURSOR
FOR
SELECT SCHEMA_N,
TABLE_N,
CONDITION,
TARGETDB,
SOURCEDB,
COLUMN_LIST
FROM #TMP_NAMES
OPEN KUR
FETCH NEXT
FROM KUR
INTO #SCHEMA_N,
#TABLE_N,
#CONDITION,
#TARGETDB,
#SOURCEDB,
#COLUMN_LIST
WHILE ##FETCH_STATUS = 0
BEGIN
DECLARE #TOP VARCHAR(100)
SET #TOP = (
SELECT CAST(Wartosc AS VARCHAR)
FROM dbo.Table_B
WHERE Id = 3
)
IF #TOP < 40000
SET #TOP = 40000
WHILE (1 = 1)
BEGIN
BEGIN TRY
BEGIN TRANSACTION T_TEST
DECLARE #CHECK BIT = 0
DECLARE #START_TIME_P DATE = GETDATE()
DECLARE #sqlCMD NVARCHAR(MAX) = 'SELECT TOP 1 #check_exists = 1 FROM ' + #SOURCEDB + '.' + #SCHEMA_N + '.' + #TABLE_N + ' WHERE ' + #CONDITION
SELECT #CHECK,
#START_TIME_P,
#sqlCMD
EXEC sp_executesql #sqlCMD,
N'#check_exists bit OUTPUT, #START_TIME DATE',
#check_exists = #CHECK OUTPUT,
#START_TIME = #START_TIME_P;
IF OBJECT_ID('tempdb..#TMP_ID') IS NOT NULL
DROP TABLE #TMP_ID
CREATE TABLE #TMP_ID (Id INT)
EXEC (
'INSERT INTO #TMP_ID
SELECT TOP ' + #TOP + ' Id
FROM ' + #SOURCEDB + '.' + #SCHEMA_N + '.' + #TABLE_N + ' WHERE ' + #CONDITION
)
DECLARE #sqlCMD_Ins NVARCHAR(MAX)
SET #sqlCMD_Ins = 'INSERT INTO ' + #TARGETDB + '.' + #SCHEMA_N + '.' + #TABLE_N + ' '
SET #sqlCMD_Ins = #sqlCMD_Ins + 'SELECT ' + #COLUMN_LIST + ' FROM ' + #SOURCEDB + '.' + #SCHEMA_N + '.' + #TABLE_N + ' WHERE Id IN ( SELECT Id FROM #TMP_ID )'
IF #sqlCMD_Ins IS NULL
RAISERROR (
'Brak polecenia insert #sqlCMD_Ins',
16,
1
)
EXEC (#sqlCMD_Ins)
DECLARE #sqlCMD_Del NVARCHAR(MAX)
SET #sqlCMD_Del = 'DELETE FROM ' + #SOURCEDB + '.' + #SCHEMA_N + '.' + #TABLE_N + ' WHERE Id IN ( SELECT Id FROM #TMP_ID )'
IF #sqlCMD_Del IS NULL
RAISERROR (
'Brak polecenia insert #sqlCMD_Ins',
16,
1
)
EXEC (#sqlCMD_Del)
DROP TABLE #TMP_ID
COMMIT TRANSACTION T_TEST
END TRY
BEGIN CATCH
IF (##TRANCOUNT > 0)
BEGIN
ROLLBACK TRANSACTION T_TEST
PRINT 'Wycofanie zmian'
PRINT ERROR_MESSAGE() + ' ' + CAST(ERROR_NUMBER() AS VARCHAR(256))
END
END CATCH
IF #CHECK = 0
BREAK
END
EXEC ('SELECT ''' + #SOURCEDB + '.' + #SCHEMA_N + '.' + #TABLE_N + ''' AS DB ,COUNT(1) AS ILOSC FROM ' + #SOURCEDB + '.' + #SCHEMA_N + '.' + #TABLE_N + ' UNION ALL ' + 'SELECT ''' + #TARGETDB + '.' + #SCHEMA_N + '.' + #TABLE_N + ''' AS DB ,COUNT(1) AS ILOSC FROM ' + #TARGETDB + '.' + #SCHEMA_N + '.' + #TABLE_N)
FETCH NEXT
FROM KUR
INTO #SCHEMA_N,
#TABLE_N,
#CONDITION,
#TARGETDB,
#SOURCEDB,
#COLUMN_LIST
END
CLOSE KUR;
DEALLOCATE KUR;
DECLARE #END_TIME DATETIME = GETDATE()
SELECT 'Daty przetworzenia',
#START_TIME_P AS 'START',
#END_TIME AS 'END'
SELECT 'Czas (min)',
DATEDIFF(MINUTE, #START_TIME_P, #END_TIME)
END
Guys, maybe u have similar situation and can help.
Error msg
Wycofanie zmian
Must declare the scalar variable "#START_TIME". 137
Thanks
Instead of
exec sp_executesql #sqlCMD, N'#check_exists bit OUTPUT, #START_TIME DATE', #check_exists = #CHECK OUTPUT, #START_TIME = #START_TIME;
try
declare #date_in DATE = GETDATE()
exec sp_executesql #sqlCMD, N'#check_exists bit OUTPUT, #START_TIME DATE', #check_exists = #CHECK OUTPUT, #START_TIME = #date_in;

How to add generic condition to sp select?

I really don't know what to do in this situation, so don't be too harsh.
If I have my select:
declare #Id uniqueidentifier = 'some parent guid'
declare #Type int = 1 -- can be 1, 2 or 3
declare #UserType varchar(max) --can be 0, anything else than 0, or all users at once
if(#Type = 1)
set #UserType = 'and UserType <> 0'
if(#Type = 2)
set #UserType = 'and UserType = 0'
if(#Type = 3)
set #UserType = ''
select * from users where parentId = #Id + #UserType
What to do in the situation where condition is "generic"? Do i really need to create 3 different Sp?
You can use AND/OR logic to simulate the If-else condition in where clause. Try something like this
select * from users
where
parentid= #id
and
(
(#Type = 1 and UserType <> 0)
or
(#Type = 2 and UserType = 0)
or
(#Type = 3)
)
or you can also use Dynamic sql to do this
declare #Id uniqueidentifier = 'some parent guid'
declare #Type int = 1 -- can be 1, 2 or 3
Declare #UserType varchar(max) --can be 0, anything else than 0, or all users at once
Declare #sql nvarchar(max)
if(#Type = 1)
set #UserType = ' and UserType <> 0'
if(#Type = 2)
set #UserType = ' and UserType = 0'
if(#Type = 3)
set #UserType = ''
set #sql = 'select * from users where parentId ='''+ cast(#Id as varchar(25))+''''+ #UserType
--Print #sql
Exec sp_executesql #sql
Different select statements would be most efficient since each is a fundamentally different query. If static SQL becomes unwieldly, use dynamic SQL. Below is a parameterized example using techniques from http://www.sommarskog.se/dyn-search.html.
declare #sql nvarchar(MAX) = N'select * from users where parentId = #Id';
declare #Id uniqueidentifier = 'some parent guid';
declare #Type int = 1; -- can be 1, 2 or 3
declare #UserType varchar(max); --can be 0, anything else than 0, or all users at once
SET #sql = #sql + CASE #Type
WHEN 1 THEN N' and UserType <> 0'
WHEN 2 THEN N' and UserType = 0'
WHEN 3 THEN N'' END;
EXEC sp_executesql
#sql
, N'#Id uniqueidentifier'
, #Id = #Id;

Passing parametrs to dynamic query

I have a stored procedure as following, I need to pass paramters to the dynamic pivot. My query runs, I just need to do some filtering based on the passed parameters
-- AND (#SelectedSystemIDs IS NULL OR System.ID IN(select * from dbo.SplitInts_RBAR_1(#SelectedSystemIDs, ',')))
--AND ((#PlatformID IS NULL) OR (System.PlatformID = #PlatformID) OR (#PlatformID = 12 AND System.PlatformID <= 2))
-- AND (ServiceEntry.ServiceDateTime between #StartDate and #EndDate)
so I want to add the above criteria, how could achieve that?
ALTER PROCEDURE [dbo].[spExportStuff]
(#StartDate datetime,
#EndDate datetime,
#SelectedSystemIDs nvarchar (2000) = NULL,
#SelectedTsbIDs nvarchar (2000) = NULL,
#UserRoleID int
)
AS
DECLARE #InstrumentType int = NULL
DECLARE #PlatformID int = null
IF (#SelectedSystemIDs = '')
begin
SET #SelectedSystemIDs = NULL
END
IF (#SelectedTsbIDs = '')
begin
SET #SelectedTsbIDs = NULL
END
IF(#UserRoleID = 1)
BEGIN
SET #PlatformID = 1
END
IF(#UserRoleID = 2)
BEGIN
SET #PlatformID = 2
END
IF (#UserRoleID = 3)
BEGIN
SET #PlatformID = 12
END
IF(#UserRoleID = 4)
BEGIN
SET #PlatformID = 3
END
IF(#UserRoleID = 5)
BEGIN
SET #PlatformID = 4
END
IF(#UserRoleID = 6)
BEGIN
SET #PlatformID = NULL
END
DECLARE #PivotColumnHeaders NVARCHAR(MAX)
SELECT #PivotColumnHeaders =
COALESCE(
#PivotColumnHeaders + ',[' + cast(SystemFullName as Nvarchar) + ']',
'[' + cast(SystemFullName as varchar)+ ']'
)
FROM System
DECLARE #PivotTableSQL NVARCHAR(MAX)
SET #PivotTableSQL = N'
SELECT *
FROM (
SELECT
TSBNumber [TSBNumber],
SystemFullName,
ClosedDate
FROM ServiceEntry
INNER JOIN System
ON ServiceEntry.SystemID = System.ID
Group By TSBNumber, SystemFullName, ClosedDate
) AS PivotData
PIVOT (
max(ClosedDate)
FOR SystemFullName IN (
' + #PivotColumnHeaders + '
)
) AS PivotTable
'
EXECUTE(#PivotTableSQL)
you can construct the required criteria as another input to the stored procedure and append it to the dynamic query
ALTER PROCEDURE [dbo].[spExportStuff]
(#StartDate datetime,
#EndDate datetime,
#SelectedSystemIDs nvarchar (2000) = NULL,
#SelectedTsbIDs nvarchar (2000) = NULL,
#UserRoleID int,
#WhereClause varchar(max) -> this is the new parameter.
)
DECLARE #PivotTableSQL NVARCHAR(MAX)
SET #PivotTableSQL = N'
SELECT *
FROM (
SELECT
TSBNumber [TSBNumber],
SystemFullName,
ClosedDate
FROM ServiceEntry
INNER JOIN System
ON ServiceEntry.SystemID = System.ID
Group By TSBNumber, SystemFullName, ClosedDate
) AS PivotData
PIVOT (
max(ClosedDate)
FOR SystemFullName IN (
' + #PivotColumnHeaders + '
)
) AS PivotTable
' + #WhereClause -> you can append the where clause here.
EXECUTE(#PivotTableSQL)

Update TableType variable in dynamic SQL query

I had created User defined table type in my database. After that I had declared a variable of that table type in my procedure. And I had return my rest of the logic. At the end I am trying to update that table type variable using dynamic SQL.
But I got an error:
Msg 10700, Level 16, State 1, Line 1
The table-valued parameter "#ttbl_TagList" is READONLY and cannot be modified.
How can I solve the error?
User defined table type:
CREATE TYPE [dbo].[tt_TagList] AS TABLE(
[tagListId] [tinyint] IDENTITY(1,1) NOT NULL,
[tagId] [tinyint] NOT NULL DEFAULT ((0)),
[tagName] [varchar](100) NOT NULL DEFAULT (''),
[tagValue] [nvarchar](max) NOT NULL DEFAULT ('')
)
GO
Procedure:
CREATE PROCEDURE [dbo].[P_ReplaceTemplateTag]
AS
BEGIN
SET NOCOUNT ON;
DECLARE #ttbl_TagList dbo.tt_TagList, #V_TagId INT, #V_Counter TINYINT = 1,
#V_FinalQuery NVARCHAR(MAX) = '', #V_TagValue NVARCHAR(MAX);
INSERT INTO #ttbl_TagList (tagId, tagName, tagValue)
SELECT DISTINCT T.tagId, T.tagName, '' AS tagValue
FROM dbo.tbl_Tag T;
WHILE (1 = 1)
BEGIN
SET #V_TagValue = '';
SELECT #V_TagId = tagId FROM #ttbl_TagList WHERE tagListId = #V_Counter;
IF (##ROWCOUNT = 0)
BEGIN
BREAK;
END
IF (#V_TagId = 1)
BEGIN
/* Logic for getting tag value */
SET #V_TagValue = 'Tag Value 1';
END
ELSE IF (#V_TagId = 2)
BEGIN
/* Logic for getting tag value */
SET #V_TagValue = 'Tag Value 2';
END
ELSE IF (#V_TagId = 3)
BEGIN
/* Logic for getting tag value */
SET #V_TagValue = 'Tag Value 3';
END
ELSE IF (#V_TagId = 4)
BEGIN
/* Logic for getting tag value */
SET #V_TagValue = 'Tag Value 4';
END
IF (#V_TagValue != '')
BEGIN
SET #V_FinalQuery = #V_FinalQuery + ' WHEN ' + CONVERT(NVARCHAR(10), #V_Counter) + ' THEN ''' + #V_TagValue + '''';
END
SET #V_Counter = #V_Counter + 1;
END
IF (#V_FinalQuery != '')
BEGIN
SET #V_FinalQuery = N'UPDATE #ttbl_TagList SET tagValue = (CASE tagListId' + #V_FinalQuery + ' END)';
EXECUTE sp_executesql #V_FinalQuery, N'#ttbl_TagList dbo.tt_TagList readonly', #ttbl_TagList;
END
SELECT * FROM #ttbl_TagList;
END
TVP can not be updated directly. So try this one -
CREATE PROCEDURE [dbo].[P_ReplaceTemplateTag]
AS
BEGIN
SET NOCOUNT ON;
IF OBJECT_ID('tempdb.dbo.#t1') IS NOT NULL
DROP TABLE #t1
DECLARE
#ttbl_TagList dbo.tt_TagList
, #V_Counter TINYINT = 1
, #V_FinalQuery NVARCHAR(MAX) = ''
, #V_TagValue NVARCHAR(MAX);
INSERT INTO #ttbl_TagList (tagId, tagName, tagValue)
SELECT DISTINCT tagId, tagName, ''
FROM dbo.tbl_Tag;
WHILE (1 = 1) BEGIN
SELECT #V_TagValue =
CASE
WHEN tagId = 1 THEN 'Tag Value 1'
WHEN tagId = 2 THEN 'Tag Value 2'
WHEN tagId = 3 THEN 'Tag Value 3'
WHEN tagId = 4 THEN 'Tag Value 4'
ELSE ''
END
FROM #ttbl_TagList
WHERE tagListId = #V_Counter;
IF (##ROWCOUNT = 0) BREAK;
IF (#V_TagValue != '')
BEGIN
SET #V_FinalQuery = #V_FinalQuery + ' WHEN ' + CONVERT(NVARCHAR(10), #V_Counter) + ' THEN ''' + #V_TagValue + '''';
END
SET #V_Counter = #V_Counter + 1;
END
IF (#V_FinalQuery != '')
BEGIN
CREATE TABLE #t1
(
tagId TINYINT
, tagName VARCHAR(100)
, tagValue NVARCHAR(MAX)
)
SET #V_FinalQuery = N'
INSERT INTO #t1
SELECT tagId, tagName, (CASE tagListId' + #V_FinalQuery + ' END)
FROM #ttbl_TagList';
EXEC sys.sp_executesql
#V_FinalQuery
, N'#ttbl_TagList dbo.tt_TagList readonly'
, #ttbl_TagList;
END
SELECT * FROM #t1;
END