Si c'était moi, j'aurais tendance à essayer d'aborder le problème d'une manière différente. Plutôt que d'écrire un analyseur SQL (ce qui nécessiterait bien plus qu'une expression régulière à moins que vous ne puissiez garantir que toutes les instructions SQL utilisent un tout petit sous-ensemble de la grammaire SQL disponible), j'aurais tendance à générer un plan de requête pour chaque objet, puis requête PLAN_TABLE
pour voir les objets qu'Oracle doit frapper. Vous auriez besoin de faire une recherche supplémentaire pour les accès à l'index pour savoir sur quelle table l'index est défini, mais cela devrait être raisonnablement simple.
Si vous suivez cette voie, cependant, vous récupérerez les tables de base auxquelles votre requête touche réellement plutôt que les vues auxquelles les requêtes peuvent réellement faire référence. Autrement dit, si vous avez une requête SELECT * FROM view_1
et view_1
, à son tour, est défini comme une requête sur table_a
et table_b
, uniquement table_a
et table_b
fera partie du plan. Et vous auriez besoin de désactiver query_rewrite
pour la session si vous vouliez empêcher les plans de requête de référencer des vues matérialisées si ces vues matérialisées ne faisaient pas spécifiquement partie de la requête.
Si, pour chaque requête, vous effectuez une
EXPLAIN PLAN FOR <<the query>>
vous pouvez alors
SELECT DISTINCT object_owner, object_name, object_type
FROM plan_table
pour obtenir la liste des objets. Si OBJECT_TYPE
est comme INDEX%
, vous pouvez alors utiliser le DBA_INDEXES
afficher (ou ALL_INDEXES
ou USER_INDEXES
en fonction du propriétaire des objets en question et de votre niveau de privilèges) pour déterminer sur quelle table cet index est défini
SELECT table_owner, table_name
FROM dba_indexes
WHERE owner = <<object_owner from plan_table>>
AND index_name = <<object_name from plan_table>>
Ainsi, par exemple, si j'ai une vue view_1
create or replace view view_1
as
select *
from emp join dept using (deptno)
et une requête
select * from view_1;
je peux faire
SQL> explain plan for select * from view_1;
Explained.
SQL> ed
Wrote file afiedt.buf
1 SELECT distinct object_owner, object_name, object_type
2* FROM plan_table
SQL> /
OBJECT_OWNER OBJECT_NAME OBJECT_TYPE
------------------------------ ------------------------- -------------------------
SCOTT DEPT TABLE
SCOTT PK_DEPT INDEX (UNIQUE)
SCOTT EMP TABLE
Cela me dit que la requête touche en fait le EMP
et DEPT
les tables. Il frappe également le PK_DEPT
index afin que je puisse regarder pour voir sur quelle table cela est défini.
SQL> ed
Wrote file afiedt.buf
1 SELECT table_owner, table_name
2 FROM dba_indexes
3 WHERE owner = 'SCOTT'
4* AND index_name = 'PK_DEPT'
SQL> /
TABLE_OWNER TABLE_NAME
------------------------------ ------------------------------
SCOTT DEPT
Il s'avère que cet index est défini sur le DEPT
table également, donc je sais que seul le EMP
et DEPT
tableaux dans le SCOTT
schéma va être impliqué dans la requête.