Oracle
 sql >> база данни >  >> RDS >> Oracle

Анализирайте имена на таблици от куп SQL изрази

Ако бях аз, щях да се опитам да подходя към проблема по различен начин. Вместо да напиша SQL анализатор (който би изисквал много повече от регулярен израз, освен ако не можете да гарантирате, че всички SQL изрази използват много малко подмножество от наличната SQL граматика), бих искал да генерирам план за заявка за всеки обект и след това заявка PLAN_TABLE за да видите обектите, които Oracle трябва да удари. Ще трябва да направите допълнително търсене за достъп до индекс, за да разберете върху коя таблица е дефиниран индексът, но това трябва да е сравнително лесно.

Ако тръгнете по този път обаче, ще извлечете базовите таблици, които вашата заявка действително докосва, а не каквито и изгледи да се отнасят заявките. Тоест, ако имате заявка SELECT * FROM view_1 и view_1 , от своя страна, се дефинира като заявка срещу table_a и table_b , само table_a и table_b ще бъде част от плана. И ще трябва да деактивирате query_rewrite за сесията, ако искате да попречите на плановете на заявките да препращат към материализирани изгледи, ако тези материализирани изгледи не са конкретно част от заявката.

Ако за всяка заявка направите

EXPLAIN PLAN FOR <<the query>>

тогава можете да

SELECT DISTINCT object_owner, object_name, object_type
  FROM plan_table

за да получите списъка с обекти. Ако OBJECT_TYPE е като INDEX% , след това можете да използвате DBA_INDEXES изглед (или ALL_INDEXES или USER_INDEXES в зависимост от това кой притежава въпросните обекти и какво ниво на привилегии имате), за да определите върху коя таблица е дефиниран този индекс

SELECT table_owner, table_name
  FROM dba_indexes
 WHERE owner = <<object_owner from plan_table>>
   AND index_name = <<object_name from plan_table>>

Така че, например, ако имам изглед view_1

 create or replace view view_1
 as
 select *
   from emp join dept using (deptno)

и заявка

select * from view_1;

Мога да направя

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

Това ми казва, че заявката всъщност удря EMP и DEPT маси. Освен това удря PK_DEPT индекс, за да мога да видя в коя таблица е дефинирано.

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

Както се оказва, този индекс е дефиниран в DEPT също така, така че знам, че само EMP и DEPT таблици в SCOTT схема ще бъдат включени в заявката.




  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Как да получите последния ден от месеца в Oracle

  2. не може да получи параметър от процедурата на oracle, изпълнявана от mybatis

  3. Добре ли е винаги да използвате клауза за присъединяване в Oracle?

  4. логика в клаузата HAVING за получаване на множество стойности на група по резултат

  5. org.hibernate.MappingException:Няма съпоставяне на диалект за тип JDBC:2002