Oracle脚本无任何问题地静默停止工作

时间:2019-08-22 09:13:59

标签: oracle

我有一个Oracle脚本,它需要一些时间来执行(合并/更新数百万行),它通过sqlplus执行,并且输出重定向到日志文件。脚本的执行不一致,有时可以在50英尺内成功运行,这对我们来说已经足够了,但是有时脚本从未停止,并且没有记录异常,日志文件仍然为空,sqlplus似乎卡住了。在Oracle中运行查询之后,我看着它们突然消失了(大约1个小时后),就像有人自动杀死交易或内部流程一样。没有行被更新。 我不是Oracle DBA,所以我不知道要检查什么以了解那里发生的事情...

我已经通过使用合并指令的示例说明了我的问题,但是在许多其他脚本(例如,大量插入)中遇到了该问题。 共同点是,当脚本需要大量的Oracle资源时,我可以更改脚本并为该大规模更新做一个更优化的版本,但我真的很想知道这里到底发生了什么,以及为什么在这种情况下我根本没有信息。 我已经检查了Windows事件日志,却一无所获。 我不知道在Oracle哪里搜索以了解发生了什么。我确信必须有一些内部日志,但是我对Oracle管理的知识太有限了,在这一点上我需要帮助。

SET TIMING ON
SET SERVEROUTPUT ON SIZE unlimited
SET FEEDBACK OFF

DECLARE
    PROCEDURE SYMAG_MERGE_CUST_LASTACT 
    IS
        start_time number:= DBMS_UTILITY.get_time; 
        alter_time number; 
        merge_time number; 
        commit_time number; 
        end_time number;
    BEGIN

    -- Session settings 
    EXECUTE IMMEDIATE 'ALTER SESSION SET skip_unusable_indexes = true';
    EXECUTE IMMEDIATE 'ALTER TABLE CUSTOMERS nologging';
    EXECUTE IMMEDIATE 'ALTER SESSION ENABLE PARALLEL DML';
    EXECUTE IMMEDIATE 'ALTER SESSION FORCE PARALLEL DML';

    alter_time := DBMS_UTILITY.get_time;
    DBMS_OUTPUT.PUT_LINE('= Alter1: '||to_char((alter_time-start_time)/100)||'s ');

    MERGE /*+ first_rows parallel(C,8) parallel(SRC,8) */ INTO CUSTOMERS C
    USING (SELECT CST_CODE FROM CUSTOMERS WHERE STA_CODE <> 0) SRC ON (C.CST_CODE = SRC.CST_CODE)
    WHEN MATCHED THEN UPDATE SET CST_DATELASTACT = sysdate;

    merge_time := DBMS_UTILITY.get_time;
    DBMS_OUTPUT.PUT_LINE('= Merge: '||to_char((merge_time-alter_time)/100)||'s ');

    -- Commit 
    COMMIT;
    commit_time := DBMS_UTILITY.get_time;
    DBMS_OUTPUT.PUT_LINE('= Commit: '||to_char((commit_time-merge_time)/100)||'s ');

    -- Session settings restore
    EXECUTE IMMEDIATE 'ALTER SESSION SET skip_unusable_indexes = false';
    EXECUTE IMMEDIATE 'ALTER TABLE CUSTOMERS logging';

    end_time := DBMS_UTILITY.get_time;
    DBMS_OUTPUT.PUT_LINE('= Alter2: '||to_char((end_time-commit_time)/100)||'s ');
    DBMS_OUTPUT.PUT_LINE('----------------------------------------------------------');
    DBMS_OUTPUT.PUT_LINE('= Total time: '||to_char((end_time-start_time)/100)||'s ');

EXCEPTION   
    WHEN OTHERS THEN
        DBMS_OUTPUT.PUT_LINE('= Exception : ' || SQLCODE || ' - ' || SQLERRM);
        Rollback;
        DBMS_OUTPUT.PUT_LINE('= Rollback');
END;

BEGIN
    DBMS_OUTPUT.PUT_LINE('=== Start of script step 3-4(v2)');
    SYMAG_MERGE_CUST_LASTACT();
END;
/

EXIT;

我希望脚本在每次执行时都会停止,并至少显示一个Oracle异常,或者了解Oracle中发生了什么,以防止脚本卡住而不会记录任何错误。

编辑: 在检查alert_.log时,我只有在脚本执行时才有这些日志:

**Fatal NI connect error 12170.**

VERSION INFORMATION:
    TNS for Linux: Version 12.1.0.2.0 - Production
    Oracle Bequeath NT Protocol Adapter for Linux: Version 12.1.0.2.0 - Production
    TCP/IP NT Protocol Adapter for Linux: Version 12.1.0.2.0 - Production
Time: 21-AUG-2019 17:28:57
Tracing not turned on.
Tns error struct:
    ns main err code: 12535

TNS-12535: TNS:operation timed out
    ns secondary err code: 12560
    nt main err code: 505

TNS-00505: Operation timed out
    nt secondary err code: 110
    nt OS err code: 0
Client address: (ADDRESS=(PROTOCOL=tcp)(HOST=10.126.84.228)(PORT=10686))
Wed Aug 21 17:45:36 2019

0 个答案:

没有答案