圖 11. 選擇將信息發送至的完整倉儲庫隊列管理器

最後需要在兩個部分倉儲庫隊列管理器上定義各自的集群隊列 TEST_QUEUE。如圖 12 所示,這裡將缺省綁定類型設為不固定。
圖 12.在兩個部分倉儲庫隊列管理器上定義集群隊列

創建完兩個集群隊列後,可以在兩個完整倉儲庫隊列管理器 FULL_QM1 和 FULL_QM2 上看到兩個集群隊列 TEST_QUEUE。如圖 13 所示。
圖 13. 創建成功的兩個集群隊列

在之前顯示建立的集群拓撲圖中提到,本文只顯示建立 PART_QM1 到完整倉儲庫隊列管理器 FULL_QM1 的發送通道。而 PART_QM1 到 FULL_QM2 的發送通道是集群自動建立的。因此,在 PART_QM1 的集群發送通道中可以看到兩個發送通道,如圖 14 所示,其中 TO.FULL_QM1 發送通道是通過 MQ explorer 顯式創建的,定義類型為自動顯示集群發送方。而 TO.FULL_QM2 發送通道是系統自動創建的,定義類型為自動集群發送方。
圖 14. 隊列管理器 PART_QM1 的集群發送通道

________________________________________
使用示例應用程序演示 MQ 集群的負載平衡效果
創建完一個簡單的集群後,通過配置可以實現群集的負載均衡效果。本文在集群中定義了集群隊列 TEST_QUEUE 的兩個同名隊列實例,每個隊列實例在不同的隊列管理器上。當應用程序把消息發送到該集群隊列時,MQ 使用負載平衡算法決定消息實際發送哪個隊列管理器。
示例程序首先連接到一個完整倉儲庫隊列管理器 FULL_QM1,將綁定的類型設定為 MQOO_BIND_AS_Q_DEF,然後將五個消息放入集群隊列 TEST_QUEUE 中,如清單 8 所示。綁定類型設定為 MQOO_BIND_AS_Q_DEF 是把連接到隊列的綁定類型指定為隊列缺省的綁定類型,本例中為不固定,是在創建集群隊列時,通過設置缺省綁定類型指定的,如圖 12 所示。
清單 8. 將消息放入集群隊列的示例程序
public class ClusterPut {
private static final String HOSTNAME = “127.0.0.1”;
private static final int PORT = 5000;
private static final String CHANNEL = “SYSTEM.DEF.SVRCONN”;
private static final int CCSID = 1208;
//we can also specify FULL_QM2 as queue manager
private static final String QM_NAME = “FULL_QM1”;
private static final String Q_NAME = “TEST_QUEUE”;
public static void main(String[] args) throws Exception {
// Set up WebSphere MQ environment
MQEnvironment.hostname = HOSTNAME;
MQEnvironment.port = PORT;
MQEnvironment.channel = CHANNEL;
MQEnvironment.CCSID = CCSID;
// Create a connection to the QueueManager
MQQueueManager qMgr = new MQQueueManager(QM_NAME);
// Specify the queue that we wish to open and the open options.
//MQOO_BIND_AS_Q_DEF option is specified here, so bind type is determined by
//default queue bind type
// We can also specify MQOO_BIND_ON_OPEN or MQOO_BIND_NOT_FIXED to cover
//default queue bind type
MQQueue queue = qMgr.accessQueue(Q_NAME, MQConstants.MQOO_BIND_AS_Q_DEF
+ MQConstants.MQOO_OUTPUT);
// Define a simple WebSphere MQ Message and write some text in UTF8 format
MQMessage msg = new MQMessage();
msg.writeUTF(“Hello World!”);
// Put five messages to the cluster queue with default put message options
queue.put(msg, new MQPutMessageOptions());
queue.put(msg, new MQPutMessageOptions());
queue.put(msg, new MQPutMessageOptions());
queue.put(msg, new MQPutMessageOptions());
queue.put(msg, new MQPutMessageOptions());
// Close the queue and disconnect from the QueueManager
queue.close();
qMgr.disconnect();
}
}
指定集群隊列的缺省綁定類型為不固定,程序第一次運行後,五條消息分別放入部分倉儲庫隊列管理器 PART_QM1 和 PART_QM2 的 TEST_QUEUE 隊列中。如果不指定隊列等級和優先級,程序運行後,在 PART_QM1 的 TEST_QUEUE 隊列中有三條消息,在 PART_QM2 的 TEST_QUEUE 隊列中有兩條消息。
當集群隊列的缺省綁定類型為打開時,如圖 15 所示,程序第一次運行後,五條消息都放入 PART_QM1 的 TEST_QUEUE 隊列中。程序第二次運行後,五條消息都放入 PART_QM2 的 TEST_QUEUE 隊列中。指定為打開時,相當於在程序打開 TEST_QUEUE 集群隊列時,就決定要使用哪一個部分倉儲庫隊列管理器上的隊列,之後,在程序斷開與隊列管理器的連接前,所有的消息都放到那個隊列里。
圖 15. 隊列的缺省綁定類型

如果掛起 PART_QM1,則無論綁定類型指定為哪個選項,所有的消息都將發送到 PART_QM2 上的集群隊列里。
accessQueue 函數還有另外兩個選項 MQOO_BIND_NOT_FIXED 和 MQOO_BIND_ON_OPEN,缺省值為 MQOO_BIND_ON_OPEN。如果指定為 MQOO_BIND_ON_OPEN,消息只發送給某一隊列實例,相當於之前把集群隊列的缺省綁定類型設定為打開時。在程序中指定綁定的類型為 MQOO_BIND_NOT_FIXED 或者 MQOO_BIND_ON_OPEN 會覆蓋集群隊列的缺省綁定類型。
________________________________________
使用集群隊列時需要注意的幾點
如果對消息的邏輯處理有要求,或者對消息的處理順序有要求,這時需要使用 MQOO_BIND_ON_OPEN 選項。例如,程序 A 向某個集群隊列發送兩條相互關聯的消息,一條消息包含元數據,另一條消息包含實際數據內容,它們之間通過 groupId 相互聯繫。並且該集群隊列在集群的兩個隊列管理器上各有一個同名集群隊列實例。現在程序 B 需要從集群隊列中取出相互關聯的兩條消息進行處理,如果這兩條消息分別被發送到了兩個不同的集群隊列實例中,則程序 B 打開一個集群隊列實例後,無法通過其中一條消息的 groupId,在同一個集群隊列實例中找到另一條消息。要解決這個問題,可以將相互關聯的消息發送到同一個集群隊列實例上。在程序 A 將消息放入集群隊列時,需要指定 MQOO_BIND_ON_OPEN 選項。
集群只在消息進入時實現負載平衡,一旦消息進入某個隊列管理器上的集群隊列,它就只能由該隊列管理器處理。如果在消息被處理完之前,該隊列管理器被掛起或 者發生故障,已經進入該集群隊列的消息將不能被處理。即其他隊列管理器無法處理該隊列管理器上同名的集群隊列實例。這一點和 z/OS 的共享隊列不同。在 z/OS 平台上,如果使用共享隊列,多個隊列管理器使用的是同一個隊列實例,即使某個隊列管理器不工作,其他的隊列管理器可以處理該共享隊列上的消息。
________________________________________
以下文章點擊率最高
Loading…