DBMS_AQADM/AQ包

DBMS_AQADM/AQ包兼容Oracle的“进程间” (或者跨会话 -- inter-session) 通信的功能。

DBMS_AQADM/AQ是通过“队列”来实现session间的消息传递的。消息发送者将消息存入队列,而消息接收者从队列取出消息,从而实现消息的传递。

一个消息队列表中可以存储多个消息队列,但相同队列表中的队列中的消息类型必须是相同的。

其中,DBMS_AQADM包主要提供“队列表”和“队列”的管理功能,DBMS_AQ包主要提供收发消息功能

表1、2分别展示了DBMS_AQADM包和DBMS_AQ包的子程序。

DBMS_AQADM包子程序 说明
过程CREATE_QUEUE_TABLE 创建队列表
过程DROP_QUEUE_TALBE 删除队列表
过程CREATE_QUEUE 创建队列
函数DROP_QUEUE 删除队列
DBMS_AQ包子程序 说明
过程ENQUEUE 消息入队列
过程DEQUEUE 消息出队列

具体收发消息的操作过程为:

创建消息类型

创建消息队列表

创建消息队列

创建收发消息临时表

将消息插入发送消息临时表

发送消息(消息入队列)

接收消息(消息出队列)

从接收消息临时表取消息(消息不及时取出,再接收消息时,上一次收到的消息将丢失)

示例:

--创建自定义类型
CREATE OR REPLACE TYPE tt AS OBJECT(    
		rec_id         NUMBER,
    tablename      VARCHAR2(50),
    blobfieldname  VARCHAR2(50),
    dutyname       VARCHAR2(50));
/

--创建队列表    
     BEGIN
  DBMS_AQADM.CREATE_QUEUE_TABLE
  (
    QUEUE_TABLE           =>        'aqtest'
   ,QUEUE_PAYLOAD_TYPE    =>        'tt'
   );
End;
/

--建队列
begin
    dbms_aqadm.create_queue
    ( queue_name => 'test_queue',
      queue_table => 'aqtest');
end;
/

--建临时发送消息表
create table send_msg (message tt);

--建临时接收消息表
create table get_msg (message tt);

--将消息插入发送消息临时表
insert into send_msg values(tt(1,'表1','blob字段1','任务1'));

--发送消息
DECLARE
   enq_msgid   RAW (16);
   eopt        DBMS_AQ.enqueue_options_t;
   mprop       DBMS_AQ.message_properties_t;
BEGIN
   DBMS_AQ.ENQUEUE(queue_name           => 'test_queue',
                    enqueue_options      => eopt,
                    message_properties   => mprop,
                    payload              => 'sysdba.send_msg',
                    msgid                => enq_msgid);
END;
/

--接收消息
DECLARE
    deq_msgid           RAW(16);
    dopt                dbms_aq.dequeue_options_t;
    mprop               dbms_aq.message_properties_t;
    outinfo             sysdba.tt;
    no_messages         exception;
    pragma exception_init(no_messages, -20228);

BEGIN
		dopt.wait := 0;--NO wait

    DBMS_AQ.DEQUEUE(
        queue_name => 'test_queue', 
        dequeue_options => dopt,
        message_properties => mprop,
				payload => 'sysdba.get_msg',
        msgid => deq_msgid);

END;
/

--消息已经在接收消息临时表中
select * from get_msg;
MESSAGE(TT)      |
-----------------
TT(1, '表1', 'blob|
字段1', '任务1')     |
总数目:1