我编写了以下查询以获取oracle数据库中针对特定会话的最后执行的SQL语句。 SQL文本不包含绑定变量的实际值。如何获取绑定变量值以及SQL文本。
SELECT * FROM v$SQLTEXT_WITH_NEWLINES WHERE address =
(SELECT prev_sql_addr FROM v$session WHERE audsid = userenv('SESSIONID'))
ORDER BY piece;
答案 0 :(得分:25)
要获取绑定变量,您必须使用下面的代码,您不需要使用跟踪。
SELECT * FROM v$sql_bind_capture WHERE sql_id='';
或
SELECT NAME,POSITION,DATATYPE_STRING,VALUE_STRING
FROM v$sql_bind_capture WHERE sql_id='';
http://shaharear.blogspot.com/2009/02/find-bind-variable-value.html
答案 1 :(得分:5)
我认为默认情况下不存储绑定变量值。不考虑潜在的安全问题(看到其他会话的实际工作),存储的数据量将是巨大的。
如果要查看绑定变量的值,则应激活该会话的跟踪。您可以通过在该会话中执行以下命令来执行此操作:
alter session set events '10046 trace name context forever, level 12';
的更多信息
答案 2 :(得分:3)
如果你在sqlplus中,你可以执行
select * from table
( dbms_xplan.display_cursor (null,null, 'ADVANCED'));
或者如果您正在寻找其他人执行的SQL,只需输入他们的SQL_ID和子光标#:
select * from table
( dbms_xplan.display_cursor ('sql_id',child_cursor#, 'ADVANCED'));
,如
select * from table
( dbms_xplan.display_cursor ('a18asdr99x',0, 'ADVANCED'));
此方法显示仅显示peeked绑定变量。唯一可靠的方法是使用绑定变量跟踪
dbms_monitor.session_trace_enable(session_id => 127,
serial_num => 29,
waits => FALSE,
binds => TRUE)
但当然必须在执行查询之前完成
答案 3 :(得分:2)
运行以下查询,该查询将sql_id作为输入参数,并为输出提供已替换的绑定变量值。
set serveroutput on;
DECLARE
v_fulltext CLOB;
v_sql_id VARCHAR2 (100);
CURSOR c1( v_sql_id varchar2)
IS
SELECT decode(substr(NAME,1,4),':SYS',replace(name,':',':"')||'"' ,NAME ) NAME, POSITION, datatype_string,nvl(VALUE_STRING,'NULL') value_string
FROM v$sql_bind_capture
WHERE sql_id = v_sql_id;
BEGIN
v_sql_id:= '&sql_id';
SELECT sql_fulltext
INTO v_fulltext
FROM v$sql
WHERE sql_id =v_sql_id AND ROWNUM = 1;
FOR rec IN c1(v_sql_id)
LOOP
IF substr(rec.datatype_string,1,8) = 'VARCHAR2'
THEN
SELECT REPLACE (v_fulltext,
rec.NAME,
'''' || rec.value_string || ''''
)
INTO v_fulltext
FROM DUAL;
END IF;
IF rec.datatype_string = 'NUMBER'
THEN
SELECT REPLACE (v_fulltext, rec.NAME, rec.value_string)
INTO v_fulltext
FROM DUAL;
END IF;
END LOOP;
DBMS_OUTPUT.PUT_LINE(v_fulltext);
EXCEPTION
WHEN NO_DATA_FOUND
THEN DBMS_OUTPUT.PUT_LINE('NO SQL FOUND FOR THE SQL ID');
END;
/
答案 4 :(得分:0)
查看 BiPin 的回答,我对其进行了一些修改以满足我的需要。 我需要弄清楚用户在实时运行报告时使用了哪些参数。这是我的解决方案,它将 childnumber 添加到来自 v$sql_bind_capture 的查询中。
declare
v_sql_id varchar(100);
v_fulltext clob;
v_childnumber number;
begin
v_sql_id := '&sql_id';
v_childnumber := '&childnumber';
SELECT LISTAGG(SQL_text, '') within group (order by piece)
INTO v_fulltext
FROM v$sqltext
WHERE sql_id =v_sql_id;
for I in (select name,VALUE_STRING from v$sql_bind_capture where sql_id = V_SQL_ID and child_number = V_CHILDNUMBER)LOOP
v_fulltext := regexp_replace(v_fulltext,i.name||' ',i.value_string);
end LOOP;
DBMS_OUTPUT.PUT_LINE(v_fulltext);
end;