sql >> Database teknologi >  >> RDS >> Oracle

Opbygning af en tabelafhængighedsgraf med en rekursiv forespørgsel

select parent, child, level from ( select parent_table.table_name parent, child_table.table_name child from user_tables parent_table, user_constraints parent_constraint, user_constraints child_constraint, user_tables child_table where parent_table.table_name = parent_constraint.table_name and parent_constraint.constraint_type IN( 'P', 'U' ) and child_constraint.r_constraint_name = parent_constraint.constraint_name and child_constraint.constraint_type = 'R' and child_table.table_name = child_constraint.table_name and child_table.table_name != parent_table.table_name ) start with parent = 'DEPT' connect by prior child = parent

bør fungere (erstat tabelnavnet, selvfølgelig) forudsat at alt er i det samme skema. Brug DBA_-versionerne af dataordbogstabellerne og -betingelser for kolonnerne OWNER og R_OWNER, hvis du skal håndtere afhængigheder på tværs af skemaer. Ved nærmere eftertanke tager dette heller ikke højde for selvrefererende begrænsninger (dvs. en begrænsning på EMP-tabellen, at MGR-kolonnen refererer til EMPNO-kolonnen), så du bliver nødt til at ændre koden for at håndtere den sag, hvis du har brug for at håndtere med selvrefererende begrænsninger.

Til testformål tilføjede jeg et par nye tabeller til SCOTT-skemaet, der også refererer til DEPT-tabellen (inklusive en barnebarnsafhængighed)

SQL> create table dept_child2 (
  2  deptno number references dept( deptno )
  3  );

Table created.

SQL> create table dept_child3 (
  2    dept_child3_no number primary key,
  3    deptno number references dept( deptno )
  4  );

Table created.

SQL> create table dept_grandchild (
  2    dept_child3_no number references dept_child3( dept_child3_no )
  3  );

Table created.
 

og bekræftet, at forespørgslen returnerede det forventede output

SQL> ed
Wrote file afiedt.buf

  1  select parent, child, level from (
  2  select parent_table.table_name parent, child_table.table_name child
  3   from user_tables      parent_table,
  4        user_constraints parent_constraint,
  5        user_constraints child_constraint,
  6        user_tables      child_table
  7  where parent_table.table_name = parent_constraint.table_name
  8    and parent_constraint.constraint_type IN( 'P', 'U' )
  9    and child_constraint.r_constraint_name = parent_constraint.constraint_name
 10    and child_constraint.constraint_type   = 'R'
 11    and child_table.table_name = child_constraint.table_name
 12    and child_table.table_name != parent_table.table_name
 13  )
 14  start with parent = 'DEPT'
 15* connect by prior child = parent
SQL> /

PARENT                         CHILD                               LEVEL
------------------------------ ------------------------------ ----------
DEPT                           DEPT_CHILD3                             1
DEPT_CHILD3                    DEPT_GRANDCHILD                         2
DEPT                           DEPT_CHILD2                             1
DEPT                           EMP                                     1
 


  1. Migrering af MySQL til PostgreSQL på AWS RDS, del 3

  2. TRUNC(dato) Funktion i Oracle

  3. Forebyg SQL-injektionsangreb i et Java-program

  4. Hvordan begrænser jeg antallet af rækker, der returneres af en Oracle-forespørgsel efter bestilling?