12

我们在工作中遇到了大量遗留存储过程的问题。你们是否推荐任何可以帮助更好地理解这些程序的工具?某种识别过程间依赖关系和/或过程与表依赖关系的逆向工程。可以是免费或商业工具。

谢谢!

4

8 回答 8

6

比“依赖跟踪器”更便宜的解决方案是数据字典表 sys.sql_dependencies,可以从数据字典中查询此数据。Oracle 有一个具有类似功能的数据字典视图,称为 DBA_DEPENDENCIES(加上等效的 USER_ 和 ALL_ 视图)。使用其他数据字典表 (sys.tables/DBA_TABLES) 等,您可以生成对象依赖关系报告。

如果您感觉特别热衷,可以使用递归查询(Oracle CONNECT BY 或 SQL Server 公用表表达式)来构建完整的对象依赖关系图。

这是 sys.sql_dependencies 上的递归 CTE 示例。它将为每个依赖项及其深度返回一个条目。对于每个依赖关系,项目可以出现不止一次,可能在不同的深度。我没有可用的 Oracle 实例来在 DBA_DEPENDENCIES 上构建 CONNECT BY 查询,因此欢迎任何具有编辑权限以及时间和专业知识的人注释或编辑此答案。

另请注意sys.sql_dependencies,您可以从中获取列引用referenced_minor_id。这可以用于(例如)确定哪些列在暂存区域的 ETL 存储过程中实际使用,其中来自源的 DB 表的副本具有比实际使用的列更多的列。

with dep_cte as (
select o2.object_id  as parent_id
      ,o2.name       as parent_name
      ,o1.object_id  as child_id
      ,o1.name       as child_name
      ,d.referenced_minor_id
      ,1 as hierarchy_level
  from sys.sql_dependencies d
  join sys.objects o1
    on o1.object_id = d.referenced_major_id
  join sys.objects o2
    on o2.object_id = d.object_id
 where d.referenced_minor_id in (0,1)
   and not exists
       (select 1
          from sys.sql_dependencies d2
         where d2.referenced_major_id = d.object_id)

union all

select o2.object_id  as parent_id
      ,o2.name       as parent_name
      ,o1.object_id  as child_id
      ,o1.name       as child_name
      ,d.referenced_minor_id
      ,d2.hierarchy_level + 1 as hierarchy_level
  from sys.sql_dependencies d
  join sys.objects o1
    on o1.object_id = d.referenced_major_id
  join sys.objects o2
    on o2.object_id = d.object_id
  join dep_cte d2
    on d.object_id = d2.child_id
 where d.referenced_minor_id in (0,1)
)

select *
  from dep_cte
 order by hierarchy_level

我现在要向社区开放。可以方便地访问正在运行的 Oracle 实例的人在这里发布 CONNECT BY 递归查询吗?请注意,这是特定于 SQL 服务器的,并且问题所有者已经明确表示他正在使用 Oracle。我没有正在运行的 Oracle 实例来开发和测试任何东西。

于 2008-09-18T16:07:16.870 回答
4

Redgate 有一个相当昂贵的产品,称为SQL Dependency Tracker,似乎可以满足要求。

于 2008-09-16T07:00:49.620 回答
3

我认为rpetrich 提到的 Red Gate Dependency Tracker是一个不错的解决方案,它运行良好,并且 Red Gate 有 30 天的试用期(理想情况下,足够长的时间让您进行取证)。

我还会考虑隔离系统并运行SQL Profiler,它将向您显示表上的所有 SQL 操作。这通常是构建序列图的一个很好的起点,或者您选择记录这些代码。祝你好运!

于 2008-09-16T07:07:51.070 回答
1

Redgate SQL 文档。生成的文档包括交叉引用的依赖信息。例如,对于每个表,它列出了引用该表的视图、存储过程、触发器等。

于 2008-09-17T02:47:49.593 回答
1

存储过程在哪个数据库中?甲骨文、SQL Server,还有别的吗?

根据评论进行编辑:鉴于您当时正在使用 Oracle,请查看TOAD。我在其中使用了一个称为代码路线图的功能,它允许您以图形方式显示数据库中的 PL/SQL 相互依赖关系。它可以在纯代码模式下运行,显示运行时调用堆栈依赖关系,或者在代码加数据模式下,它还向您显示代码所触及的数据库对象(表、视图、触发器)。

(注意 - 我是 TOAD 用户,推荐它并没有任何好处)

于 2008-09-17T18:46:07.870 回答
1

这不是真正的深入或彻底,但我认为如果您使用的是 MS SQL Server 或 Oracle(也许 Nigel 可以帮助提供 PL-SQL 示例)......Nigel 正在做一些事情。这只会深入 3 个依赖项,但可以修改为你需要的深度。这不是最漂亮的东西......但它的功能......

select 
    so.name + case when so.xtype='P' then ' (Stored Proc)' when so.xtype='U' then ' (Table)' when so.xtype='V' then ' (View)' else ' (Unknown)' end as EntityName, 
    so2.name + case when so2.xtype='P' then ' (Stored Proc)' when so2.xtype='U' then ' (Table)' when so2.xtype='V' then ' (View)' else ' (Unknown)' end as FirstDependancy,
    so3.name + case when so3.xtype='P' then ' (Stored Proc)' when so3.xtype='U' then ' (Table)' when so3.xtype='V' then ' (View)' else ' (Unknown)' end as SecondDependancy,
    so4.name + case when so4.xtype='P' then ' (Stored Proc)' when so4.xtype='U' then ' (Table)' when so4.xtype='V' then ' (View)' else ' (Unknown)' end as ThirdDependancy
from 
  sysdepends sd 
    inner join sysobjects as so on sd.id=so.id 
    left join sysobjects as so2 on sd.depid=so2.id
    left join sysdepends as sd2 on so2.id=sd2.id and so2.xtype not in ('S','PK','D')
    left join sysobjects as so3 on sd2.depid=so3.id and so3.xtype not in ('S','PK','D')
    left join sysdepends as sd3 on so3.id=sd3.id and so3.xtype not in ('S','PK','D')
    left join sysobjects as so4 on sd3.depid=so4.id and so4.xtype not in ('S','PK','D')
where so.xtype = 'P' and left(so.name,2)<>'dt'
group by so.name, so2.name, so3.name, so4.name, so.xtype, so2.xtype, so3.xtype, so4.xtype
于 2008-09-18T17:02:55.130 回答
1

如何找到数据库对象的依赖链(MS SQL Server 2000(?)+) by Jacob Sebastian

每次他需要部署新报表或修改现有报表时,他都需要知道依赖于给定报表存储过程的数据库对象是什么。有时报告非常复杂,每个存储过程可能有几十个依赖对象,每个依赖对象可能依赖于其他几十个对象。

他需要一种方法来递归地查找给定存储过程的所有依赖对象。我使用 CTE 编写了一个递归查询来实现这一点。

于 2011-10-27T22:33:48.063 回答
0

逆向工程的最佳工具是 APEX。太奇妙了。它甚至可以追踪到 .NET 程序集并告诉您在哪里使用了 proc。它是迄今为止同类产品中最深的产品。RedGate 有很好的其他工具,但在这种情况下没有。

于 2008-09-18T20:34:45.607 回答