Service Broker基础应用(下)

数据库 SQL Server
在上篇《SQL Server 2008中Service Broker基础应用(上)》中,简要介绍了Service Broker的一般步骤,本文继续介绍Service Broker的设置会话优先级,存储过程中实现。

导读:在上篇《SQL Server 2008中Service Broker基础应用(上)》中,简要介绍了Service Broker的一般步骤,本文继续介绍Service Broker的设置会话优先级,存储过程中实现。

一、Service Broker的设置会话优先级

自SQL Server 2008起,对非常活跃的Service Broker应用程序,提供了设置优先级的命令CREATE BROKER PRIORITY(http://msdn.microsoft.com/en-us/library/bb934170.aspx)。通过该命令,可以设置从1至10共10个等级的颗粒度来调试会话的优先级,默认为5。在此之前,你必须得首先打开HONOR_BROKER_PRIORITY开关。

-- 设置会话优先级 --启用会话优先级选项 ALTER DATABASE BookStore SET HONOR_BROKER_PRIORITY ON --启用会话优先级选项 ALTER DATABASE BOOKDistribution SET HONOR_BROKER_PRIORITY ON --查看设置结果 SELECT name, is_honor_broker_priority_on FROM sys.databases WHERE name IN ('BookStore', 'BookDistribution') /* name is_honor_broker_priority_on BookStore 1 BookDistribution 1 */ USE BookStore GO CREATE BROKER PRIORITY Conv_Priority_BookOrderContract_BookOrderService FOR CONVERSATION SET (CONTRACT_NAME = [//SackConsulting/BookOrderContract],--特定的契约 LOCAL_SERVICE_NAME = [//SackConsulting/BookOrderService],--本地服务 REMOTE_SERVICE_NAME = ANY,--远程服务为ANY,即Service Broker端点的任何相关服务 PRIORITY_LEVEL = 10)--设置优先级为10 
  • 1.
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.
  • 7.
  • 8.
  • 9.
  • 10.
  • 11.
  • 12.
  • 13.
  • 14.
  • 15.
  • 16.
  • 17.
  • 18.
  • 19.
  • 20.
  • 21.
  • 22.
  • 23.
  • 24.
  • 25.
  • 26.
  • 27.
  • 28.
  • 29.

通过sys.conversation_priorities目录视图,查询优先级

SELECT name, priority, service_contract_id, local_service_id,remote_service_name FROM sys.conversation_priorities cp /* name priority service_contract_id local_service_id remote_service_name Conv_Priority_BookOrderContract_BookOrderService 10 65536 65536 NULL */
  • 1.
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.
  • 7.
  • 8.

如果你希望包含服务和契约名称,可以将服务和从sys.conversation_priorities(http://msdn.microsoft.com/zh-cn/library/bb895280%28v=sql.100%29.aspx)返回的契约ID与sys.service_contracts(http://msdn.microsoft.com/en-us/library/ms184378.aspx),sys.services(http://msdn.microsoft.com/en-us/library/ms174429.aspx)目录视图关联起来。

USE BookDistribution GO --创建目标服务的优先级,与发起方的优先级保持一致, --以使会话的优先级设置覆盖整个会话的生命周期 CREATE BROKER PRIORITY Conv_Priority_BookOrderContract_BookDistributionService FOR CONVERSATION SET (CONTRACT_NAME = [//SackConsulting/BookOrderContract], LOCAL_SERVICE_NAME = [//SackConsulting/BookDistributionService], REMOTE_SERVICE_NAME = ANY, PRIORITY_LEVEL = 10) USE BookStore GO ALTER BROKER PRIORITY Conv_Priority_BookOrderContract_BookOrderService FOR CONVERSATION SET (REMOTE_SERVICE_NAME = '//SackConsulting/BookDistributionService') --修改远程服务名称 ALTER BROKER PRIORITY Conv_Priority_BookOrderContract_BookOrderService FOR CONVERSATION SET (PRIORITY_LEVEL = 9) --设置优先级 --删除优先级设置 DROP BROKER PRIORITY Conv_Priority_BookOrderContract_BookOrderService
  • 1.
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.
  • 7.
  • 8.
  • 9.
  • 10.
  • 11.
  • 12.
  • 13.
  • 14.
  • 15.
  • 16.
  • 17.
  • 18.
  • 19.
  • 20.
  • 21.
  • 22.
  • 23.
  • 24.
  • 25.
  • 26.

二、Service Broker的存储过程实现

在上文中,我们使用的临时T-SQL来演示Service broker的步骤,事实上, 我们完全可以通过存储过程或外部应用程序自动激活并处理队列中的消息。使用Create Queue(http://msdn.microsoft.com/en-us/library/ms190495.aspx)和Alter Queue(http://msdn.microsoft.com/en-us/library/ms189529.aspx)选项,也可以指定可以激活并处理在同一队列中传入的消息的、同时执行的相同服务程序的数量。

继续上文的示例:

-- Creating the Bookstore Stored Procedure USE BookDistribution GO CREATE PROCEDURE dbo.usp_SB_ReceiveOrders AS DECLARE @Conv_Handler uniqueidentifier DECLARE @Conv_Group uniqueidentifier DECLARE @OrderMsg xml DECLARE @TextResponseMsg varchar(8000) DECLARE @ResponseMsg xml DECLARE @Message_Type_Name nvarchar(256); DECLARE @OrderID int; -- XACT_ABORT automatically rolls back the transaction when a runtime error occurs SET XACT_ABORT ON BEGIN TRAN; RECEIVE TOP(1) @OrderMsg = message_body, @Conv_Handler = conversation_handle, @Conv_Group = conversation_group_id, @Message_Type_Name = message_type_name FROM dbo.BookDistributionQueue; IF @Message_Type_Name = '//SackConsulting/SendBookOrder' BEGIN INSERT dbo.BookOrderReceived (conversation_handle, conversation_group_id, message_body) VALUES (@Conv_Handler,@Conv_Group, @OrderMsg ) SELECT @OrderID = @OrderMsg.value('(/order/@id)[1]', 'int' ) SELECT @TextResponseMsg = '<orderreceived id= "' + CAST(@OrderID as varchar(10)) + '"/>'; SELECT @ResponseMsg = CAST(@TextResponseMsg as xml); SEND ON CONVERSATION @Conv_Handler MESSAGE TYPE [//SackConsulting/BookOrderReceived] (@ResponseMsg ); END IF @Message_Type_Name = 'http://schemas.microsoft.com/SQL/ServiceBroker/EndDialog' BEGIN END CONVERSATION @Conv_Handler; END COMMIT TRAN GO
  • 1.
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.
  • 7.
  • 8.
  • 9.
  • 10.
  • 11.
  • 12.
  • 13.
  • 14.
  • 15.
  • 16.
  • 17.
  • 18.
  • 19.
  • 20.
  • 21.
  • 22.
  • 23.
  • 24.
  • 25.
  • 26.
  • 27.
  • 28.
  • 29.
  • 30.
  • 31.
  • 32.
  • 33.
  • 34.
  • 35.
  • 36.
  • 37.
  • 38.
  • 39.
  • 40.
  • 41.
  • 42.
  • 43.
  • 44.
  • 45.
  • 46.
  • 47.
  • 48.

解析:该存储过程包含处理//SackConsulting/SendBookOrder和http://schemas.microsoft.com/SQL/ServiceBroker/EndDialog消息类型的逻辑。如果发送发后者,特定会话的句柄的特定会话会结束。如果接收到图书订单消息类型,它的消息将插入到表中,并且返回订单确认信息。

可以使用Alter Queue命令修改既有的队列。这个命令使用与Create Queue相同的选项,它允许改变队列的状态与保持期、待激活的存储过程、队列读取存储过程实例的最大数量以及过程的安全模式契约。

Alter Queue包括一个额外的参数Drop,它用来删除队列的所有存储过程激活设置。

使用Alter Queue命令将存储过程绑定到既有的队列:

----使用Alter Queue命令将存储过程绑定到既有的队列 ALTER QUEUE dbo.BookDistributionQueue WITH ACTIVATION (STATUS = ON, PROCEDURE_NAME = dbo.usp_SB_ReceiveOrders, MAX_QUEUE_READERS = 2,--独立处理队列中不同消息的同一存储过程同时执行的最大数量 EXECUTE AS SELF)--即存储过程将以与执行Alter Queue命令的主体的相同的权限来执行
  • 1.
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.

为了测试BookStore数据库的新服务程序,开始一个会话并设置新顺序:

Use BookStore GO DECLARE @Conv_Handler uniqueidentifier DECLARE @OrderMsg xml; BEGIN DIALOG CONVERSATION @conv_handler FROM SERVICE [//SackConsulting/BookOrderService] TO SERVICE '//SackConsulting/BookDistributionService' ON CONTRACT [//SackConsulting/BookOrderContract]; SET @OrderMsg = '<order id="3490" customer="29" orderdate="7/22/2008"> <LineItem ItemNumber="1" ISBN="1-59059-592-0" Quantity="2" /> </order>'; SEND ON CONVERSATION @Conv_Handler MESSAGE TYPE [//SackConsulting/SendBookOrder] (@OrderMsg);
  • 1.
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.
  • 7.
  • 8.
  • 9.
  • 10.
  • 11.
  • 12.
  • 13.
  • 14.
  • 15.
  • 16.
  • 17.
  • 18.
  • 19.

当队列Status=ON并且队列中到到达新消息时,执行存储过程来处理传入的消息。可以使用存储过程或外部程序,但使用存储过程的好处是,它们提供了处理消息、自动执行所有需要的响应和相关业务任务的简单的封装好的组件。

如果在目标队列上有存储过程被执行,并且激活新的接收到的消息,那么应该已经有订单确认消息返回到dbo.BookStoreQueue:

SELECT conversation_handle, CAST(message_body as xml) message FROM dbo.BookStoreQueue /* conversation_handle message A7B7FA73-5B5F-E011-8B4E-001C23FA56DD <orderreceived id="3439" /> */
  • 1.
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.

小结:

本文主要介绍Service Broker的设置会话优先级,存储过程中实现。下文将介绍Service broker的远程实现。

原文链接:http://www.cnblogs.com/downmoon/archive/2011/04/12/2013333.html

【编辑推荐】

  1. Service Broker基础应用(上)
  2. 简述Service Broker事件通知功能
  3. 一个Excel导入SQL Server的例子
  4. 优化你的DiscuzNT,让它跑起来
  5. 浅述当前模式读与一致性读的区别
责任编辑:艾婧 来源: 博客园
相关推荐

2011-05-06 15:37:10

Service BroSQL Server

2015-03-30 15:15:00

CloudFoundrPaaS开源

2011-05-06 15:00:52

Service BroSQL Server

2011-05-06 15:54:47

Service BroSQL Server

2021-06-02 08:07:59

LinuxService应用

2015-03-30 14:57:03

paascloudfoundrservice bro

2011-08-29 11:25:29

清空service bSQL Server

2011-07-06 15:36:31

ASP

2022-05-02 16:18:22

RocketMQBrokertopic

2015-08-07 10:00:58

Windows 10Service Rel

2021-03-15 09:44:39

Broker源码RocketMQ

2022-08-31 09:21:40

MQTT BrokeOthers

2011-04-15 09:33:24

NAT

2014-06-05 10:21:29

HTTP

2020-12-22 06:05:43

Mbedtls应用基础

2010-06-13 15:28:56

UML基础与应用

2015-01-12 13:48:55

Android应用组件

2013-01-18 10:45:38

IBMdW

2009-05-28 13:27:33

Windows CE

2016-09-20 22:04:55

Docker Linux Names
点赞
收藏

51CTO技术栈公众号