Listing Objects Used in Stored Procedures (MS SQL)

Recently, I had to clean up a large data base. Some of the tables in that database were obsolete and needed to get deleted. Obsolete tables were not used in any stored procedures, so I needed to list all the tables used in stored procedures and subtract them from the set of all tables in the dataset to get the ones I could delete. So the starting point is to get a list of all objects used in a USP:

WITH cte 
AS 
(
	SELECT 
		source.name AS source, 
		target.name AS target,
		CASE target.xtype 
			WHEN 'U'  THEN 'Table'
			WHEN 'P'  THEN 'Store Procedure'
			WHEN 'FN' THEN 'Function'
			WHEN 'V'  THEN 'View'
		END AS type
	FROM sysdepends d 
	INNER JOIN sysobjects source ON source.id = d.id
	INNER JOIN sysobjects target ON target.id = d.depid
	WHERE source.xtype = 'P' 
)
SELECT DISTINCT target, source, type
FROM cte
ORDER BY target, type DESC, source

Now the script above returns all objects that ARE in use. But I need to know the objects that ARE NOT in use. Here’s how I do that (note: other than in the script above, below I am only interessted in table objects, not views or other USPs):

-- declare a tables-typed variable to store the result set

DECLARE @tables_in_use TABLE
(
	name VARCHAR(MAX) NOT NULL
)

-- add all user tables in the database

INSERT @tables_in_use
SELECT name 
FROM sysobjects 
WHERE xtype = 'U'

-- delete all tables that are in use

;WITH cte 
AS 
(
	SELECT 
		source.name AS source, 
		target.name AS target
	FROM sysdepends d 
	INNER JOIN sysobjects source ON source.id = d.id
	INNER JOIN sysobjects target ON target.id = d.depid
	WHERE source.xtype = 'P' 
)
DELETE t
FROM cte
INNER JOIN  @tables_in_use t ON t.name = cte.target

-- the tables not in use remain in the result set

SELECT * 
FROM @tables_in_use
ORDER BY name

Freelance full-stack .NET and JS developer and architect. Located near Cologne, Germany.

Leave a Reply

Your email address will not be published. Required fields are marked *