天天看點

排程作業(Oracle Scheduler)

Oracle Scheduler可以幫助DBA或者資料庫使用者自動排程和運作各種類型的作業,比如資料庫備份、收集優化器統計資訊、生成各種報表或者執行業務流程等等,也可以把Schedule和Resource Manager結合起來通過時間視窗激活指定的Resource Plan,完成企業在資源管理和作業排程上的各種複雜需求,在10g之前可以通過DBMS_JOB工具來實作類似的功能,但毫無疑問 ,DBMS_SCHEDULER的靈活性和多樣性比起老版本工具都有了極大的提升。

一,功能概述

 Oracle Scheduler到底可以實作那些具體功能呢?來看一下官方文檔給出的解釋:

 . Run database program units

    可以在本地或者遠端資料庫執行的資料庫程式包括:PL/SQL 匿名塊、PL/SQL 存儲過程、JAVA 存儲過程以及鍊

 . Run external executables, (executables that are external to the database)

    執行外部的可執行檔案,包括應用程式、Shell腳本、Windows批處理檔案,如果要在遠端主機執行外部作業,遠端主機隻需要安裝Agent而不需要Database

 . Schedule job execution using the following methods:

    .Time-based scheduling 

        You can schedule a job to run at a particular date and time, either once or on a repeating basis.

    .Event-based scheduling

        You can start jobs in response to system or business events. Your applications can detect events and then signal the Scheduler. Depending on the type of  signal         sent, the Scheduler starts a specific job. 

    .Dependency scheduling

        You can set the Scheduler to run tasks based on the outcome of one or more previous tasks. You can define complex dependency chains that include branching         and  nested chains.

 . Prioritize jobs based on business requirements.

    .Controlling Resources by Job Class

        把有相同特性的Job指定到一個Job Class,再把Job Class映射到Resource Consumer Group,實作對排程作業的資源配置設定控制

    .Controlling Job Prioritization based on Schedules

        通過時間視窗改變作業的優先等級,建立Window在一個時間範圍激活相應的 Resource Plan 來控制不同作業在不同時段的優先等級

 . Manage and monitor jobs

 . Execute and manage jobs in a clustered environment

    支援在RAC環境管理排程作業

二,基本概念

Oracle Scheduler包含的主要對象包括:Schedule,Program,Job,Job Class,Chain,Window,Database Destination,File Watcher,Credential ...具體介紹如下:

. Schedule (時間表)

    通過 DBMS_SCHEDULER 包中的過程 CREATE_SCHEDULE 定義排程的開始時間,結束時間以及重複間隔

    CREATE_EVENT_SCHEDULE 過程用來建立由事件觸發的時間表,由一個特定時間段内的一個事件調起一項任務

. Program (程式)

    定義了作業的形式及内容,作業形式可以是PL/SQL 匿名塊,也可以是存儲過程或者外部可執行檔案,執行的存儲過程帶有輸入參數時必須以匿名塊運作

. Job (作業)

    通過CREATE_JOB建立一個作業,這個存儲過程使用了重載,是以輸入參數的選擇可以非常靈活,既可以獨立設定作業的時間、内容、Job Class,也可以引用已     經存在的Schedule 和 Program 來簡化作業的建立

. Job Class (作業類)

     作業類中定義了Resource Consumer Group ,Service(RAC),日志等級,日志保留時間。要注意的一點是在Resource Manager中,service 參數會将會話映射到一個  資源使用者組,如果同時指定了RAC節點和使用者組,使用者組參數優先

. Chain (鍊)

    說白了就是一系列的作業通過鍊來建立起一套依賴關系,大概的思路是這樣的:先使 CREATE_CHAIN 建立一個鍊,再通過 DEFINE_CHAIN_STEP 和 DEFINE_CHAIN_EVENT_STEP 給要連結的 Program、Sub Chain、Event Condition、Event Schedule 分别定義一個别名(step_name),然後拿 DEFINE_CHAIN_RULE 定義這些 Step 的依賴規則,一通判斷、分支、嵌套之後,鍊就算建立完成了,在 CREATE_JOB 時 (job_type => 'CHAIN',job_action => 'chain_name') 就可以了,做人得講究,這個必須上圖:

排程作業(Oracle Scheduler)

. Window (視窗)

    視窗指的是一個介于開始時間和結束時間之間的時間段,(為什麼這麼簡單的一個概念被我說的如此繞口,我的國小國文老師呢?您有話要說嗎。。),通常用來調起作業,或者在不同的時間段激活不同的 Resource Plan 以調整作業之間的資源配置設定,文檔中還提到了 Overlapping Windows ,暫不研究了, 來吧,有圖有真相:

排程作業(Oracle Scheduler)

. Database Destination (資料庫路徑)

    通過 CREATE_DATABASE_DESTINATION 建立,在 CREATE_JOB 中作為一個輸入參數,用來執行遠端排程

. Credential (證書)

     證書用來儲存OS或者資料庫的使用者密碼,在執行External Job 或者遠端資料庫作業時使用

. File Watcher (檔案螢幕)

    這個好玩。。可以用來檢測一個OS檔案是否存在,根據檔案大小判斷傳輸是否完成,繼而觸發一個 Event Schedule

 . Lightweight Job (輕量級作業,為什麼我的顔色不對呢?) 

    11gR1之前不被支援,通過 job_style 指定,輕量級作業并不是一個排程器對象,它适用于多個頻繁執行的小作業,看看官方文檔的介紹:

  • Unlike regular jobs, they are not schema objects.
  • They have significantly better create and drop times over regular jobs because they do not have the overhead of creating a schema object.
  • They have lower average session create time than regular jobs.
  • They have a small footprint on disk for job metadata and run-time data.

三,建立過程

1,建立排程作業執行一個 Shell 腳本

執行Shell 腳本會在/tmp 生成一個檔案:

  1. [[email protected] ~]$ cat /tmp/job.sh 
  2. #!/bin/bash
  3. /bin/touch /tmp/abc.txt

注意:如果job.sh沒有執行權限,在執行下面的SQL語句之前,需要執行chmod指令,否則schedule job會失敗 chmod u+x /tmp/job.sh

建立證書,建立并立即執行作業:

  1. SQL> exec dbms_scheduler.create_credential('CRE1','user1','abcd1234')
  2. PL/SQL procedure successfully completed.
  3. SQL> exec dbms_scheduler.create_job(dbms_scheduler.generate_job_name,'EXECUTABLE','/tmp/job.sh',0,'','','','DEFAULT_JOB_CLASS',TRUE,FALSE,'Test.','CRE1')
  4. PL/SQL procedure successfully completed.
  5. SQL> select job_name,state,run_count,failure_count,raise_events from dba_scheduler_jobs where comments='Test.';
  6. JOB_NAME STATE RUN_COUNT FAILURE_COUNT RAISE_EVENTS
  7. ---------- --------------- ---------- ------------- --------------------
  8. JOB$_127 SUCCEEDED 1 0
  9. SQL> select JOB_NAME,STATUS,CREDENTIAL_NAME,ADDITIONAL_INFO from dba_scheduler_job_run_details where job_name='JOB$_127';
  10. JOB_NAME STATUS CREDENTIAL ADDITIONAL_INFO
  11. ---------- ---------- ---------- --------------------------------------------------------------------------------
  12. JOB$_127 SUCCEEDED CRE1 EXTERNAL_LOG_ID="job_74659_457",
  13.                                  USERNAME="user1"

檢查作業是否執行成功

  1. [[email protected] ~]$ ls /tmp/abc.txt 
  2. /tmp/abc.txt

2,分别執行SQL語句、匿名塊、PL/SQL 存儲過程

  1. SQL> exec dbms_scheduler.create_job(dbms_scheduler.generate_job_name,'PLSQL_BLOCK','insert into scott.t1(dname) values(''BLOCK'');',0,'','','','DEFAULT_JOB_CLASS',TRUE,FALSE,'Test_1')
  2. PL/SQL procedure successfully completed.
  3. SQL> exec dbms_scheduler.create_job(dbms_scheduler.generate_job_name,'PLSQL_BLOCK','BEGIN p2(''50'',''t'',''t''); END;',0,'','','','DEFAULT_JOB_CLASS',TRUE,FALSE,'Test_3')
  4. PL/SQL procedure successfully completed.
  5. SQL> exec dbms_scheduler.create_job(dbms_scheduler.generate_job_name,'STORED_PROCEDURE','p1',0,'','','','DEFAULT_JOB_CLASS',TRUE,FALSE,'Test_2')
  6. PL/SQL procedure successfully completed.

3,建立 Program 并在 Job 中引用

  1. SQL> exec dbms_scheduler.create_program('TEST1','PLSQL_BLOCK','BEGIN p2(''50'',''t'',''t''); END;',0,TRUE,'Pro_1')
  2. PL/SQL procedure successfully completed.
  3. SQL> exec dbms_scheduler.create_job(dbms_scheduler.generate_job_name,program_name => 'TEST1',repeat_interval => '',end_date => '',enabled => TRUE ,auto_drop => FALSE,comments => 'Test_9')
  4. PL/SQL procedure successfully completed.

4,建立 Job 時分别引用 Program 和 Schedule

  1. SQL> BEGIN
  2.   2 DBMS_SCHEDULER.CREATE_SCHEDULE(
  3.   3 SCHEDULE_NAME => 'sch1',
  4.   4 START_DATE => sysdate,
  5.   5 END_DATE => sysdate+3650,
  6.   6 REPEAT_INTERVAL => 'freq=yearly; bymonth=jan,apr,jul,oct; bymonthday=2',    --10年時間裡每年每個季度的第一個月的第二天執行作業
  7.   7 COMMENTS => 'Quarterly Report.'
  8.   8 );
  9.   9 END;
  10.  10 /
  11. PL/SQL procedure successfully completed.
  12. SQL> BEGIN
  13.   2 DBMS_SCHEDULER.CREATE_JOB(
  14.   3 dbms_scheduler.generate_job_name,
  15.   4 PROGRAM_NAME=>'TEST1',
  16.   5 SCHEDULE_NAME=>'sch1',
  17.   6 ENABLED=>TRUE,
  18.   7 AUTO_DROP=>FALSE,
  19.   8 COMMENTS=>'Test_99'
  20.   9 );
  21.  10 END;
  22.  11 /
  23. PL/SQL procedure successfully completed.

轉載自: http://blog.chinaunix.net/uid-26190993-id-3590381.html