Utilisation de la messagerie persistante avec les messages stockés dans la banque d'objets cloud

Le package DBMS_PIPE dispose de fonctionnalités étendues sur Autonomous Database pour prendre en charge la messagerie persistante, où les messages sont stockés dans la banque d'objets cloud.

A propos de la messagerie persistante avec DBMS_PIPE

La messagerie persistante avec DBMS_PIPE permet à des sessions de base de données de communiquer dans la même région ou entre régions avec des messages stockés dans la banque d'objets cloud.

Messages persistants dans DBMS_PIPE :

  • Permet d'envoyer et de récupérer des messages très volumineux.

  • Prendre en charge l'envoi d'un grand nombre de messages de type pipe.

  • Prendre en charge l'envoi et la réception de messages au sein d'une même base de données, sur plusieurs bases de données et dans différentes régions.

  • Prendre en charge plusieurs canaux à l'aide du même URI d'emplacement de banque d'objets cloud.

Vous pouvez créer des canaux de messagerie persistants dans n'importe quel type DBMS_PIPE pris en charge :

  • Canal implicite : créé automatiquement lorsqu'un message est envoyé avec un nom de canal inconnu à l'aide de la fonction DBMS_PIPE.SEND_MESSAGE.
  • Canal explicite : créé à l'aide de la fonction DBMS_PIPE.CREATE_PIPE avec un nom de canal spécifié par l'utilisateur.
  • Pipe publique : accessible par tout utilisateur disposant du droit d'accès EXECUTE sur le package DBMS_PIPE.
  • Pipe privée : accessible par les sessions avec le même utilisateur que le créateur de pipe.
Remarque

Oracle recommande de créer un pipeline explicite avant d'envoyer ou de recevoir des messages avec des messages persistants. La création d'un canal explicite avec DBMS_PIPE.CREATE_PIPE garantit que le canal est créé avec les droits d'accès souhaités, publics ou privés (en définissant le paramètre private).

L'exemple suivant présente le workflow général pour DBMS_PIPE avec la messagerie persistante :

Description de l'image database-pipe-persistent-messaging.eps
Description de l'image database-pipe-persistent-messaging.eps

Les applications existantes utilisant DBMS_PIPE peuvent continuer à fonctionner avec un minimum de modifications. Vous pouvez configurer des applications existantes qui utilisent DBMS_PIPE avec un objet d'informations d'identification et un URI d'emplacement à l'aide d'un déclencheur de connexion ou d'une autre routine d'initialisation. Après avoir défini les informations d'identification DBMS_PIPE et l'URI d'emplacement, aucune autre modification n'est nécessaire pour utiliser la messagerie persistante. Toute utilisation ultérieure du pipeline stocke les messages dans la banque d'objets cloud plutôt que dans la mémoire de base de données. Vous pouvez ainsi modifier la méthode de stockage des messages du stockage d'objets cloud persistant en mémoire, avec un minimum de modifications.

Présentation et fonctionnalités de la messagerie persistante

Fonctionnalités de DBMS_PIPE utilisant la messagerie persistante :

  • Les messages peuvent être envoyés et extraits sur plusieurs instances Autonomous Database de la même région ou de plusieurs régions.

  • Les messages persistants doivent être écrits ou lus par un seul processus. Cela évite les incohérences de contenu de message dues à des écritures et des lectures simultanées. A l'aide d'un canal de messages persistant, DBMS_PIPE n'autorise qu'une seule opération, l'envoi d'un message ou d'un message de réception à être actif à un moment donné. Toutefois, si une opération n'est pas possible en raison d'une opération en cours, le processus réessaie régulièrement jusqu'à ce que la valeur timeout soit atteinte.

  • DBMS_PIPE utilise DBMS_CLOUD pour accéder à la banque d'objets cloud. Les messages peuvent être stockés dans n'importe quelle banque d'objets cloud prise en charge. Pour plus d'informations, reportez-vous à DBMS_CLOUD Formats d'URI.

  • DBMS_PIPE utilise DBMS_CLOUD pour accéder à la banque d'objets cloud et tous les types d'informations d'identification pris en charge sont disponibles :

DBMS_PIPE Autorisation et sécurité des privilèges

Les procédures DBMS_PIPE sont exécutées avec les droits de l'appelant. Les canaux privés appartiennent à l'utilisateur actuel et un canal privé créé par un utilisateur ne peut être utilisé que par le même utilisateur. Cela s'applique à la fois aux canaux en mémoire et aux canaux de messagerie persistants où les messages sont stockés dans la banque d'objets cloud. L'envoi et la réception de messages s'exécutent dans le schéma de l'appelant.

A l'aide de canaux privés, où les messages sont stockés dans la banque d'objets cloud, un objet d'informations d'identification est requis pour l'authentification avec la banque d'objets cloud identifiée par le paramètre location_uri. L'utilisateur appelant doit disposer du privilège EXECUTE sur l'objet d'informations d'identification indiqué avec le paramètre credential_name utilisé pour accéder à la banque d'objets.

Pour utiliser un canal public, l'utilisateur, session de base de données, doit disposer du privilège d'exécution sur DBMS_PIPE. Pour un canal public utilisant la messagerie persistante et stockant des messages vers la banque d'objets cloud, l'utilisateur et la session de base de données doivent disposer du privilège d'exécution sur DBMS_CLOUD et du privilège d'exécution sur l'objet d'informations d'identification (ou vous pouvez créer un objet d'informations d'identification autorisé à accéder à l'URI d'emplacement contenant le message).

DBMS_PIPE Limitation

Le package DBMS_PIPE ne prend pas en charge l'envoi de messages entre des bases de données qui utilisent des jeux de caractères différents. Par exemple, si vous disposez d'une instance Autonomous Database qui utilise AL32UTF8 et d'une autre instance qui utilise WE8MSWIN1252, vous ne pouvez pas envoyer de messages avec DBMS_PIPE entre ces deux bases de données. Dans ce cas, le système génère l'erreur ORA-12704 si vous tentez d'envoyer des messages avec DBMS_PIPE entre ces deux bases de données.

Pour plus d'informations sur le choix d'un jeu de caractères pour Autonomous Database.

Créer un tuyau persistant explicite et envoyer un message

Décrit les étapes de création d'un tuyau persistant avec un nom de tuyau spécifié (tuyau explicite).

  1. Stockez vos informations d'identification de banque d'objets à l'aide de la procédure DBMS_CLOUD.CREATE_CREDENTIAL. Exemples :
    BEGIN
      DBMS_CLOUD.CREATE_CREDENTIAL(
        credential_name => 'my_persistent_pipe_cred',
        username => 'adb_user@example.com',
        password => 'password'
      );
    END;
    /

    Cette opération stocke les informations d'identification dans la base de données dans un format crypté. Vous pouvez utiliser n'importe quel nom d'informations d'identification. Cette étape est requise une seule fois, sauf si les informations d'identification de banque d'objets changent. Une fois les informations d'identification stockées, vous pouvez utiliser le même nom d'informations d'identification pour accéder à la banque d'objets cloud afin d'envoyer et de recevoir des messages avec DBMS_PIPE.

    Pour obtenir des informations détaillées sur les paramètres, reportez-vous à Procédure CREATE_CREDENTIAL. Pour Oracle Cloud Infrastructure Object Storage, les informations d'identification doivent utiliser l'authentification Oracle Cloud Infrastructure native.

    La création d'informations d'identification pour accéder à Oracle Cloud Infrastructure Object Storage n'est pas requise si vous activez les informations d'identification de principal de ressource. Pour plus d'informations, reportez-vous à Utilisation du principal de ressource pour accéder aux ressources Oracle Cloud Infrastructure.

    Remarque

    Certains outils tels que SQL*Plus et SQL Developer utilisent l'arrondi (&) comme caractère spécial. Si votre mot de passe comporte une esperluette, utilisez la commande SET DEFINE OFF dans ces outils comme indiqué dans l'exemple pour désactiver le caractère spécial et créer les informations d'identification correctement.
  2. Créez un canal explicite pour envoyer et extraire des messages. Par exemple, créez un pipeline nommé ORDER_PIPE.
    DECLARE
      r_status INTEGER;
    BEGIN
        r_status := DBMS_PIPE.CREATE_PIPE(pipename => 'ORDER_PIPE');
    END;
    /

    Pour plus d'informations, reportez-vous à CREATE_PIPE Fonction.

  3. Vérifiez que le pipeline est créé.
    SELECT ownerid, name, type FROM v$db_pipes 
           WHERE name = 'ORDER_PIPE';
    OWNERID NAME       TYPE    
    ------- ---------- ------- 
         80 ORDER_PIPE PRIVATE 
  4. Utilisez les procédures DBMS_PIPE pour définir les informations d'identification d'accès et l'URI d'emplacement par défaut afin de stocker les messages persistants dans la banque d'objets cloud.
    BEGIN
        DBMS_PIPE.SET_CREDENTIAL_NAME('my_persistent_pipe_cred');
        DBMS_PIPE.SET_LOCATION_URI('https://objectstorage.us-phoenix-1.oraclecloud.com/n/namespace-string/b/bucketname1/'); 
    END;
    /

    Ces procédures définissent le nom des informations d'identification par défaut et l'URI d'emplacement par défaut à utiliser avec les procédures DBMS_PIPE.

    Si vous utilisez Oracle Cloud Infrastructure Object Storage pour stocker des messages, vous pouvez utiliser des URI natifs Oracle Cloud Infrastructure ou des URI Swift. Cependant, l'URI d'emplacement et les informations d'identification doivent correspondre au type suivant :

    • Si vous utilisez un format d'URI natif pour accéder à Oracle Cloud Infrastructure Object Storage, vous devez utiliser l'authentification des clés de signature Oracle Cloud Infrastructure natives dans l'objet d'informations d'identification.

    • Si vous utilisez le format d'URI Swift pour accéder à Oracle Cloud Infrastructure Object Storage, vous devez utiliser une authentification par jeton d'authentification dans l'objet d'informations d'identification.

    Pour plus d'informations, reportez-vous à Procédure SET_CREDENTIAL_NAME et à Procédure SET_LOCATION_URI.

  5. Emballez et envoyez un message sur le tuyau.
    DECLARE
      l_result INTEGER;
      l_date   DATE;
    BEGIN
        l_date := sysdate;
        DBMS_PIPE.PACK_MESSAGE(l_date);         -- date of order
        DBMS_PIPE.PACK_MESSAGE('C123');         -- order number
        DBMS_PIPE.PACK_MESSAGE(5);              -- number of items in order
        DBMS_PIPE.PACK_MESSAGE('Printers');     -- type of item in order
    
     
        l_result := DBMS_PIPE.SEND_MESSAGE(
                        pipename => 'ORDER_PIPE',
                        credential_name => DBMS_PIPE.GET_CREDENTIAL_NAME,
                        location_uri => DBMS_PIPE.GET_LOCATION_URI);
         
        IF l_result = 0 THEN
            DBMS_OUTPUT.put_line('DBMS_PIPE sent order successfully');
        END IF;
     
    END;
    /

    Pour plus d'informations, reportez-vous aux sections PACK_MESSAGE Procedures et SEND_MESSAGE Function.

Extraire un message persistant sur la même base de données

Décrit les étapes d'extraction d'un message persistant à partir d'un canal explicite sur la même instance Autonomous Database (instance où le message a été envoyé).

Sur une instance Autonomous Database, vous pouvez recevoir des messages envoyés à un canal à partir d'une autre session. Les procédures DBMS_PIPE sont des procédures avec droits de l'appelant et exécutées en tant qu'utilisateur appelé en cours.

Les canaux privés appartiennent à l'utilisateur actuel qui crée le canal. Les canaux privés ne sont accessibles que par le même utilisateur qui a créé le canal. Cela s'applique aux canaux utilisant des messages en mémoire et aux canaux utilisant des messages persistants avec des messages stockés dans la banque d'objets cloud.

Les canaux publics sont accessibles par toute session de base de données disposant du privilège d'exécution sur DBMS_PIPE. Cela s'applique aux canaux utilisant des messages en mémoire et aux canaux utilisant des messages persistants avec des messages stockés dans la banque d'objets cloud.

  1. Vérifiez que le pipeline est créé.
    SELECT ownerid, name, type FROM v$db_pipes 
           WHERE name = 'ORDER_PIPE';
    
    OWNERID NAME       TYPE    
    ------- ---------- ------- 
         80 ORDER_PIPE PRIVATE 

    Lorsque vous êtes sur la même instance Autonomous Database et que le pipeline existe, vous n'avez pas besoin d'exécuter DBMS_PIPE.CREATE_PIPE avant de recevoir un message. Cela s'applique lorsque le canal a été créé sur la même instance, comme indiqué dans Création d'un canal persistant explicite et envoi d'un message.

  2. Recevez un message du pipe.
    DECLARE
        message1  DATE;
        message2  VARCHAR2(100);
        message3  INTEGER;
        message4  VARCHAR2(100);
        l_result  INTEGER;
    
    BEGIN
    
        DBMS_PIPE.SET_CREDENTIAL_NAME('my_persistent_pipe_cred');
        DBMS_PIPE.SET_LOCATION_URI('https://objectstorage.us-phoenix-1.oraclecloud.com/n/namespace-string/b/bucketname1/'); 
        l_result := DBMS_PIPE.RECEIVE_MESSAGE (
                      pipename => 'ORDER_PIPE',
                      timeout  => DBMS_PIPE.MAXWAIT,
                      credential_name => DBMS_PIPE.GET_CREDENTIAL_NAME,
                      location_uri => DBMS_PIPE.GET_LOCATION_URI);
     
        IF l_result = 0 THEN
            DBMS_PIPE.unpack_message(message1);
            DBMS_PIPE.unpack_message(message2);
            DBMS_PIPE.unpack_message(message3);
            DBMS_PIPE.unpack_message(message4);
     
            DBMS_OUTPUT.put_line('Order Received Successfully On: ' || TO_CHAR(sysdate, 'dd-mm-yyyy hh24:mi:ss'));
            DBMS_OUTPUT.put_line('Date of Order: ' || message1);
            DBMS_OUTPUT.put_line('Order Number: ' || message2);
            DBMS_OUTPUT.put_line('Number of Items In Order: ' || message3);
            DBMS_OUTPUT.put_line('Item Type in Order: ' || message4);
        END IF;
     
    END;
    /

    Lorsque vous êtes sur la même instance Autonomous Database, les informations d'identification existent déjà et vous n'avez pas besoin d'exécuter DBMS_CLOUD.CREATE_CREDENTIAL pour recevoir un message. Cela s'applique lorsque le canal a été créé sur la même instance, comme indiqué dans Création d'un canal persistant explicite et envoi d'un message.

Pour plus d'informations, reportez-vous à Procédure SET_CREDENTIAL_NAME et à Procédure SET_LOCATION_URI.

Pour plus d'informations, reportez-vous à RECEIVE_MESSAGE Fonction.

Extraire un message persistant en créant un tuyau sur une autre base de données

Décrit les étapes d'extraction d'un message persistant stocké dans la banque d'objets cloud avec un canal explicite sur une instance Autonomous Database différente de l'instance qui a envoyé le message.

  1. Stockez vos informations d'identification de banque d'objets à l'aide de la procédure DBMS_CLOUD.CREATE_CREDENTIAL. Exemples :
    BEGIN
      DBMS_CLOUD.CREATE_CREDENTIAL(
        credential_name => 'my_persistent_pipe_cred',
        username => 'adb_user@example.com',
        password => 'password'
      );
    END;
    /

    Cette opération stocke les informations d'identification dans la base de données dans un format crypté. Vous pouvez utiliser n'importe quel nom d'informations d'identification. Cette étape est requise une seule fois, sauf si les informations d'identification de banque d'objets changent. Une fois que vous avez stocké les informations d'identification, vous pouvez utiliser le même nom d'informations d'identification pour accéder à la banque d'objets cloud afin d'envoyer et de recevoir des messages avec DBMS_PIPE.

    Pour obtenir des informations détaillées sur les paramètres, reportez-vous à Procédure CREATE_CREDENTIAL.

    La création d'informations d'identification pour accéder à Oracle Cloud Infrastructure Object Storage n'est pas requise si vous activez les informations d'identification de principal de ressource. Pour plus d'informations, reportez-vous à Utilisation du principal de ressource pour accéder aux ressources Oracle Cloud Infrastructure.

    Remarque

    Certains outils tels que SQL*Plus et SQL Developer utilisent l'arrondi (&) comme caractère spécial. Si votre mot de passe comporte une esperluette, utilisez la commande SET DEFINE OFF dans ces outils comme indiqué dans l'exemple pour désactiver le caractère spécial et créer les informations d'identification correctement.
  2. Créez un canal explicite portant le même nom que le canal qui a envoyé le message. Par exemple, créez un pipeline nommé ORDER_PIPE.
    DECLARE
      r_status INTEGER;
    BEGIN
        r_status := DBMS_PIPE.CREATE_PIPE(pipename => 'ORDER_PIPE');
    END;
    /

    Reportez-vous à Fonction CREATE_PIPE.

  3. Vérifiez que le pipeline est créé.
    SELECT ownerid, name, type FROM v$db_pipes 
           WHERE name = 'ORDER_PIPE';
    
    OWNERID NAME       TYPE    
    ------- ---------- ------- 
         80 ORDER_PIPE PRIVATE 
  4. Utilisez les procédures DBMS_PIPE afin de définir les informations d'identification d'accès et l'URI d'emplacement par défaut pour la banque d'objets afin que DBMS_PIPE puisse accéder au message persistant.
    BEGIN
        DBMS_PIPE.SET_CREDENTIAL_NAME('my_persistent_pipe_cred');
        DBMS_PIPE.SET_LOCATION_URI('https://objectstorage.us-phoenix-1.oraclecloud.com/n/namespace-string/b/bucketname1/'); 
    END;
    /

    Ces procédures définissent le nom des informations d'identification par défaut et l'URI d'emplacement par défaut à utiliser avec les procédures DBMS_PIPE.

    Si vous utilisez Oracle Cloud Infrastructure Object Storage pour stocker des messages, vous pouvez utiliser des URI natifs Oracle Cloud Infrastructure ou des URI Swift. Cependant, l'URI d'emplacement et les informations d'identification doivent correspondre au type suivant :

    • Si vous utilisez un format d'URI natif pour accéder à Oracle Cloud Infrastructure Object Storage, vous devez utiliser l'authentification des clés de signature Oracle Cloud Infrastructure natives dans l'objet d'informations d'identification.

    • Si vous utilisez le format d'URI Swift pour accéder à Oracle Cloud Infrastructure Object Storage, vous devez utiliser une authentification par jeton d'authentification dans l'objet d'informations d'identification.

    Pour plus d'informations, reportez-vous à Procédure SET_CREDENTIAL_NAME et à Procédure SET_LOCATION_URI.

  5. Recevez un message du canal persistant.
    DECLARE
        message1  DATE;
        message2  VARCHAR2(100);
        message3  INTEGER;
        message4  VARCHAR2(100);
        l_result  INTEGER;
    
    BEGIN
    
        DBMS_PIPE.SET_CREDENTIAL_NAME('my_persistent_pipe_cred');
        DBMS_PIPE.SET_LOCATION_URI('https://objectstorage.us-phoenix-1.oraclecloud.com/n/namespace-string/b/bucketname1/'); 
        l_result := DBMS_PIPE.RECEIVE_MESSAGE (
                      pipename => 'ORDER_PIPE',
                      timeout  => DBMS_PIPE.MAXWAIT,
                      credential_name => DBMS_PIPE.GET_CREDENTIAL_NAME,
                      location_uri => DBMS_PIPE.GET_LOCATION_URI);
     
        IF l_result = 0 THEN
            DBMS_PIPE.unpack_message(message1);
            DBMS_PIPE.unpack_message(message2);
            DBMS_PIPE.unpack_message(message3);
            DBMS_PIPE.unpack_message(message4);
     
            DBMS_OUTPUT.put_line('Order Received Successfully On: ' || TO_CHAR(sysdate, 'dd-mm-yyyy hh24:mi:ss'));
            DBMS_OUTPUT.put_line('Date of Order: ' || message1);
            DBMS_OUTPUT.put_line('Order Number: ' || message2);
            DBMS_OUTPUT.put_line('Number of Items In Order: ' || message3);
            DBMS_OUTPUT.put_line('Item Type in Order: ' || message4);
        END IF;
     
    END;
    /

    Pour plus d'informations, reportez-vous à RECEIVE_MESSAGE Fonction.

Suppression d'un tuyau persistant

Décrit les étapes de suppression d'un tuyau persistant.

Les canaux persistants envoient et reçoivent des messages en stockant les messages dans le stockage d'objet cloud. Utilisez DBMS_PIPE.REMOVE_PIPE pour enlever un canal persistant sur une instance Autonomous Database.

  1. Appelez la fonction DBMS_PIPE.REMOVE_PIPE pour enlever un pipeline.
    DECLARE
       l_result  INTEGER;
    BEGIN
         l_result := DBMS_PIPE.REMOVE_PIPE('ORDER_PIPE');
    END;
    /

    La fonction REMOVE_PIPE enlève le canal de l'instance Autonomous Database où elle est exécutée. Cependant, REMOVE_PIPE n'affecte pas les autres instances Autonomous Database avec un canal du même nom qui utilise le même URI d'emplacement.

  2. Sur l'instance Autonomous Database, lorsque vous avez exécuté DBMS_PIPE.REMOVE_PIPE, vérifiez que le pipeline est enlevé.
    SELECT ownerid, name, type FROM v$db_pipes 
           WHERE name = 'ORDER_PIPE';
    
    No rows selected