How to check all stored procedures which update a specific column - sql

Following is the sample to search stored procedures which have the keyword Student in them:
SELECT TOP (1000) *
FROM [eUniversityManagement].[sys].[all_sql_modules]
WHERE definition LIKE '%Student%'
I just wondering can we search any stored procedure that has and UPDATE on Student.name for example:
UPDATE STUDENT
SET Name = #Name,
Address = #Address,
DOB = #DOB
WHERE id = #StudentID
Thanks.

You can use the sys.dm_sql_referenced_entities function for this. It's a little complicated, as it wants the procedure name which references the column, so you need to start off with all objects and apply the functions
SELECT o.name, schema_name = s.name
FROM sys.objects o
JOIN sys.schemas s ON s.schema_id = o.schema_id
CROSS APPLY sys.dm_sql_referenced_entities (QUOTENAME(s.name) + '.' + QUOTENAME(o.name), 'OBJECT') r
WHERE o.type IN ('P', 'TR')
AND r.referenced_entity_name = 'student'
AND r.referenced_minor_name = 'Name'
AND r.is_updated = 1;

Related

extract a string from a stored proc definition

I need to check the library used by several stored procs that extract data from a remote server.
I have (with SO help, see SO 21708681) built the below code:
DECLARE #tProcs TABLE
(
procID int IDENTITY,
procObjectID nvarchar(100),
procName nvarchar(100)
);
insert into #tProcs
SELECT object_id, name
FROM sys.objects
WHERE type in (N'P', N'PC') and name like '%_Extract'
declare #countProcs int, #I int=0
select #countProcs=COUNT(*) from #tProcs
while #I<#countProcs
Begin
declare #source_code nvarchar(max)
declare #objectID nvarchar(50)
declare #proc_Name nvarchar(200)
select #objectID=procObjectID from #tProcs where procID=#I
select #proc_Name=procName from #tProcs where procID=#I
select #source_code = definition
from sys.sql_modules
where object_id = #objectID
SELECT PATINDEX('BOCTEST.%', #proc_Name) as Pos, #proc_Name
-- or SELECT charindex(#source_code, '%BOCTEST%')
set #I=#I+1
End
Inside each of the target stored procs there is a line like this:
DECLARE YP040P_cursor CURSOR FOR SELECT * FROM BOCTEST.S653C36C.LIVEBOC_A.YP040P
I need to know for each of the stored procs the part 'LIVEBOC_A' (which can either be 'LIVEBOC_A' or LIVEBOC_B)
I tried to use PATINDEX and CHARINDEX to get the location of the start opf that string in the definition from sysmodules but all I get back is either zero or an error that string or binary data would be truncated.
try
SELECT
name,
table_name = CASE WHEN OBJECT_DEFINITION(OBJECT_ID) LIKE '%BOCTEST.S653C36C.LIVEBOC_A.YP040P%' THEN 'LIVEBOC_A'
WHEN OBJECT_DEFINITION(OBJECT_ID) LIKE '%BOCTEST.S653C36C.LIVEBOC_B.YP040P%' THEN 'LIVEBOC_B' END
FROM sys.objects o
WHERE o.[type] IN ('P', 'PC')
AND name like '%_Extract'
You can do what you want with a query like this one:
select name = s.name + '.' + p.name ,
dt_created = p.create_date ,
dt_modified = p.modify_date ,
livboc_usage = case
when m.definition like '%declare%cursor%boctext.[^.].LIVEBOC_A.%' then 'A'
when m.definition like '%declare%cursor%boctext.[^.].LIVEBOC_B.%' then 'B'
else null
end
from sys.schemas s
join sys.procedures p on p.schema_id = s.schema_id
join sys.sql_modules m on m.object_id = p.object_id
But since what you're looking for are cross-server dependencies of a table, you should be able to get that simply by querying the system view sys.sql_expression_dependencies, which
Contains one row for each by-name dependency on a user-defined entity in the current
database. A dependency between two entities is created when one entity, called the
referenced entity, appears by name in a persisted SQL expression of another entity,
called the referencing entity. For example, when a table is referenced in the definition
of a view, the view, as the referencing entity, depends on the table, the referenced
entity. If the table is dropped, the view is unusable.
You can use this catalog view to report dependency information for the following
entities:
Schema-bound entities.
Non-schema-bound entities.
Cross-database and cross-server entities.
Entity names are reported; however, entity IDs are not resolved.
Column-level dependencies on schema-bound entities.
Column-level dependencies for non-schema-bound objects can be returned
by using sys.dm_sql_referenced_entities.
Server-level DDL triggers when in the context of the master database.
To that end, running a query like this in the database the referencing stored procedures live should do you:
select name = o.name ,
type = o.type_desc ,
liveboc_usage = case d.referenced_schema_name
when 'liveboc_a' then 'A'
when 'liveboc_b' then 'B'
else null
end ,
has_dependency_on = d.referenced_server_name
+ '.' + d.referenced_database_name
+ '.' + d.referenced_schema_name
+ '.' + d.referenced_entity_name
from sys.sql_expression_dependencies d
join sys.objects o on o.object_id = d.referenced_id
join sys.schemas s on s.schema_id = o.schema_id
where d.referenced_server_name = 'BOCTEST'
and d.referenced_database_name = 'S653C36C'
and d.referenced_schema_name like 'LIVEBOC_[AB]'
and d.referenced_entity_name = 'YP040P'

Deleting Extended Properties of a column

I have a database where I put comments in the Description property of many columns in my tables to describe the columns. The Description property apparently is implemented as an Extended Property named MS_Description.
Now I need to copy the database to SQL Azure, that does not permit Extended Properties. What is the Transact SQL commands available to search every column for the Extended Property MS_Description and delete it.
Here you have a detailed explanation on how to list extended properties on SQL Server 2008R2.
Then at the end of that page you have several references, one of them is to the sp_dropextendedproperty. Make use of it at will.
One blog with useful information and detailed samples.
Here you have a code sample to show all extended properties for columns in a table:
USE AdventureWorks2008R2;
GO
SELECT major_id, minor_id, t.name AS [Table Name],
c.name AS [Column Name],
value AS [Extended Property]
FROM sys.extended_properties AS ep
INNER JOIN sys.tables AS t ON ep.major_id = t.object_id
INNER JOIN sys.columns AS c ON ep.major_id = c.object_id
AND ep.minor_id = c.column_id
WHERE class = 1;
GO
Even more samples here
These sentences were useful to me:
-- find the property of a specific column
SELECT * FROM SYS.EXTENDED_PROPERTIES
WHERE [major_id] = OBJECT_ID('My_Table')
AND [name] = N'MS_Description'
AND [minor_id] = (SELECT [column_id], * FROM SYS.COLUMNS
WHERE [name] = 'My_Column' AND [object_id] = OBJECT_ID('My_Table') )
-- find a random property in all columns in a table (useful when a column was deleted but the property was left behind)
SELECT * FROM SYS.EXTENDED_PROPERTIES
WHERE [major_id] = OBJECT_ID('My_Table')
AND [name] = N'MS_Description'
AND CAST([value] AS VARCHAR(MAX)) LIKE '%"Nombre": "My_Column"%'
-- drop extended properties from an existing column
IF EXISTS (
SELECT 1 FROM SYS.EXTENDED_PROPERTIES
WHERE [major_id] = OBJECT_ID('My_Table')
AND [name] = N'MS_Description'
AND [minor_id] = (SELECT [column_id], * FROM SYS.COLUMNS
WHERE [name] = 'My_Column' AND [object_id] = OBJECT_ID('My_Table') )
)
BEGIN
EXECUTE sp_dropextendedproperty #name = N'MS_Description',
#level0type = N'SCHEMA',
#level0name = N'dbo',
#level1type = N'TABLE',
#level1name = N'My_Table',
#level2type = N'COLUMN',
#level2name = N'My_Column';
END

How to find the name of stored procedure, based on table name search, using SQL Server 2008?

I want to find all of the stored procedures where a particular table is being used. There are lots of stored procedures in the database, so it's not feasible to check each procedure.
Is there any way to use a search query so that I can find the stored procedures?
I have tried this code:
SELECT distinct so.name
FROM syscomments sc
INNER JOIN sysobjects so ON sc.id=so.id
WHERE sc.TEXT LIKE '% RejectionReason %'
Where RejectionReason is my table name, but it shows all procedures where RejectionReason is used as column name, so that doesn't work.
SELECT o.name, o.type_desc, p.name, p.type_desc
FROM sys.sql_dependencies d
INNER JOIN sys.objects o
ON d.object_id = o.object_id
INNER JOIN sys.objects p
ON d.referenced_major_id = p.object_id
AND o.name = 'RejectionReason'
or
SELECT o.name, t.TABLE_NAME, c.text
FROM syscomments c
JOIN sysobjects o
ON c.id = o.id
JOIN INFORMATION_SCHEMA.Tables t
ON c.text LIKE '%RejectionReason%'
or
EXEC sp_depends #objname = N'RejectionReason';
if none of those help you check this blog:
http://blog.sqlauthority.com/2010/02/04/sql-server-get-the-list-of-object-dependencies-sp_depends-and-information_schema-routines-and-sys-dm_sql_referencing_entities/
Try to use RedGate's free tool SQL Search.
Here is a piece of code hope it will work. Just changes the table name it depends upon your code
SELECT DISTINCT so.name
FROM syscomments sc INNER JOIN sysobjects so on sc.id=so.id
WHERE sc.text LIKE '%tablename%'
e.g.:
SELECT DISTINCT so.name
FROM syscomments sc INNER JOIN sysobjects so on sc.id=so.id
WHERE sc.text LIKE '%users%'
You will get the list of store procedures and the table relations.
As per MSDN sp_depends will be removed in future releases in case you are using that, you can use the following query instead:
SELECT referencing_schema_name, referencing_entity_name, referencing_id, referencing_class_desc, is_caller_dependent
FROM sys.dm_sql_referencing_entities ('dbo.TableName', 'OBJECT');
There are two possibilities I am aware of.
Firstly SQL Management Studio has an option to show Dependencies. Right-click on the Table and select View Dependencies However, this will not highlight usps where the tablename is embedded in dynamic SQL.
The second option is to right click on the database and select Generate Scripts. Follow the wizard and script all the usps to a new query window, then search that for the name of your table. This is more laborious, but will find all uses.
I guess this script shows all the dependent object of the table, including SPs.
USE MYDatabase
GO
DECLARE #TableName varchar(100)
SET #TableName = 'mytable'
SELECT
SourceSchema = OBJECT_SCHEMA_NAME(sed.referencing_id)
,SourceObject = OBJECT_NAME(sed.referencing_id)
,ReferencedDB = ISNULL(sre.referenced_database_name, DB_NAME())
,ReferencedSchema = ISNULL(sre.referenced_schema_name,
OBJECT_SCHEMA_NAME(sed.referencing_id))
,ReferencedObject = sre.referenced_entity_name
,ReferencedColumnID = sre.referenced_minor_id
,ReferencedColumn = sre.referenced_minor_name
FROM sys.sql_expression_dependencies sed
CROSS APPLY sys.dm_sql_referenced_entities(OBJECT_SCHEMA_NAME(sed.referencing_id)
+ '.' + OBJECT_NAME(sed.referencing_id), 'OBJECT') sre
WHERE sed.referenced_entity_name = #TableName
AND sre.referenced_entity_name = #TableName
for more details you can check out.
http://sqlserverplanet.com/sql-server-2008/find-dependent-objects/
This will return SP's and Views.
SELECT DISTINCT o.name AS Object_Name,o.type_desc
FROM sys.sql_modules m
INNER JOIN sys.objects o
ON m.object_id=o.object_id
WHERE m.definition Like '%TableName%'
SysObjects stores basic information about all objects inside your database. It's useful for you to know because it tells us the name of each object and the type of the object.
SysComments stores the actual text (code) for your stored procedures and functions. It contains an ID field that maps back to the id field in SysObjects.
select so.name, text
from sysobjects so, syscomments sc
where so.id = sc.id
and text like '%RejectionReason%'
I am using the following SQL script to search for column names and text inside all stored procedures of your database. You can use it as well to find tables in stored procedures.
Specify the search term in variable #SearchFor(as you would use it in a LIKE expression, e.g. '%LastName%' to find columns and stored procedures containing LastName).
It will find column names in tables as well as text inside stored procedures. The script can even display the SP source code, if you set #SPNameOnlyto 0.
--
-- Purpose: Search field names in all tables, views stored procedures
--
DECLARE #SearchFor nvarchar(max)='%Search_SP_Or_Table_Or_View%' -- search for this string
DECLARE #SearchSP bit = 1 -- 1=search in SPs as well
DECLARE #DisplaySPSource bit = 1 -- 1=display SP source code
-- tables
if (#SearchSP=1) begin
(
select '['+c.table_Schema+'].['+c.table_Name+'].['+c.column_name+']' [schema_object],
t.table_type
from information_schema.columns c
left join information_schema.Tables t on c.table_name=t.table_name
where column_name like #SearchFor or t.table_name like #SearchFor
UNION
select '['+routine_Schema+'].['+routine_Name+']' [schema_object],
'PROCEDURE' as table_type from information_schema.routines
where routine_definition like #SearchFor or routine_name like #SearchFor
and routine_type='procedure'
)
order by table_type, schema_object
end else begin
select '['+c.table_Schema+'].['+c.table_Name+'].['+c.column_name+']' [schema_object],
t.table_type
from information_schema.columns c
left join information_schema.Tables t on c.table_name=t.table_name
where column_name like #SearchFor or t.table_name like #SearchFor
order by c.table_Name, c.column_name
end
-- stored procedure (source listing)
if (#SearchSP=1) begin
if (#DisplaySPSource=1) begin
select '['+routine_Schema+'].['+routine_Name+']' [schema.sp], routine_definition
from information_schema.routines
where routine_definition like #SearchFor or routine_name like #SearchFor
and routine_type='procedure'
order by routine_name
end
end

How to identify whether the table has identity column

I want to find out whether the table has an identity column or not. Table is unknown to me. I have not done the structure of the table. Using Query?
I am using Sql Server Compact Edition.
IF (OBJECTPROPERTY(OBJECT_ID('TABLE_NAME'), 'TableHasIdentity') = 1)
ObjectProperty is available starting sql server 2008 Reference:
OBJECTPROPERTY
This query returns a table's identity column name:
CREATE PROCEDURE dbo.usp_GetIdentity
#schemaname nvarchar(128) = 'dbo'
,#tablename nvarchar(128)
AS
BEGIN
SELECT OBJECT_NAME(OBJECT_ID) AS TABLENAME,
NAME AS COLUMNNAME,
SEED_VALUE,
INCREMENT_VALUE,
LAST_VALUE,
IS_NOT_FOR_REPLICATION
FROM SYS.IDENTITY_COLUMNS
WHERE OBJECT_NAME(OBJECT_ID) = #tablename
AND OBJECT_SCHEMA_NAME(object_id) = #schemaname
END
Then form the code side.
Call this stored procedure using the datareader role, then check datareader.hasrows(). If the condition value is true (1), then the table has identity column if set. If not then it doesn't have an identity column.
I know it's long time ago but i found this helpful
try this :
IF EXISTS (SELECT * from syscolumns where id = Object_ID(#TABLE_NAME) and colstat & 1 = 1)
BEGIN
-- Do your things
END
Any of the below queries can be used to check if an Identity Column is present in the table
1)
SELECT *
FROM sys.identity_columns
WHERE OBJECT_NAME(object_id) = 'TableName'
2)
SELECT *
FROM sys.identity_columns
WHERE object_id = (
SELECT id
FROM sysobjects
WHERE name = 'TableName'
)
I would just like to add this option as well as I think it is the simplest
SELECT COLUMNPROPERTY(OBJECT_ID('TableName'),'ColumnName','isidentity')
One way to do this would be to make use of the stored procedure sp_help. I.e:
sp_help MyTable
This will return a DataSet that has all the information you would need on the table. There is a specific Table that has information on identities.
I.e:
If it does not contain an identity field, the Identity column will say: "No identity column defined".
#Pranay: he said Compact Edition. Stored procedures aren't supported, and there is no sys.anything.
This is the call:
SELECT Count(*) FROM INFORMATION_SCHEMA.COLUMNS WHERE AUTOINC_INCREMENT IS NOT NULL AND TABLE_NAME='this_table'
It will return either 1 (true) or 0 (false).
...
declare #tblhasIdentCol bit = IF (IDENT_CURRENT( #dbName +'.'+ #schemaName +'.'+ #tableName ) IS NOT NULL , 1 , 0 )
You get numeric value if table has identity
Very simple answer would be to run this:
SELECT IDENT_CURRENT('TABLE-NAME')
This would give max value of identity column if exists, if the column doesn't exist, it gives 1 as result.
Based on max value, you can identify which column is having that and determine the identity column.
This the query that get u all the tableNames, columnnames of the table, and is_identity or not in the selected database
SELECT
sys.columns.name
, sys.tables.name
, is_identity
FROM sys.columns
INNER JOIN sys.tables ON sys.tables.object_id = sys.columns.object_id
AND sys.columns.is_identity = 1
CREATE FUNCTION dbo.fnTableHasIdentity(#Tbl sysname)
RETURNS TINYINT
BEGIN
RETURN OBJECTPROPERTY(OBJECT_ID(#Tbl), 'TableHasIdentity')
END
--As simple as that!
select t.name as TableName,c.name as ColumnName
from sys.identity_columns c
inner join sys.tables t on c.object_id = t.object_id
where t.name = 'TableName'
If you like me, needed to be able to do this for tables in an arbitrary database, then I found the following solution:
IF EXISTS (
SELECT 1
FROM [database name].sys.identity_columns AS id_col
INNER JOIN [database name].sys.objects
ON objects.object_id = id_col.object_id
INNER JOIN [database name].sys.schemas
ON schemas.schema_id = objects.schema_id
AND schemas.name = 'schema name'
WHERE OBJECT_NAME(id_col.object_id, DB_ID('database name')) = 'table name'
) SELECT 1 ELSE SELECT 0
you can get the 1 or 0 Boolean Form if the current table has identity Columns by using this
SELECT Count(Column_ID) FROM sys.identity_columns WHERE OBJECT_NAME(object_id) = 'tableName'
One way to list all Tables with their identity column if it exists
to get you desired table add at the end of the filter "and o.name='TableName'"
where Tbale Nam is the table you are looking for
SELECT o.[Name][TableName],i.[name][IdentityColName] FROM
sys.objects o
left outer join sys.identity_columns i on i.object_id=o.object_id
where o.type='U'

How to Find the list of Stored Procedures which affect a particular column?

Im working on this large DB which has a lot of the business knowledge embedded in the SPs[I know!] and there is a lot of chaining between the SPs. i.e one stored proc calling another.
Im want to find out a list of stored procedures which update a particular column. How would I do that.
Using showplan_All as outlined in
SQL Table and column Parser for stored procedures doesnt work for me, because this is a shared dev db.
using a Sp from master db scanning system text as described is not feasible because I dont have access to the master db.
So how can I find this informaion?
From system view sys.sql_dependencies you can get dependencies at column level.
DECLARE #Schema SYSNAME
DECLARE #Table SYSNAME
DECLARE #Column SYSNAME
SET #Schema = 'dbo'
SET #Table = 'TableName'
SET #Column = 'ColumnName'
SELECT o.name
FROM sys.sql_dependencies AS d
INNER JOIN sys.all_objects AS o ON o.object_id = d.object_id
INNER JOIN sys.all_objects AS ro ON ro.object_id = d.referenced_major_id
INNER JOIN sys.all_columns AS c ON c.object_id = ro.object_id AND c.column_id = d.referenced_minor_id
WHERE (SCHEMA_NAME(ro.schema_id)=#Schema)
and o.type_desc = 'SQL_STORED_PROCEDURE'
and ro.name = #Table
and c.name = #Column
GROUP BY o.name
Have you tried this : EXEC sp_depends #objname = [table name of the column you are interested in].
So for example, if you had a column named Price in a table named Product, you would execute this: EXEC sp_depends #objname = N'Product'.
Simply executing this would give you list of all sps, views, etc which depend on that particular table.
I use this all the time as I work with a db which has over 400 tables :-)
sp_depends page on MSDN
Try something like this:
use YourDatabase;
select [Name]
from sys.procedures
where object_definition([object_id]) like '%YourColumnName%';
Obviously this has the potential to generate a lot of false positives depending on what the column is named but at least you will have a list of procedures to sift through.
Here's one that works in SQL 2000+; Note that as Andrew noted in his, you will get false positives depending on your column name, but it's a starting place:
SELECT DISTINCT o.Name
FROM syscomments c
JOIN sysobjects o ON c.ID = o.ID
WHERE c.Text LIKE '%ColumnName%'
ORDER BY o.Name
use msdb
go
select * from sysjobs j
inner join sysjobsteps s
on j.job_id=s.job_id
where command like '%HBR_INSTRUMENT%'