在11g中,Oracle提供了一个新建的Scheduler特性,帮助将作业实现自动化。它还可以帮助你控制资源的利用与并可以将数据库中的作业按优先顺序执行。传统的dbms_jobs的一个限制是它只能调度基于PL/SQL的作业,不能用来调度操作系统的可执行文件或脚本。

Scheduler包括如下权限:
scheduler_admin角色包含所有的scheduler系统权限,授权如下:
SQL> grant scheduler_admin to djp01
  2  /
 
Grant succeeded.
 
SQL>
manage scheduler系统权限允许做以下工作:‘
创建、删除和更改作业类,窗口和窗口组。
停止作业
提前启动和停止窗口(关于这些部件在下文中进行介绍)。
授权如下:
SQL> grant manage scheduler to djp01
  2  /
 
Grant succeeded.
 
SQL>
create job系统权限允许做如下工作:
创建作业(job)、进度表(schedule)、程序(program)、链(chain)和事件(event)。
(关于这些部件在下文中会进行介绍),授权如下:
SQL> grant create job to djp01
  2  /
 
Grant succeeded.
 
SQL>
如果要执行的程序在不同的模式下,那么必要拥有执行相应模式下的程序的执行权限,如下execute any procedure。
 
Scheduler包括如下基本部件:
(1)作业(job)
作业是一个计划执行一次或多次的任务。例子如下:
SQL> alter session set nls_date_format = 'yyyy-mm-dd hh24:mi:ss'
  2  /
 
Session altered.
 
SQL> alter session set nls_timestamp_tz_format = 'yyyy-mm-dd hh24:mi:ss.ff'
  2  /
 
Session altered.
 
SQL> alter session set nls_timestamp_format = 'yyyy-mm-dd hh24:mi:ss.ff'
  2  /
 
Session altered.
 
SQL>

说明:在使用调度程序时,会涉及一些时间的相关信息,我这里进行一些时间格式的设置方便使用。

SQL> create table emp_bak
  2  as
  3  select *
  4  from employees
  5  where 1 = 0
  6  /
 
Table created.
 
SQL> 
 
SQL> begin
  2     dbms_scheduler.create_job(
  3        job_name=>'test_job',
  4        job_type=>'PLSQL_BLOCK',
  5        job_action=>'insert into emp_bak select * from employees where rownum <= 200;',
  6        start_date=>'2012-12-09 14:40:00',
  7        repeat_interval=>'FREQ=DAILY;INTERVAL=2',
  8        end_date=>'2012-12-09 20:00:00',
  9        comments=>'insert old employees into the emp_bak table',
 10        auto_drop=>false,
 11        enabled=>true);
 12  end;
 13  /
 
PL/SQL procedure successfully completed.
 
SQL>
说明:job_name指定作业的名称;job_type指定要创建的作业的类型,其值包括PLSQL_BLOCK(PL/SQL块),STORED_PROCEDURE(存储过程),EXECUTABLE(可执行文件或Java程序)。job_action指定作业要执行过程,命令或脚本。start_date与end_date指定作业的启动与结束时间。comments用于给当前作业添加注释。enabled指定创建作业时,是否启动或禁用作业,默认值为false,表示禁用;值为true,表启用。auto_drop指定该作业执行完成后,是否自动将其删除,默认值为true,表示执行完成后自动删除该作业。repeat_interval指定作业执行的频率,FREQ=DAILY;INTERVAL=2表示每天运行一次该作业。该值是一个日历表达式(calendaring expression)由三个部分组成,Frequency: 这是表达式必须包含的部分,用FREQ指定,可能取的值为YEARLY,MONTHLY,WEEKLY,DAILY,HOURLY,MINUTELY和SECONDLY。repeat interval:这个时间间隔由INTERVAL关键字标识,表示执行的频率。specific:提供一个作业何时运行的详细信息,可能取值为:BYMONTH,BYWEEKNO,BYYEARDAY,BYMONTHDAY,BYDAY,BYHOUR,BYMINUTE和BYSECOND。例如:BYMONTHDAY表示每月的某一天,BYDAY表示每周的某一天。以下是典型的日历表达式:
FREQ=DAILY;INTERVAL=3;每三天执行一次。
FREQ=HOURLY;INTERVAL=2;每隔一小时执行一次。
FREQ=WEEKLY,BYDAY=SUN;每个星期日执行一次。
FREQ=WEEKLY;INTERVAL=2,BYDAY=FRI;每隔一周的周五执行一次。
FREQ=MONTHLY;BYMONTHDAY=1;每月最后一天执行一次。
FREQ=MINUTELY;INTERVAL=30;每半个小时执行一次。
下面我们看一下执行的情况:
SQL> select count(*)
  2  from emp_bak
  3  /
 
  COUNT(*)
----------
       200
 
SQL>
上述调度程序的作业成功运行,下面我们看一些该作业的信息:
 
SQL> select job_style,job_type,job_action,program_name,state
  2  from dba_scheduler_jobs
  3  where job_name = upper('test_job')
  4  /
 
JOB_STYLE              JOB_TYPE
---------------------- --------------------------------
JOB_ACTION
--------------------------------------------------------------------------------
PROGRAM_NAME
--------------------------------------------------------------------------------
STATE
------------------------------
REGULAR                PLSQL_BLOCK
insert into emp_bak select * from employees where rownum <= 200;
 
COMPLETED
 
 
SQL>
状态显示,该作业执行完成,该作业的类型为REGULAR(规律性的)。
 
作业的其他一些管理:
禁用一个作业:
SQL> exec dbms_scheduler.disable('test_job');
 
PL/SQL procedure successfully completed.
 
SQL>
激活一个作业:
SQL> exec dbms_scheduler.enable('test_job');
 
PL/SQL procedure successfully completed.
 
SQL>
运行一个作业:
SQL> truncate table emp_bak;
 
Table truncated.
 
SQL> exec dbms_scheduler.run_job('test_job');
 
PL/SQL procedure successfully completed.
 
SQL> select count(*)
  2  from emp_bak
  3  /
 
  COUNT(*)
----------
       200
 
SQL>
说明:该运行相当于是手工执行一次相应的程序。
停止一个作业:
SQL> exec dbms_scheduler.stop_job('test_job');
如果一个作业不在运行状态,它将会出现ORA-27366错误。
删除一个作业:
SQL> exec dbms_scheduler.drop_job('test_job');
 
PL/SQL procedure successfully completed.
 
SQL>
 

(2)进度表(schedule)

进度表是数据库执行一个作业的时间及频率的说明。假如有一些作业都是在大致相同的时间内运行的,那么,可以使用一个进度表,可以化这些作业的创建与管理。例子如下:
SQL> begin
  2     dbms_scheduler.create_schedule(
  3        schedule_name=>'test_schedule',
  4        start_date=>systimestamp,
  5        repeat_interval=>'FREQ=MINUTELY;INTERVAL=30',
  6        end_date=>systimestamp+3,
  7        comments=>'Every 30 minute');
  8  end;
  9  /
 
PL/SQL procedure successfully completed.
 
SQL>
下面我们查看该进度表的创建信息:
SQL> select start_date,end_date,schedule_type
  2  from dba_scheduler_schedules
  3  where schedule_name = upper('test_schedule')
  4  /
 
START_DATE
---------------------------------------------------------------
END_DATE
---------------------------------------------------------------
SCHEDULE_TYPE
----------------
2012-12-09 17:22:43.781000
2012-12-12 17:22:43.000000
CALENDAR
 
SQL>

可以对已经创建的进度表进行相关属性的更改,如下:

SQL> begin
  2     dbms_scheduler.set_attribute(
  3        name=>'test_schedule',
  4        attribute=>'start_date',
  5        value=>systimestamp);
  6  end;
  7  /
 
PL/SQL procedure successfully completed.
 
SQL>
对已经有的进度表,我们可以进行删除,如下:
SQL> exec dbms_scheduler.drop_schedule('test_schedule');
 
PL/SQL procedure successfully completed.
 
SQL>
 
(3)程序(program)
程序包括关于一个scheduler作业的元数据。程序包括程序名,程序类型以及程序的动作。它是一个过程或是可执行脚本的实际名称。例子如下:
SQL> begin
  2     dbms_scheduler.create_program(
  3        program_name=>'test_program',
  4        program_type=>'STORED_PROCEDURE',
  5        program_action=>'auto_archive_emp',
  6        enabled=>true,
  7        comments=>'use to execute the procedure of auto_archive_emp');
  8  end;
  9  /
 
PL/SQL procedure successfully completed.
 
SQL>
说明:program_type与program_action同上述的job_type,job_action含义一样,这里不再说明。enabled表示该程序是否被启用,默认值为false,表示禁用。
我们可以用如下的方法对程序进行启用或禁用:
禁用一个程序:
SQL> exec dbms_scheduler.disable('test_program');
 
PL/SQL procedure successfully completed.
 
SQL>
启用一个程序:
SQL> exec dbms_scheduler.enable('test_program');
 
PL/SQL procedure successfully completed.
 
SQL>
同样,我们也可以进行删除,如下:
SQL> exec dbms_scheduler.drop_program('test_program');
 
PL/SQL procedure successfully completed.
 
SQL>
对程序相关信息的查看可以使用dba_scheduler_programs数据字典。
(4)链(chain)
可以使用调度程序链的概念将相关的程序链接在一起。因此,一个程序的成功运行,可能是以另外的程序成功运行为基础;还可以是基于一个键而非程序启动作业。链中连续的位置称为链的“步骤(step)”,每个步骤指向另一个链,程序或事件。由于链使用Oracle Streams Rules Engine(Oracle流规则引擎对象)。因此用户必须具有create job 和Rules Engine权限才能创建一个链。例子如下:
进行如下授权:
SQL> begin
  2     dbms_rule_adm.grant_system_privilege(
  3        dbms_rule_adm.create_rule_obj,'djp01');
  4     dbms_rule_adm.grant_system_privilege(
  5        dbms_rule_adm.create_rule_set_obj,'djp01');
  6     dbms_rule_adm.grant_system_privilege(
  7        dbms_rule_adm.create_evaluation_context_obj,'djp01');
  8  end;
  9  /
 
PL/SQL procedure successfully completed.
 
SQL>
创建如下:
SQL> begin
  2     dbms_scheduler.create_chain(
  3        chain_name=>'test_chain',
  4        comments=>'A shain test');
  5  end;
  6  /
 
PL/SQL procedure successfully completed.
 
SQL>
定义链步骤:
SQL> begin
  2     dbms_scheduler.define_chain_step(
  3        chain_name=>'test_chain',
  4        step_name=>'test_step1',
  5        program_name=>'test_program1');
  6     dbms_scheduler.define_chain_step(
  7        chain_name=>'test_chain',
  8        step_name=>'test_step2',
  9        program_name=>'test_program2');
 10  end;
 11  /
 
PL/SQL procedure successfully completed.
 
SQL>
说明:链步骤可以指向一个程序、链或事件。使用不同的参数进行标识。
为了使用链有效的运行,必须给链添加规则,用于确定步骤何时运行并指定运行条件。如下:
SQL> begin
  2     dbms_scheduler.define_chain_rule(
  3        chain_name=>'test_chain',
  4        condition=>'true',
  5        action=>'start test_step1');
  6     dbms_scheduler.define_chain_rule(
  7        chain_name=>'test_chain',
  8        condition=>'test_step1 completed',
  9        action=>'start test_step2');
 10     dbms_scheduler.define_chain_rule(
 11        chain_name=>'test_chain',
 12        condition=>'test_step2 completed',
 13        action=>'end');
 14  end;
 15  /
 
PL/SQL procedure successfully completed.
 
SQL>
说明:在规则中,我们按照每一步的先后顺序进行定义。如果每个步骤中都事务的先后关系,使用链是一个不错的选择。

在上述步骤完成之后,我们还需要对链进行启用,如下:

SQL> exec dbms_scheduler.enable('test_chain');
 
PL/SQL procedure successfully completed.
 
SQL>
这时,我们就可以在作业(job)中使用该链了(job_type指定为chain,job_action指定对应链的名称,如test_chain)。
我们还可以使用如下方式运行:
SQL> begin
  2     dbms_scheduler.run_chain(
  3        chain_name=>'test_chain',
  4        start_steps=>'test_step1,test_step2');
  5  end;
  6  /
 
PL/SQL procedure successfully completed.
 
SQL>
 
(5)事件(event)

Scheduler使用Oracle Stream Advanced Qeueing(Oracle流高级队列)触发事件并启动基于事件的数据库作业。事件是一个应用程序或是进程注意到某个事件或动作时发出的一条消息。有两种类型的事件:Scheduler引发的事件和应用程序引发的事件。Scheduler引发的事件由Scheduler运行中的变化而导致,比如Scheduler作业成功完成是一个事件。应用程序引发的事件由Scheduler为启动一个作业而使用或是消费。

使用基于事件的作业,只要在create_job过程上指定event_condition与queue_spec即可。但是事件的定义涉及到了,dbms_aqadm程序包的一些使用。我查看了dbms_aqadm包的声明,没有相关的注释,之后试了几次,没有达到效果,这个问题有待解决。
 
下面我们来看几个综合使用的例子:
SQL> begin
  2     dbms_scheduler.create_job(
  3        job_name=>'test_job1',
  4        program_name=>'test_program1',
  5        schedule_name=>'test_schedule',
  6        enabled=>true,
  7        auto_drop=>false,
  8        comments=>'use program and schedule to create job');
  9  end;
 10  /
 
PL/SQL procedure successfully completed.
 
SQL>
说明:在上述作业的创建中,我使用了程序与进度表。如果要进行调整,可以调整相应的程序与进行度即可。
SQL> begin
  2     dbms_scheduler.create_job(
  3        job_name=>'test_job2',
  4        schedule_name=>'test_schedule',
  5        job_type=>'chain',
  6        job_action=>'test_chain',
  7        enabled=>true,
  8        auto_drop=>false,
  9        comments=>'use chain to create job');
 10  end;
 11  /
 
PL/SQL procedure successfully completed.
 
SQL>
说明:在创建job时,我们两样也可以指定一个链。如果要指定链,那么job_type为chain,job_action为所创建的链名。

Oracle 调度程序(scheduler)摘自一位大神的更多相关文章

  1. [Linux]运维三十六计--腾讯两位大神的总结

    这里是腾讯两位大神梁定安.周小军总记得运维DBA三十六计,So有道理

  2. git命令行 整理(一位大神给我的私藏)

    Evernote Export Git 是一个很强大的分布式版本控制系统.它不但适用于管理大型开源软件的源代码,管理私人的文档和源代码也有很多优势. Git常用操作命令: 1) 远程仓库相关命令 检出 ...

  3. 大神的P图过程!快来偷窥!

    来自美国的艺术家James(@jameasons) 平时我们总是能看到一些大神合成出这样的图片, 但是他们P图的过程是怎样的,很多人都是不知道的. 接下来再看看这位大神的其他作品, 如果你看了上面视频 ...

  4. Android大神 博客

    https://github.com/yeungeek/awesome-android-person Android大神 受Trinea的开源项目的启发和参考,也准备列一列Android圈里的大神们. ...

  5. 【推荐】Java工程师如何从普通成为大神值得一读

    本文源自 http://www.hollischuang.com/archives/489 一点感悟 java作为一门编程语言,在各类编程语言中作为弄潮儿始终排在前三的位置,这充分肯定了java语言的 ...

  6. 【web前端面试题整理04】阿里一行之大神面对面

    前言 这段时间我在河南一家公司当了一段时间的前端主管,最后可耻的匿了,原因各种各样,最主要的就是不想呆在郑州了. 其实这里的同事还是很不错的,面对老总最后的挽留我不是没有动心,而是这个地方确实不太好, ...

  7. 兄台息怒,关于arguments,您的想法和大神是一样一样的----闲聊JS中的apply和call

    JavaScript提供了apply和call两种调用方式来确定函数体中this的指向,表现出来的特征就是:对象可以'借用'其他对象的方法.之前的几篇博客回顾了一些Web控件的一些开发方法,我们聊了如 ...

  8. iOS组件化思路-大神博客研读和思考

    一.大神博客研读 随着应用需求逐步迭代,应用的代码体积将会越来越大,为了更好的管理应用工程,我们开始借助CocoaPods版本管理工具对原有应用工程进行拆分.但是仅仅完成代码拆分还不足以解决业务之间的 ...

  9. 跟着大神重写的KNN 文档归类小工具

    ·背景 在知道KNN之前,楼主有时候会粗糙地做一些分类模型的计算.在拜读了Orisun大神[http://www.cnblogs.com/zhangchaoyang/articles/2162393. ...

随机推荐

  1. Linux搭建PHP+MySQL+Apache环境

    环境: CentOS 6.4 MySQL详细安装可参考:http://www.cnblogs.com/yangxia-test/archive/2012/11/12/2766237.html Apac ...

  2. Android优化—— 内存分析工具 MAT 的使用

    1 内存泄漏的排查方法 Dalvik Debug Monitor Server (DDMS) 是 ADT插件的一部分,其中有两项功能可用于内存检查 : ·    heap 查看堆的分配情况 ·     ...

  3. C和指针笔记 3.6链接属性

    链接属性决定如何处理在不同文件中出现的标识符.标识符的作用域也它的链接属性有关,但这两个属性并不相同. 没有链接属性的标识符(none)总是被当作单独的个体,也就是说该标识符的多个声明被当作独立不同的 ...

  4. poj2407

    欧拉函数裸题. 欧拉函数:在数论,对正整数n,欧拉函数是少于或等于n的数中与n互质的数的数目. 欧拉函数的定义: E(N)= (  区间[1,N-1] 中与 N 互质的整数个数). 对于 积性函数 F ...

  5. Eclipse调试按钮消失问题

    Window-->Reset Perspective 把Eclipse重置一下,然后 点击红色框圈的向下的箭头,在弹出的菜单里边,点击 show debug toolbar 这个菜单项目,然后奇 ...

  6. [shell]. 点的含义

    . 的含义 当前目录 隐藏文件 任意一个字符 生效配置文件

  7. 装了个干净的win7

    lanny的电脑基本信息 我的电脑 联想 ThinkPad T450s 笔记本电脑 操作系统 Windows 旗舰版 64位 主显卡 集成显卡 IE浏览器 版本号 8.0 基本硬件展示 处理器 英特尔 ...

  8. OSGEARTH三维地形开源项目

    第一章   OSGEarth介绍 第二章   OSGEarth编译环境配置 OSGEarth的编译环境配置随着版本的不同.运行平台的不同,也有很大的差异.本章主要以Windows XP SP3(x86 ...

  9. QuickFIX/J常见问题汇总

    最近在搞QuickFIX/J,网上的资料不算很多,遇到一些简单的问题都需要google一阵才能找到解决方法,因此做点记录: 错误:Rejecting invalid message: quickfix ...

  10. Asp.net通过Jquery操作WebService进行Ajax读写

    一说到开始,我们当然需要项目. 首先,创建一个Asp.net Web 应用,然后新增一个名称为“Web 服务”的文件,也就是后缀名为".asmx"的文件,然后需要进行配置一下,在W ...