Статьи

Как отправлять текстовые сообщения с помощью службы Windows Azure

Недавно я ждал в О’Харе обратного рейса в Колумбус. Я запустил Evernote, чтобы наверстать упущенное в некоторых статьях Windows Azure, которые я хотел прочитать (я многое сохранил в Evernote). Одной из первых статей, которые я прочитал, была статья CodeProject Люка Джефферсона в Red Gate . Статья Люка дает действительно хорошую основу для использования командлетов Cerebrata PowerShell и Twilio для отправки SMS-сообщений, когда у вашей службы Windows Azure есть «проблемы».

Это заставило меня задуматься — могу ли я написать нечто подобное (я был вдохновлен), прежде чем я вернусь домой в Колумбус? Я бы хотел немного подправить его, чтобы он работал как рабочая роль Windows Azure. Я должен был бы сделать большую часть письма без опоры Интернета (помните — нет Wi-Fi в О’Харе и нет Wi-Fi в моем самолете). У меня было бы короткое интернет-соединение перед посадкой в ​​самолет, если бы я использовал свой удивительный Nokia Lumia 900 для привязки. Это выполнимо!

Время не могло быть лучше! Я вспомнил, как видел в Твиттере ранее в тот же день сообщение от @WindowsAzure, объявившего о новой акции от Twilio, чтобы получить бесплатные сообщения для клиентов Windows Azure . Идеальное время, чтобы попробовать это!



В то время как статья Люка о CodeProject использует командлеты PowerShell, я хотел попробовать это с обычным кодом C # и запустить решение в простой рабочей роли Windows Azure. Для этого мне нужно будет работать с Windows Azure Service Management API. Как указывает Люк в своей статье, API управления службами Windows Azure — это REST API. Он отлично объясняет основы, поэтому обязательно ознакомьтесь с ним и обратитесь в MSDN за всеми подробностями.

К сожалению, для этого API пока нет красивой оболочки .NET. Я взглянул на библиотеку Azure Fluent Management , но в ней еще не было всех функций, необходимых для этого маленького проекта с домашним животным (но, похоже, это здорово — что-то, за чем нужно следить). К счастью, я вспомнил, что прочитал отличную книгу Нила Маккензи по разработке Microsoft Windows Azure, и в ней был рецепт получения свойств размещенной службы. Бинго! Этот рецепт очень полезен (как и многие в книге Нила), и я держал код в примерном проекте, который я собрал, читая книгу Нила. С отправной точкой для использования API управления службами Windows Azure единственное, что мне теперь нужно, — это API для работы с Twilio.

Пора запустить функцию привязки к телефону, зарегистрироваться в Twilio и загрузить их API. Я решил использовать клиентскую библиотеку twilio-csharp и установил ее через NuGet. Достаточно просто. Со всем, что мне нужно было скачать, пришло время выключиться и сесть на самолет.

Основы того, что я хотел сделать, довольно просты:

  1. Получите свойства определенной размещенной службы Windows Azure
  2. Проверьте, запущен ли сервис или нет
  3. Если служба не работает, отправьте мне SMS-сообщение, чтобы сообщить, что что-то не так.
  4. Спи немного, а затем повторите процесс.

Получить свойства размещенного сервиса

private HostedServiceProperties GetHostedServiceProperties(string subscriptionId, string serviceName, string thumbprint)
{
String uri = String.Format(ServiceOperationFormat, subscriptionId, serviceName);

ServiceManagementOperation operation = new ServiceManagementOperation(thumbprint);
XDocument hostedServiceProperties = operation.Invoke(uri);

var deploymentInformation = (from t in hostedServiceProperties.Elements()
select new
{
DeploymentStatus = (from deployments in t.Descendants(WindowsAzureNamespace + "Deployments")
select deployments.Element(WindowsAzureNamespace + "Deployment").Element(WindowsAzureNamespace + "Status").Value).First(), RoleCount = (from roles in t.Descendants(WindowsAzureNamespace + "RoleList")
select roles.Elements()).Count(), InstanceCount = (from instances in t.Descendants(WindowsAzureNamespace + "RoleInstanceList")
select instances.Elements()).Count()
}).First();

var properties = new HostedServiceProperties
{
Status = deploymentInformation.DeploymentStatus,
RoleCount = deploymentInformation.RoleCount,
InstanceCount = deploymentInformation.InstanceCount
};

return properties;
}

Отправить сообщение, если не работает

     // Get the hosted service
     var serviceProperties = GetHostedServiceProperties(subscriptionId, hostedServiceName, managementCertificateThumbprint);

     // If the service is not running.
     if (serviceProperties.Status != "Running")
     {
          string message = string.Format("Service '{0}' is not running.  Current status is '{1}'.",
                                                   hostedServiceName, serviceProperties.Status);

          // Send the SMS message
          twilio.SendSmsMessage(fromPhoneNumber, toPhoneNumber, message);
     }
}

Собираем все вместе

 private readonly XNamespace WindowsAzureNamespace = "http://schemas.microsoft.com/windowsazure";
 private const string ServiceOperationFormat = "https://management.core.windows.net/{0}/services/hostedservices/{1}?embed-detail=true";

public override void Run()
 {
 Trace.WriteLine("Staring Windows Azure Notifier Role", "Information");

// Get the configuration settings needed to work with the hosted service.
 var hostedServiceName = GetConfigurationValue("HostedServiceName");
 var subscriptionId = GetConfigurationValue("SubscriptionId");
 var managementCertificateThumbprint = GetConfigurationValue("ManagementCertificateThumbprint");

// Get the configuration settings for Twilio.
 var twilioId = GetConfigurationValue("TwilioId");
 var twilioToken = GetConfigurationValue("TwilioToken");
 var fromPhoneNumber = GetConfigurationValue("FromPhoneNumber");
 var toPhoneNumber = GetConfigurationValue("ToPhoneNumber");

// Create an instance of the Twilio client.
 var twilio = new TwilioRestClient(twilioId, twilioToken);

while (true)
 {
 // Get the hosted service
 var serviceProperties = GetHostedServiceProperties(subscriptionId, hostedServiceName, managementCertificateThumbprint);

 // If the service is not running.
 if (serviceProperties.Status != "Running")
 {
  string message = string.Format("Service '{0}' is not running. Current status is '{1}'.",
  hostedServiceName, serviceProperties.Status);

 // Send the SMS message
 twilio.SendSmsMessage(fromPhoneNumber, toPhoneNumber, message);
 }

 Thread.Sleep(TimeSpan.FromMinutes(5));
 Trace.WriteLine("Working", "Information");
 }
 

Я собрал большую часть этого, прежде чем стюардесса сообщила мне, что пришло время выключиться, чтобы подготовиться к приземлению. Единственное, что мне было нужно, — это идентификатор подписки Windows Azure, отпечаток сертификата управления Windows Azure и размещенная служба для проверки этого. У меня есть несколько служб Windows Azure, работающих по разным причинам, поэтому все это было достаточно легко получить.

Со всеми необходимыми битами пришло время проверить это. Чтобы это работало в Windows Azure (в отличие от моего локального эмулятора), мне нужно было бы включить свой сертификат управления как часть развертываемой мной роли. При использовании эмулятора сертификат уже находится на моей машине для разработки, поэтому мне не нужно было делать ничего особенного.

Добавьте сертификат в роль

Я также загрузил бы этот сертификат как сервисный сертификат.

Сертификаты размещенной службы Windows Azure

Имея сертификаты на месте, я был готов развернуть службу как роль сверхмалого рабочего. Затем я выбрал одно из своих демонстрационных приложений и сказал Windows Azure закрыть его. Вскоре после этого я получил новое текстовое сообщение из своего аккаунта в Twilio!

Хотя это было просто доказательство концепции, это было довольно круто и может быть довольно мощным.

Если вам нужен весь исходный код этого проекта, вы можете скачать его здесь .