【问题标题】:Is there any way to keep a track of rows inserted by a oracle function in database有什么方法可以跟踪数据库中oracle函数插入的行
【发布时间】:2016-10-20 11:06:40
【问题描述】:

我有一个程序来更新从开始日期到结束日期的余额,并且 我还想跟踪插入的记录数。我正在使用 dbms_output.put_line 来获取插入的记录数,但它没有给出任何输出,当执行完成时,将显示计数的输出。程序代码如下:

create or replace function updatebal(start_date IN DATE, end_date IN DATE)
RETURN NUMBER 
IS
difference number;
curr_r  number;
BEGIN 
difference := end_date - start_date;
curr_r := 0;
while curr_r <= difference LOOP
curr_r := curr_r + 10;
for curr_in in 1..10 LOOP
date_value := date_value +1 ;
insertAvailBal(date_value);
commit;
select count(*) into totalCount from avail_bal;
dbms_output.put_line('total count' || totalCount);
end loop;
END LOOP;
RETURN 1;
END;

现在我试图从这个过程中打印 totalCount 来获取插入到这个表中的行数avail_bal。但是没有输出。 请帮助我,在此先感谢

【问题讨论】:

    标签: stored-procedures plsql oracle10g oracle-sqldeveloper stored-functions


    【解决方案1】:

    正如 Tony 已经回答的那样:您无法更改 dbms_output 的行为。

    向存储过程外部发送进度信号的推荐方法是使用dbms_application_info 包来管理v$session_longops 中的信息

    您甚至可以为外循环和内循环管理单独的进度指示器。 v$session_longops 甚至会根据一段时间内的平均持续时间显示该过程需要多长时间的估计值。如果每个(报告的)步骤的运行时间相当恒定,那么这些估计是非常准确的。

    你可以像这样增强你的功能:

    create or replace function updatebal(start_date IN DATE, end_date IN DATE)
      RETURN NUMBER 
    IS
      difference number;
      curr_r  number;
      main_index binary_integer;
      sub_index  binary_integer;
      main_slno  binary_integer;
      sub_slno   binary_integer;
    
    BEGIN 
      difference := end_date - start_date;
      curr_r := 0;
    
      -- initialize the module information
      dbms_application_info.set_module('updatebal', 'Calculate Balance');
    
      -- initialize two different "handles" for the inner and outer loop
      main_index := dbms_application_info.set_session_longops_nohint;
      sub_index := dbms_application_info.set_session_longops_nohint;
    
      while curr_r <= difference LOOP
        curr_r := curr_r + 10;
    
        -- report each outer step
        dbms_application_info.set_session_longops(rindex => main_index, 
                slno => main_slno, 
                op_name => 'main loop', 
                sofar => curr_r, 
                totalwork => difference);
    
        for curr_in in 1..10 LOOP
    
          date_value := date_value +1;
    
          insertAvailBal(date_value);
          commit;
    
          select count(*) into totalCount from avail_bal;
    
          -- report each inner step with the totalcount
          dbms_application_info.set_session_longops(
                          rindex => sub_index, 
                          slno => sub_slno, 
                          op_name => 'Sub Loop, totalcount'||totalcount, 
                          sofar => curr_in, totalwork => 10);
    
        end loop;
      END LOOP;
    
      RETURN 1;
    
      dbms_application_info.set_module(null,null);
    END;
    /
    

    查看手册了解更多详情:
    https://docs.oracle.com/database/121/ARPLS/d_appinf.htm#ARPLS003

    【讨论】:

      【解决方案2】:

      dbms_output 就是这样工作的,它在运行完成后显示它的所有输出,你不能实时监控它。

      如果你真的需要这种实时的进度监控,你可以使用一个带有自治事务的过程将消息插入一个特殊的表中,然后从另一个会话你可以查看内容在进程仍在运行时删除该表。

      此类程序的示例:

      procedure log_message (p_message varchar2) is
         pragma autonomous_transaction;
      begin
         insert into message_table (message) values (p_message);
         commit;
      end;
      

      【讨论】:

        猜你喜欢
        • 2014-06-13
        • 1970-01-01
        • 1970-01-01
        • 2012-05-30
        • 1970-01-01
        • 2013-08-18
        • 2017-08-24
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多