將永久訊息與儲存在雲端物件存放區中的訊息搭配使用
DBMS_PIPE 套裝程式在自治式 AI 資料庫上有擴充的功能,可支援將訊息儲存在雲端物件存放區中的持續性訊息傳遞。
關於使用 DBMS_PIPE 的持續性訊息
使用 DBMS_PIPE 的永久訊息可讓一或多個資料庫階段作業在相同區域或跨區域與儲存在「雲端物件存放區」中的訊息進行通訊。
DBMS_PIPE 中的永久訊息:
-
允許您傳送與擷取非常大的訊息。
-
支援傳送大量管道訊息。
-
支援在單一資料庫內跨多個資料庫和不同區域的資料庫傳送和接收訊息。
-
支援使用相同雲端物件存放區位置 URI 的多個管線。
永久訊息管道可在任何支援的 DBMS_PIPE 類型中建立:
-
隱含管:使用
DBMS_PIPE.SEND_MESSAGE函數以不明的管路名稱傳送訊息時,會自動建立。 -
明確管線:使用
DBMS_PIPE.CREATE_PIPE函數與使用者指定的管線名稱建立。 -
公用管線:任何具備
DBMS_PIPE套裝程式之EXECUTE權限的使用者都可以存取。 -
專用管線:具有與管線建立者相同之使用者的階段作業可以存取。
注意:Oracle 建議您先建立明確的管道,再傳送或接收含有永久訊息的訊息。使用 DBMS_PIPE.CREATE_PIPE 建立明確的管道可確保使用您想要的存取權限 (透過設定 private 參數) 來建立管道。
下列顯示具有永久訊息之 DBMS_PIPE 的一般工作流程:
database-pipe-persistent-messaging.svg 圖解描述
使用 DBMS_PIPE 的現有應用程式可繼續以最少的變更運作。您可以使用登入觸發程式或使用其他初始化常式,將使用 DBMS_PIPE 的現有應用程式與證明資料物件和位置 URI 搭配使用。設定 DBMS_PIPE 證明資料和位置 URI 之後,不需要進行其他變更即可使用永久訊息。所有後續使用管道都會將訊息儲存在「雲端物件存放區」中,而不是儲存在資料庫記憶體中。這可讓您在進行最少變更的情況下,將訊息的儲存方法從記憶體內變更為永久雲端物件儲存。
永久訊息傳遞概要和功能
使用永久訊息傳遞的 DBMS_PIPE 功能:
-
您可以在相同區域或跨區域的多個自治式 AI 資料庫執行處理之間傳送和擷取訊息。
-
永久訊息可以只由一個處理作業來寫入或讀取。這可避免因並行讀取和寫入而導致訊息內容不一致。
DBMS_PIPE只允許在指定的時間執行一項作業、傳送訊息或接收訊息,以及這些作業受到鎖定機制的保護。不過,如果因為進行中的作業而無法進行作業,則處理作業會定期重試,直到達到timeout值為止。 -
DBMS_PIPE使用DBMS_CLOUD來存取「雲端物件存放區」。訊息可以儲存在任何支援的雲端物件存放區中。如需詳細資訊,請參閱雲端物件儲存 URI 格式。 -
DBMS_PIPE使用DBMS_CLOUD存取「雲端物件存放區」,並提供所有支援的證明資料類型:DBMS_CLOUD.CREATE_CREDENTIAL:請參閱 CREATE_CREDENTIAL 程序以瞭解詳細資訊。
DBMS_PIPE 權限授權與安全性
DBMS_PIPE 程序會以呼叫者的權限執行。專用管線是目前使用者所擁有,而使用者所建立的專用管線只能由同一使用者使用。這適用於將訊息儲存到雲端物件存放區的記憶體內管和永久訊息傳遞管。傳送與接收訊息會在呼叫者的綱要中執行。
使用儲存訊息至「雲端物件存放區」的專用管線,進行 location_uri 參數識別之「雲端物件存放區」的認證時,必須要有證明資料物件。呼叫使用者的證明資料物件必須具備 credential_name 參數 (用來存取物件存放區) 所指定之 EXECUTE 權限。
若要使用公用管道,使用者、資料庫階段作業必須具有 DBMS_PIPE 的執行權限。對於使用永久訊息並將訊息儲存至「雲端物件存放區」的公用管道,使用者、資料庫階段作業必須具有 DBMS_CLOUD 的執行權限,並且對證明資料物件執行權限 (或者您可以建立允許存取包含該訊息之位置 URI 的證明資料物件)。
DBMS_PIPE 限制
DBMS_PIPE 套裝程式不支援在使用不同字元集的資料庫之間傳送訊息。例如,如果您有一個使用 AL32UTF8 的自治式 AI 資料庫執行處理,以及另一個使用 WE8MSWIN1252 的執行處理,您就無法在這兩個資料庫之間傳送含有 DBMS_PIPE 的訊息。在此情況下,如果您嘗試在這兩個資料庫之間傳送含有 DBMS_PIPE 的訊息,系統將會發出 ORA-12704 錯誤。
如需詳細資訊,請參閱自治式 AI 資料庫的字元集選擇。
建立明確的持續性管線並傳送訊息
說明建立具有指定管道名稱 (明確管道) 的永久管道的步驟。
-
使用
DBMS_CLOUD.CREATE_CREDENTIAL程序儲存您的物件存放區證明資料。舉例而言:BEGIN DBMS_CLOUD.CREATE_CREDENTIAL( credential_name => 'my_persistent_pipe_cred', username => 'adb_user@example.com', password => 'password' ); END; /此作業會以加密格式將證明資料儲存在資料庫中。您可以為證明資料名稱使用任何名稱。請注意,除非您的物件存放區證明資料變更,否則此步驟只需要執行一次。儲存證明資料之後,您可以使用相同的證明資料名稱來存取「雲端物件存放區」,以傳送及接收含有
DBMS_PIPE的訊息。如需有關參數的詳細資訊,請參閱 CREATE_CREDENTIAL Procedure 。對於 Oracle Cloud Infrastructure Object Storage,證明資料必須使用原生 Oracle Cloud Infrastructure 認證。
注意:有些工具 (例如 SQL*Plus 和 SQL Developer) 會使用 & 字元 (
&) 作為特殊字元。如果您的密碼中有 & 字元,請在這些工具中使用SET DEFINE OFF命令 (如範例所示),以停用特殊字元並正確建立證明資料。 -
建立明確的管道來傳送和擷取訊息。例如,建立名為
ORDER_PIPE的管。DECLARE r_status INTEGER; BEGIN r_status := DBMS_PIPE.CREATE_PIPE(pipename => 'ORDER_PIPE'); END; /請參閱 CREATE_PIPE 函數瞭解詳細資訊。
-
確認已建立管路。
SELECT ownerid, name, type FROM v$db_pipes WHERE name = 'ORDER_PIPE';OWNERID NAME TYPE ------- ---------- ------- 80 ORDER_PIPE PRIVATE -
使用
DBMS_PIPE程序來設定預設存取證明資料和位置 URI,以將永久訊息儲存至「雲端物件存放區」。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; /這些程序設定用於
DBMS_PIPE程序的預設證明資料名稱和預設位置 URI。如果您使用 Oracle Cloud Infrastructure Object Storage 來儲存訊息,可以使用 Oracle Cloud Infrastructure 原生 URI 或 Swift URI。不過,位置 URI 與憑證的類型必須相符,如下所示:
-
如果您使用原生 URI 格式來存取 Oracle Cloud Infrastructure Object Storage,則必須在證明資料物件中使用原生 Oracle Cloud Infrastructure 簽署金鑰認證。
-
如果您使用 Swift URI 格式存取 Oracle Cloud Infrastructure Object Storage,則必須在證明資料物件中使用認證權杖認證。
請參閱 SET_CREDENTIAL_NAME 程序和 GET_LOCATION_URI 函數瞭解詳細資訊。
-
-
在管道上包裝並傳送訊息。
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; /請參閱 Oracle Database 19c PL/SQL Packages and Types Reference 中的 PACK_MESSAGE Procedures 或 Oracle Database 26ai PL/SQL Packages and Types Reference 和 SEND_MESSAGE Function 以瞭解詳細資訊。
擷取相同資料庫上的永久訊息
描述從相同自治式 AI 資料庫執行處理 (訊息傳送所在的執行處理) 上明確管路擷取永久訊息的步驟。
在「自治式 AI 資料庫」執行處理上,您可以接收從不同階段作業傳送至管路的訊息。DBMS_PIPE 程序是呼叫者的權限程序,並以目前呼叫的使用者身分執行。
專用管是目前建立管路的使用者所擁有。專用管只能由建立管路的同一使用者存取。這適用於使用記憶體內訊息的管線,以及使用永久訊息與儲存在雲端物件存放區中的訊息的管線。
任何具有 DBMS_PIPE 執行權限的資料庫階段作業都可以存取公用管線。這適用於使用記憶體內訊息的管線,以及使用永久訊息與儲存在雲端物件存放區中的訊息的管線。
-
確認已建立管路。
SELECT ownerid, name, type FROM v$db_pipes WHERE name = 'ORDER_PIPE';OWNERID NAME TYPE ------- ---------- ------- 80 ORDER_PIPE PRIVATE當您在相同的「自治式 AI 資料庫」實例且管路存在時,您不需要在收到訊息之前執行
DBMS_PIPE.CREATE_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; /當您在相同的自治式 AI 資料庫執行處理上時,證明資料已經存在,您不需要執行
DBMS_CLOUD.CREATE_CREDENTIAL來接收訊息。如建立明確的永久管路並傳送訊息所示,在相同的執行處理上建立管路時會套用此設定。
請參閱 SET_CREDENTIAL_NAME 程序和 GET_LOCATION_URI 函數瞭解詳細資訊。
請參閱 RECEIVE_MESSAGE 函數瞭解詳細資訊。
在不同的資料庫上建立管線以擷取永久訊息
描述在自治式 AI 資料庫執行處理上使用明確管道擷取儲存在雲端物件存放區中,與傳送訊息之執行處理不同的永久訊息的步驟。
-
使用
DBMS_CLOUD.CREATE_CREDENTIAL程序儲存您的物件存放區證明資料。舉例而言:BEGIN DBMS_CLOUD.CREATE_CREDENTIAL( credential_name => 'my_persistent_pipe_cred', username => 'adb_user@example.com', password => 'password' ); END; /此作業會以加密格式將證明資料儲存在資料庫中。您可以為證明資料名稱使用任何名稱。請注意,除非您的物件存放區證明資料變更,否則此步驟只需要執行一次。儲存證明資料之後,您可以使用相同的證明資料名稱來存取「雲端物件存放區」,以傳送及接收含有
DBMS_PIPE的訊息。如需有關參數的詳細資訊,請參閱 CREATE_CREDENTIAL Procedure 。
注意:有些工具 (例如 SQL*Plus 和 SQL Developer) 會使用 & 字元 (
&) 作為特殊字元。如果您的密碼中有 & 字元,請在這些工具中使用SET DEFINE OFF命令 (如範例所示),以停用特殊字元並正確建立證明資料。 -
建立與傳送訊息之管道名稱相同的明確管道。例如,建立名為
ORDER_PIPE的管。DECLARE r_status INTEGER; BEGIN r_status := DBMS_PIPE.CREATE_PIPE(pipename => 'ORDER_PIPE'); END; /請參閱 CREATE_PIPE 函數。
-
確認已建立管。
SELECT ownerid, name, type FROM v$db_pipes WHERE name = 'ORDER_PIPE';OWNERID NAME TYPE ------- ---------- ------- 80 ORDER_PIPE PRIVATE -
使用
DBMS_PIPE程序來設定「物件存放區」的預設存取證明資料和位置 URI,讓DBMS_PIPE可以存取永久訊息。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; /這些程序設定用於
DBMS_PIPE程序的預設證明資料名稱和預設位置 URI。如果您使用 Oracle Cloud Infrastructure Object Storage 來儲存訊息,可以使用 Oracle Cloud Infrastructure 原生 URI 或 Swift URI。不過,位置 URI 與憑證的類型必須相符,如下所示:
-
如果您使用原生 URI 格式來存取 Oracle Cloud Infrastructure Object Storage,則必須在證明資料物件中使用原生 Oracle Cloud Infrastructure 簽署金鑰認證。
-
如果您使用 Swift URI 格式存取 Oracle Cloud Infrastructure Object Storage,則必須在證明資料物件中使用認證權杖認證。
請參閱 SET_CREDENTIAL_NAME 程序和 GET_LOCATION_URI 函數瞭解詳細資訊。
-
-
接收來自永久管路的訊息。
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; /請參閱 RECEIVE_MESSAGE 函數瞭解詳細資訊。
移除持續的導管
描述移除永久管的步驟。
永久管線會透過在雲端物件存放區中儲存訊息來傳送和接收訊息。使用 DBMS_PIPE.REMOVE_PIPE 可移除自治式 AI 資料庫執行處理上的永久管路。
-
呼叫
DBMS_PIPE.REMOVE_PIPE函數以移除管道。DECLARE l_result INTEGER; BEGIN l_result := DBMS_PIPE.REMOVE_PIPE('ORDER_PIPE'); END; /REMOVE_PIPE函數會將管從執行處的「自治式 AI 資料庫」實例中移除,但REMOVE_PIPE不會影響其他具有相同名稱且使用相同位置 URI 之管路的「自治式 AI 資料庫」實例。 -
在「自治式 AI 資料庫」實例上執行
DBMS_PIPE.REMOVE_PIPE,確認已移除該管路。SELECT ownerid, name, type FROM v$db_pipes WHERE name = 'ORDER_PIPE';No rows selected