sql >> データベース >  >> RDS >> Oracle

C++アプリケーションへのデータベース通知を取得する方法

    1つのアプローチは、Oracleの高度なキューイング を使用することです。 。そのためには、キュー(およびキュー表)を設定し、キュー内の次のメッセージを待機するPL/SQLプロシージャを作成する必要があります。

    次に、C++側はPL/ SQLプロシージャを呼び出します。このプロシージャは、次のイベントが発生したときに戻ります。

    Oracle側では、DBMS_SCHEDULER または、イベントを作成する同様の機能 、つまり、適切なタイミングで新しいメッセージをキューに挿入します。

    それはまだポーリングアプローチです。ただし、2つのイベントの間にアクティビティはまったくありません。

    更新:

    ここにいくつかのサンプルコードがあります。

    キューの初期設定(メッセージには数値とテキスト値が含まれています):

    grant AQ_ADMINISTRATOR_ROLE to appuser;
    grant EXECUTE ON DBMS_AQ to appuser;
    grant EXECUTE ON DBMS_AQ to appuser;
    
    
    CREATE TYPE sample_payload_type AS OBJECT
    (
      cmd  VARCHAR2(20),
      id   NUMBER
    );
    
    
    BEGIN
      DBMS_AQADM.CREATE_QUEUE_TABLE (
        queue_table        => 'sample_queue_table',
        queue_payload_type => 'sample_payload_type',
        sort_list          => 'ENQ_TIME',
        compatible         => '10.0'
      );
    END;
    /
    
    BEGIN
      DBMS_AQADM.CREATE_QUEUE (
        queue_name         => 'sample_queue',
        queue_table        => 'sample_queue_table'
      );
    
      DBMS_AQADM.START_QUEUE (
        queue_name         => 'sample_queue'
      );
    END;
    /
    

    パッケージヘッダー:

    create or replace package sample_queue_pkg
    as
    
      procedure get_next_msg(
        i_max_wait      number
       ,o_cmd      out  varchar2
       ,o_id       out  number
      );
    
    
      procedure put_msg(
        i_cmd           varchar2
       ,i_id            number
      );
    
    end sample_queue_pkg;
    /
    

    パッケージ本体:

    create or replace package body sample_queue_pkg
    as
    
      procedure get_next_msg(
        i_max_wait      number
       ,o_cmd      out  varchar2
       ,o_id       out  number
      )
      is
        dequeue_options dbms_aq.dequeue_options_t;
        message_properties dbms_aq.message_properties_t;
        message_handle RAW(16);
        message sample_payload_type;
    
        NO_MESSAGE_RECEIVED EXCEPTION;
        PRAGMA EXCEPTION_INIT(NO_MESSAGE_RECEIVED, -25228);
    
      begin
        dequeue_options.wait := i_max_wait;
        DBMS_AQ.DEQUEUE (
          queue_name => 'appuser.sample_queue',
          dequeue_options => dequeue_options,
          message_properties => message_properties,
          payload => message,
          msgid => message_handle
        );
    
        o_cmd := message.cmd;
        o_id := message.id;
    
      exception
        when NO_MESSAGE_RECEIVED then
          o_cmd := null;
          o_id := null;
    
      end get_next_msg;
    
    
      procedure put_msg(
        i_cmd           varchar2
       ,i_id            number
      )
      is
        enqueue_options dbms_aq.enqueue_options_t;
        message_properties dbms_aq.message_properties_t;
        message_handle RAW(16);
        message sample_payload_type;
        message_id NUMBER;
    
      begin
        message := sample_payload_type(i_cmd, i_id);
        DBMS_AQ.ENQUEUE(
          queue_name => 'appuser.sample_queue',
          enqueue_options => enqueue_options,
          message_properties => message_properties,
        payload => message,
          msgid => message_handle
        );
      end put_msg;
    
    end sample_queue_pkg;
    /
    

    データベースサーバーは、次のコードを使用してメッセージを送信できます。

    sample_queue_pkg.put_msg('run_task', 8234);
    commit;
    

    C ++サーバーは、保存されているsample_queue_pkg.get_next_msgを呼び出すメッセージを待機(および受信)できます。 。パラメータi_max_wait 次のメッセージを待機する最大時間を秒単位で指定します。次のメッセージを待機し、サーバーが終了しようとしているというシグナルを受信するまでメッセージを処理するループを実装することをお勧めします。



    1. SQLiteで数値を通貨としてフォーマットする

    2. テーブル値パラメーターのパフォーマンスに関する問題

    3. SSLを使用してPentahoケトル/スプーンをHerokuPostgreSQLに接続する際の問題

    4. android.database.sqlite.SQLiteCantOpenDatabaseException:不明なエラー(コード14):データベースを開くことができませんでした