Quite frankly I don't think you're going to get very far with your parsing idea. You're making very brave assumptions about how code is going to be formatted in every single procedure. I'm very meticulous about formatting but there's no way I could guarantee the kind of consistency you're depending on across that many procedures, even if I did write them all myself.
With the caveat that deferred name resolution can bite you in the rear and that dependency tracking was certainly far from perfect in SQL Server 2005 (see the workarounds I posted for keeping it accurate even in SQL Server 2008), here are a couple of ideas (and they're not perfect either, but they'll definitely cause less gray hair):
You can get parameters in a much easier way than brute force parsing, by using the catalog view
sys.parameters
:SELECT OBJECT_NAME([object_id]), p.name, t.name FROM sys.parameters AS p INNER JOIN sys.types AS t ON p.system_type_id = t.system_type_id WHERE p.is_output = 1;
If all of your procedures have been recompiled and you are not subject to deferred name resolution issues, you can get table names and column names from
sys.sql_dependencies
- however this will include columns that are referenced in where/join clauses even if they are not in the select list:SELECT [procedure] = OBJECT_NAME(d.[object_id]), [table] = OBJECT_NAME(d.referenced_major_id), [column] = c.name FROM sys.sql_dependencies AS d INNER JOIN sys.columns AS c ON c.[object_id] = d.referenced_major_id AND c.column_id = d.referenced_minor_id;
There is a column here called is_selected
but I have not found it to be accurate/reliable.
Note that anything that happens in dynamic SQL stays in dynamic SQL - so if your procedures use dynamic SQL it will be next to impossible to cull out table/column names.