e-learning、オラクル研修、LMS(学習管理システム)のiStudy

e-learning、オラクル研修、LMS(学習管理システム)のiStudy

第84回 「オブジェクトの依存性の表示」

2014.01.30

こんにちは。インストラクターの蓑島です。

前回はオブジェクトの依存性について解説しました。今回はその依存性を簡単に表示する機能をご紹介します。すなわち、あるオブジェクトの定義を変更する場合、どのオブジェクトに影響があるかを簡単に特定する方法です。
例えば、EMP表の定義を変更する前に、どこまでのPL/SQLプログラムに影響がありえるかを事前に調べておく、といった使い方をします。

まず、その機能を使うにはその機能を使いたいデータベースユーザでスクリプトを実行して必要なオブジェクトを作成する必要があります。そのスクリプトはデータベースサーバの所定の場所に用意されています。以下のように実行します。

下記の例はLinuxサーバーですが、Windowsサーバでも基本は同じです。

まずデータベースサーバーに直接ログインします。
そして、この機能を使いたいユーザでSQL*Plusでデータベースに接続します。ここではscottユーザとしましょう。

$ sqlplus scott/tiger

そして、以下のようにスクリプトを実行します。

1
SQL> @?/rdbms/admin/utldtree.sql

このスクリプトを初めて実行すると途中のDROP処理でエラーとなる箇所がありますが無視してください。

なおこのスクリプトの「?」はORACLE_HOMEと呼ばれているディレクトリを表す記号です。このディレクトリ以下のrdbms/adminの下に、utldtree.sqlというスクリプトが必ずあります。ここで事前にこのスクリプトの一番最後の部分を確認しておいてください。
一番最後の部分に、「order by seq#」という記述があると思いますが、もし無ければ追加してください。少し古いときのオラクルのリリースでは「group by ~」という記述があれば、その順番に行を返すことになっていましたが、最近のリリースでは内部ロジックが変更され、group by を指定してもその順番に行を返す保障はありません。
順番が大事なので、もし最後にorder byが無ければ追加しておいてください。

1
2
3
4
5
6
7
8
9
10
スクリプトの一番最後の部分
・・・・
create view ideptree (dependencies)
as
   select lpad( ' ' ,3*( max (nested_level))) || max (nvl(type, '<no permission="">' )
     || ' ' || schema || decode(type, NULL , '' , '.' ) || name )
   from deptree
   group by seq#
   order by seq#    ← この記述が無ければ追加しておく
</ no >

ではこのスクリプトを実行することで依存性を表示するために必要なオブジェクトができましたので、早速、SCOTTスキーマのEMP表の定義が変更されたら、どこまでのオブジェクトに影響するかを表示してみましょう。つまり、SCOTT.EMPに依存するオブジェクトの表示です。以下のように行います。

まず、プロシージャを実行します。

1
2
3
SQL> EXEC DEPTREE_FILL( 'TABLE' , 'SCOTT' , 'EMP' )
 
PL/SQLプロシージャが正常に完了しました。

これによりSCOTT.EMPに依存するオブジェクトのデータが、deptree_temptabという表に収集されるのですが、そのデータをわかりやすく階層的に表示してくれるビューが IDEPTREEビューです。
このビューは以下のようになんの条件もつけず、SELECT * FROM IDEPTREE; と単純に問い合わせてください。以下は私が普段使っているサーバーでの結果です。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
SQL> SELECT * FROM IDEPTREE;
 
DEPENDENCIES
---------------------------------------------------
TABLE SCOTT.EMP
    TRIGGER SCOTT.TRIG_EMP_TEST
    VIEW SCOTT.V_GSAL
    VIEW SCOTT.V_TEST2
    VIEW SCOTT.V_OYA_KO
    PACKAGE BODY SCOTT.PAC1
    PACKAGE BODY SCOTT.PAC2
    PROCEDURE SCOTT.PROC79
    PROCEDURE SCOTT.PROC80
    VIEW SCOTT.V_EMP
       FUNCTION SCOTT.FUNC1
          PROCEDURE SCOTT.PROC1
 
12行が選択されました。

この結果で、5行目の「TABLE SCOTT.EMP」が起点となるオブジェクトであるSCOTT.EMP表ですね。その下6行目から14行目までが同じ階層のオブジェクトですが、これらはSCOTT.EMP表に対して直接的に依存するオブジェクトです。トリガーがあったり、パッケージがあったり、プロシージャなどありますね。また、15行目(FUNCTION SCOTT.FUNC1)と16行目(PROCEDURE SCOTT.PROC1)の階層が深くなっていますが、それらはすぐ上の階層のオブジェクトに依存することを表しています。それらの深い階層のオブジェクトのソースコードには、SCOTT.EMPを参照する記述はありませんが、SCOTT.EMPに間接的に依存しているわけです。つまりPROC1プロシージャはFUNC1ファンクションに依存し、FUNC1ファンクションはV_EMPビューに依存し、V_EMPビューはEMP表に依存する(前回の内容)ことがとてもわかりやすく確認できます。

まとめると以下のとおりです。

1.スクリプトを実行する(初回のみ)
SQL> @?/rdbms/admin/utldtree.sql

2.起点となるオブジェクトを指定してプロシージャを実行する
SQL> EXEC DEPTREE_FILL('オブジェクトのタイプ','スキーマ名','オブジェクト名')

3.IDEPTREEビューを問い合わす
SQL> SELECT * FROM IDEPTREE;

いかがですか? あるオブジェクトに依存するオブジェクトはどれか? ということをとても簡単に正確に知ることができますね。PL/SQLプログラムや表、ビューなどの定義を修正する前に事前に影響する可能性のあるオブジェクトを簡単に特定できるわけです。

それでは今回はここまでとします。また、次回ご期待ください。

先頭へ戻る