Cloud Service 中WebRole就相當與我們的WebSite,而WorkRole相當與我們在服務器上寫了個Windows Service,站在高可用的角度上來講,Cloud Service要優於WebSite,拿個例子來說,我們上傳個數據,數據需要入庫,通常website需要提交數據,等待響應,這個時候如果並發量大,系統響應時間會很長.如果使用Cloud Service就不存在這個問題,WebRole只負責把數據提交上來,而對數據的處理入庫則可以提交給WorkRole來處理,中間可以使用Service Bus中消息隊列機制進行信息的傳遞.個人感覺非常好的一個東東.
不說那么多廢話了,我們實際動手來完成一個WebRole和WorkRole具體的一個Demo.
首先,創建我們Cloud Service項目.
然后選擇添加,WebRole Asp.net Web角色 和 WorkRole 輔助角色與服務總線隊列
點擊編輯已添加的WebRole1和WorkerRoleWithSBQueue1修改對應的名字.
然后確定,選擇Web Forms,空的解決模板.如果大家這里身份驗證存在問題,請參考我的第二節內容.
點擊確定按鈕,生成我們的解決方案.
下來我們登陸我們的WindowsAzure門戶中,點擊Service Bus菜單創建我們的消息服務.
選擇我們創建的Service Bus查看它的連接信息.
然后我們復制他的連接字符串
下來我們打開,我們CloudService的配置文件,將連接Service Bus的連接字符串放入進去.
下來我們在這個配置文件中,修改WebRole中的內容,因為WebRole他需要訪問Service Bus那么我們在這里定義它的節點.
下來我們對具體的配置文件進行修改,也是將WorkRole中的ServiceBus配置,拷貝到WebRole中.
下來再我們剛才Windows Azure門戶當中復制的連接字符串,也放入對應的配置里.
下來,使用同樣的方法配制我們第三個配置文件:
這里我們Cloud Service中相關Service Bus就配置完成.
然后我們在WebRole中,右鍵添加一個Default頁面:
完成下列代碼
Default.aspx
<%@ Page Language="C#" AutoEventWireup="true" CodeBehind="Default.aspx.cs" Inherits="DemoWebRole.Default" %>
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
<head runat="server">
<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
<title></title>
</head>
<body>
<form id="form1" runat="server">
<div>
<asp:TextBox ID="txbInput" runat="server"></asp:TextBox>
<asp:Button ID="BtnSend" runat="server" Text="發送消息" OnClick="BtnSend_Click" />
<p />
<asp:Label ID="Label1" runat="server" Text=""></asp:Label>
</div>
</form>
</body>
</html>
Default.aspx.cs
using Microsoft.ServiceBus.Messaging;
using Microsoft.WindowsAzure;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
namespace DemoWebRole
{
public partial class Default : System.Web.UI.Page
{
const string QueueName = "DemoQueue";
protected void Page_Load(object sender, EventArgs e)
{
}
protected void BtnSend_Click(object sender, EventArgs e)
{
string strinput = txbInput.Text.ToString();
Send(strinput);
txbInput.Text = string.Empty;
}
private void Send(string text)
{
string connectionString = CloudConfigurationManager.GetSetting("Microsoft.ServiceBus.ConnectionString");
MessagingFactory factory = MessagingFactory.CreateFromConnectionString(connectionString);
// Initialize the connection to Service Bus Queue
MessageSender sender = factory.CreateMessageSender(QueueName);
BrokeredMessage message1 = new BrokeredMessage(text);
sender.Send(message1);
}
}
}
這個時候他會提示,和Service Bus相關的組件,沒有被引用
這個組件在那里呢,我們可以查看WorkRole中的引用找到它.
下來將地址路徑進行拷貝,然后再WebRole中引用進去.這個時候就沒有問題了.
下來我們修改WorkRole的代碼,讓WebRole傳遞過來的內容,輸出出來:
WorkerRole.cs
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Net;
using System.Threading;
using Microsoft.ServiceBus;
using Microsoft.ServiceBus.Messaging;
using Microsoft.WindowsAzure;
using Microsoft.WindowsAzure.ServiceRuntime;
namespace TeacherWorkerRole
{
public class WorkerRole : RoleEntryPoint
{
// 隊列的名稱
const string QueueName = "TeacherQueue";
// QueueClient 是線程安全的。建議你進行緩存,
// 而不是針對每一個請求重新創建它
QueueClient Client;
ManualResetEvent CompletedEvent = new ManualResetEvent(false);
public override void Run()
{
Trace.WriteLine("正在開始處理消息");
// 啟動消息泵,並且將為每個已收到的消息調用回調,在客戶端上調用關閉將停止該泵。
Client.OnMessage((receivedMessage) =>
{
try
{
// 處理消息
Trace.WriteLine("正在處理 Service Bus 消息: " + receivedMessage.SequenceNumber.ToString() + receivedMessage.GetBody<string>());
}
catch
{
// 在此處處理任何處理特定異常的消息
}
});
CompletedEvent.WaitOne();
}
public override bool OnStart()
{
// 設置最大並發連接數
ServicePointManager.DefaultConnectionLimit = 12;
// 如果隊列不存在,則創建隊列
string connectionString = CloudConfigurationManager.GetSetting("Microsoft.ServiceBus.ConnectionString");
var namespaceManager = NamespaceManager.CreateFromConnectionString(connectionString);
if (!namespaceManager.QueueExists(QueueName))
{
namespaceManager.CreateQueue(QueueName);
}
// 初始化與 Service Bus 隊列的連接
Client = QueueClient.CreateFromConnectionString(connectionString, QueueName);
return base.OnStart();
}
public override void OnStop()
{
// 關閉與 Service Bus 隊列的連接
Client.Close();
CompletedEvent.Set();
base.OnStop();
}
}
}
好的,代碼編寫完成,我們進行調試.這時候你可以在配制文件中修改你的實例數,比如我可以設置我的WebRole設置為2個實例,WorkRole2個實例.
兩種設置方式,1種是在配制文件直接配制,另一種是直接在Cloud Service中選擇對應的WebRole和WorkRole右鍵屬性中配制,然后他自動在配制文件中生成.
下來我們在去設置Demo Cloud Service使用全仿真器,默認仿真器只能使用單實例.
然后我們運行Demo Cloud Service進行全仿真測試
打開仿真界面.我們可以進行測試
點擊發送消息,可以看到其中的一個WorkRole已經獲取到我發送的消息了
嘿嘿,很有成就感吧!.