Как увидеть фактический оператор SQL SQL, который выполняется

Я использую собственное встроенное приложение, которое генерирует стандартный набор отчетов на еженедельной основе. У меня нет доступа к исходному коду приложения, и все говорят, что для схемы базы данных Oracle нет документации. (Aargh!)

Мне было предложено определить спецификации для варианта существующего отчета (например, применить дополнительные фильтры для ограничения набора данных и немного изменить макет). В принципе это звучит достаточно просто, но сложно без какой-либо существующей документации.

Я понимаю, что журналы не могут помочь мне, потому что отчет запрашивает только базу данных; он фактически не вставляет, не удаляет или не обновляет значения базы данных, поэтому ничего не записывать (это правильно?).

Итак, мой вопрос заключается в следующем: есть ли инструмент или утилита (Oracle или иначе), которые я могу использовать, чтобы увидеть фактический оператор SQL, который выполняется во время выполнения задания генерации отчета? Я полагаю, что если я увижу, какие таблицы фактически доступны для создания существующего отчета, у меня будет очень хорошая отправная точка для изучения схемы и определения правильного SQL для моего собственного отчета.

Ответ 1

На стороне словаря данных есть много инструментов, которые вы можете использовать, например Schema Spy

Чтобы посмотреть, какие запросы запущены, просмотрите представления sys.v_ $sql и sys.v_ $sqltext. Вам также потребуется доступ к sys.all_users

Следует отметить, что запросы, которые используют параметры, будут отображаться один раз с такими типами, как

and TABLETYPE=’:b16’

в то время как другие, которые не будут отображаться несколько раз, например:

and TABLETYPE=’MT’

Примером этих таблиц в действии является следующий SQL, чтобы найти 20 лучших свиней. Вы можете изменить это, удалив WHERE rownum <= 20 и, возможно, добавив ORDER BY module. Вы часто обнаруживаете, что модуль даст вам представление о том, какое программное обеспечение выполняет запрос (например: "TOAD 9.0.1.8", "Тонкий клиент JDBC", "runcbl @somebox (TNS V1-V3)" и т.д.)

SELECT 
 module, 
 sql_text, 
 username, 
 disk_reads_per_exec, 
 buffer_gets, 
 disk_reads, 
 parse_calls, 
 sorts, 
 executions, 
 rows_processed, 
 hit_ratio, 
 first_load_time, 
 sharable_mem, 
 persistent_mem, 
 runtime_mem, 
 cpu_time, 
 elapsed_time, 
 address, 
 hash_value 
FROM 
  (SELECT
   module, 
   sql_text , 
   u.username , 
   round((s.disk_reads/decode(s.executions,0,1, s.executions)),2)  disk_reads_per_exec, 
   s.disk_reads , 
   s.buffer_gets , 
   s.parse_calls , 
   s.sorts , 
   s.executions , 
   s.rows_processed , 
   100 - round(100 *  s.disk_reads/greatest(s.buffer_gets,1),2) hit_ratio, 
   s.first_load_time , 
   sharable_mem , 
   persistent_mem , 
   runtime_mem, 
   cpu_time, 
   elapsed_time, 
   address, 
   hash_value 
  FROM
   sys.v_$sql s, 
   sys.all_users u 
  WHERE
   s.parsing_user_id=u.user_id 
   and UPPER(u.username) not in ('SYS','SYSTEM') 
  ORDER BY
   4 desc) 
WHERE
 rownum <= 20;

Обратите внимание, что если запрос длинный, вам нужно будет запросить v_ $sqltext. В этом сохранен весь запрос. Вам нужно будет найти ADDRESS и HASH_VALUE и забрать все части. Например:

SELECT
 *
FROM
 sys.v_$sqltext
WHERE
 address = 'C0000000372B3C28'
 and hash_value = '1272580459'
ORDER BY 
 address, hash_value, command_type, piece
;

Ответ 2

Извините за короткий ответ, но уже поздно. Google "oracle event 10046 sql trace". Лучше всего проследить отдельный сеанс, потому что вычисление того, какой SQL принадлежит тому, какой сеанс из v $sql нелегко, если он является общим SQL и используется несколькими пользователями.

Если вы хотите произвести впечатление на своих друзей Oracle DBA, узнайте, как установить трассировку oracle с событием 10046, интерпретируйте смысл событий ожидания и найдите пользователей верхнего уровня.

У Quest был бесплатный продукт, который позволил вам захватить SQL, когда он вышел с клиентской стороны, но не уверен, что он работает с вашим продуктом/версией Oracle. Google "квест oracle sql monitor" для этого.

Спокойной ночи.

Ответ 3

Я думаю, что таблица V $SQLAREA содержит то, что вы ищете (см. столбцы SQL_TEXT и SQL_FULLTEXT).

Ответ 4

Да, это определенно возможно. Представления v $sql содержат эту информацию. Что-то вроде этот фрагмент кода должен указывать на вас в правильном направлении. Я сам не пробовал эту часть кода - нигде рядом с Oracle DB прямо сейчас.

[Edit] Прокляните еще два ответа. В следующий раз нужно набирать скорость; -)

Ответ 5

- я использую что-то вроде этого, с концепциями и некоторым кодом, украденным из аштома.
- предложения по улучшению приветствуются

С
sess AS
(
  SELECT *
  ОТ V $SESSION
  WHERE USERNAME = USER
  ORDER BY SID
)
SELECT si.SID,
     si.LOCKWAIT,
     si.OSUSER,
     si.PROGRAM,
     si.LOGON_TIME,
     si.STATUS,
     (
         SELECT ROUND (USED_UBLK * 8/1024,1)
         FROM V $TRANSACTION,
              Sess
         WHERE sess.TADDR = V $TRANSACTION.ADDR
         И sess.SID = si.SID

      ) rollback_remaining,

      (
         SELECT (MAX (DECODE (PIECE, 0, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 1, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 2, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 3, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 4, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 5, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 6, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 7, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 8, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 9, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 10, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 11, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 12, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 13, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 14, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 15, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 16, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 17, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 18, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 19, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 20, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 21, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 22, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 23, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 24, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 25, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 26, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 27, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 28, SQL_TEXT, NULL)) ||
                 MAX (DECODE (PIECE, 29, SQL_TEXT, NULL)))
          FROM V $SQLTEXT_WITH_NEWLINES
          WHERE ADDRESS = SI.SQL_ADDRESS AND
          PIECE < 30
      ) SQL_TEXT
FROM sess si;

Ответ 6

У меня была аналогичная проблема в приложении Java. Я написал оболочку драйвера JDBC вокруг драйвера Oracle, поэтому весь вывод отправляется в файл журнала.