Configuring and Deploying the Azure Email Service application - 2 of 5
This is the second tutorial in a series of five that show how to build and deploy the Azure Email Service sample application. For information about the application and the tutorial series, see the first tutorial in the series.
In this tutorial you'll learn:
- How to set up your computer for Azure development by installing the Azure SDK.
- How to configure and test the Azure Email Service application on your local machine.
- How to publish the application to Azure.
- How to view and edit Azure tables, queues, and blobs by using Visual Studio Server Explorer.
- How to configure tracing and view trace data.
- How to scale the application by increasing the number of worker role instances.
Set up the development environment
To start, set up your development environment by installing the Azure SDK for Visual Studio 2013.
If you don't have Visual Studio installed, Visual Studio Express for Web will be installed along with the SDK.
Depending on how many of the SDK dependencies you already have on your machine, installing the SDK could take a long time, from several minutes to a half hour or more.
Download and run the completed solution
Download and unzip the completed solution.
Start Visual Studio.
From the File menu choose Open Project, navigate to where you downloaded the solution, and then open the solution file.
Press CTRL+SHIFT+B to build the solution.
By default, Visual Studio automatically restores the NuGet package content, which was not included in the .zip file. If the packages don't restore, install them manually by going to the Manage NuGet Packages for Solution dialog and clicking the Restore button at the top right.
In Solution Explorer, make sure that AzureEmailService is selected as the startup project.
Press CTRL+F5 to run the application.
The application home page appears in your browser.
Click Mailing Lists in the menu bar.
(Screen shots show web page style from Visual Studio 2012 project templates but the content is the same for Visual Studio 2013.)
Click Create New.
Enter some test data, and then click Create.
Create a couple more mailing list entries.
Click Subscribers, and then add some subscribers. Set Verified to
Prepare to add messages by creating a .txt file that contains the body of an email that you want to send. Then create an .htm file that contains the same text but with some HTML (for example, make one of the words in the message bold or italicized). You'll use these files in the next step.
Click Messages, and then add some messages. Select the files that you created in the previous step. Don't change the scheduled date which defaults to one week in the future. The application can't send messages until you configure SendGrid.
The data that you have been entering and viewing is being managed by the Azure storage emulator. The storage emulator uses a SQL Server Express LocalDB database to emulate the way Azure Storage works in the cloud. The application is using the storage emulator because that is what the project was configured to use when you downloaded it. This setting is stored in .cscfg files in the AzureEmailService project. The ServiceConfiguration.Local.cscfg file determines what is used when you run the application locally in Visual Studio, and the ServiceConfiguration.Cloud.cscfg file determines what is used when you deploy the application to the cloud. Later you'll see how to configure the application to use an Azure Storage account.
Close the browser.
View development storage in Visual Studio
The Azure Storage browser in Server Explorer provides a convenient way to work directly with Azure Storage resources.
From the View menu in Visual Studio, choose Server Explorer.
Expand the Azure node, then expand the Storage node, and then expand the (Development) node underneath the Azure Storage node.
If you haven't already logged in to Azure in Visual Studio, you'll be prompted for your Azure credentials. Enter credentials for the account that has the subscription you want to run the cloud service in.
Expand Tables to see the tables that you created in the previous steps.
Double click the MailingList table.
Notice how the window shows the different schemas in the table.
MailingList entities have
FromEmailAddress property, and
Subscriber entities have the
Verified property (plus
SubscriberGUID which isn't shown because the image isn't wide enough). The table has columns for all of the properties, and if a given table row is for an entity that doesn't have a given property, that cell is blank.
Another tool you can use to work with Azure Storage resources is Azure Storage Explorer.
Create an Azure Storage account
When you run the sample application in Visual Studio, you can access tables, queues, and blobs in the Azure storage emulator or in an Azure Storage account in the cloud. In this section of the tutorial you create the Azure Storage account that you'll configure Visual Studio to use later in the tutorial.
In your browser, open the Azure Management Portal.
In the Azure Management Portal, click Storage, then click New.
- Click Quick Create.
In the URL input box, enter a URL prefix.
This prefix plus the text you see under the box will be the unique URL to your storage account. If the prefix you enter has already been used by someone else, you'll see "The storage name is already in use" above the text box and you'll have to choose a different prefix.
Set the region to the area where you want to deploy the application.
Set the Replication drop-down box to Locally redundant.
When geo-replication is enabled for a storage account, the stored content is replicated to a secondary location to enable failover to that location in case of a major disaster in the primary location. Geo-replication can incur additional costs. For test and development accounts, you generally don't want to pay for geo-replication. For more information, see How To Manage Storage Accounts.
Click Create Storage Account.
In the image, a storage account is created with the URL
This step can take several minutes to complete. While you are waiting, you can repeat these steps and create a production storage account. It's often convenient to have a test storage account to use for local development, another test storage account for testing in Azure, and a production storage account.
Click the test account that you created in the previous step, then click the Manage Access Keys icon.
Visual Studio will automatically configure connection strings with one of these keys when you select the storage account. You can also update the connection strings manually.
There are two keys so that you can periodically change the key that you use without causing an interruption in service to a live application. You regenerate the key that you're not using, then you can change the connection string in your application to use the regenerated key. If there were only one key, the application would lose connectivity to the storage account when you regenerated the key. The keys that are shown in the image are no longer valid because they were regenerated after the image was captured.
Create a Cloud Service
In the Azure Management Portal, click Cloud Services then click the New icon.
Click Quick Create.
In the URL input box, enter a URL prefix.
Like the storage URL, this URL has to be unique, and you will get an error message if the prefix you choose is already in use by someone else.
Set the region to the area where you want to deploy the application.
You should create the cloud service in the same region that you created the storage account. When the cloud service and storage account are in different datacenters (different regions), latency will increase and you will be charged for bandwidth outside the data center. Bandwidth within a data center is free.
Azure affinity groups provide a mechanism to minimize the distance between resources in a data center, which can reduce latency. This tutorial does not use affinity groups. For more information, see How to Create an Affinity Group in Azure.
Click Create Cloud Service.
In the following image, a cloud service is created with the URL aescloud.cloudapp.net.
Configure the application to use your Azure Storage account
Next, you'll see how to configure the application so that it uses your Azure Storage account when it runs in Visual Studio, instead of development storage.
In Solution Explorer, right-click MvcWebRole under Roles in the AzureEmailService project, and click Properties.
In the MvcWebRole [Role] window, click the Settings tab.
In the Service Configuration drop down box, select Local.
Select the StorageConnectionString entry, and you'll see an ellipsis (...) button at the right end of the line. Click the ellipsis button to open the Storage Account Connection String dialog box.
In the Create Storage Connection String dialog, click Your subscription, and then choose your Subscription and your storage Account name.
Follow the same procedure that you used for the
StorageConnectionString connection string to set the
Microsoft.WindowsAzure.Plugins.Diagnostics.ConnectionString connection string.
Follow the same procedure that you used for the two connection strings for the MvcWebRole role to set the connection strings for the WorkerRoleA role and the workerRoleB role.
Open the ServiceConfiguration.Local.cscfg file that is located in the AzureEmailService project.
Role element for
MvcWebRole you'll see a
ConfigurationSettings element that has the settings that you updated by using the Visual Studio UI.
<Instances count="1" />
<Setting name="Microsoft.WindowsAzure.Plugins.Diagnostics.ConnectionString" value="DefaultEndpointsProtocol=https;AccountName=[name];AccountKey=[Key]" />
<Setting name="StorageConnectionString" value="DefaultEndpointsProtocol=https;AccountName=aestest;AccountKey=[Key]" />
Role elements for the two worker roles you'll see the same two connection strings.
You can edit these files directly instead of using the Visual Studio [Role] window. For more information on the configuration files, see Configuring an Azure Project
Test the application configured to use your storage account
Press CTRL+F5 to run the application. Enter some data by clicking the Mailing Lists, Subscribers, and Messages links as you did previously in this tutorial.
In Visual Studio, open Server Explorer.
Expand the Storage node under the Azure node, and then expand the node for the storage account that you configured the application to use.
Expand Tables, and double-click the
MailingList table to see the data that you entered on the Mailing List and Subscriber pages of the application.
Optional steps to disable Azure Storage Emulator automatic startup
If you are not using the storage emulator, you can decrease project start-up time and use less local resources by disabling automatic startup for the Azure storage emulator.
In Solution Explorer, right click the AzureEmailService cloud project and select Properties.
Select the Development tab.
Set Start Azure storage emulator to False.
Note: You should only set this to false if you are not using the storage emulator.
This window also provides a way to change the Service Configuration file that is used when you run the application locally from Local to Cloud (from ServiceConfiguration.Local.cscfg to ServiceConfiguration.Cloud.cscfg).
In the Windows system tray, right click on the compute emulator icon and click Shutdown Storage Emulator.
Configure the application to use SendGrid
The sample application uses SendGrid to send emails. In order to send emails by using SendGrid, you have to set up a SendGrid account, and then you have to update a configuration file with your SendGrid credentials.
Note: If you don't want to use SendGrid, or can't use SendGrid, you can easily substitute your own email service. The code that uses SendGrid is isolated in two methods in worker role B. [Tutorial 5][tut5] explains what you have to change in order to implement a different method of sending emails. If you want to do that, you can skip this procedure and continue with this tutorial; everything else in the application will work (web pages, email scheduling, etc.) except for the actual sending of emails.
Create a SendGrid account
- Follow the instructions in How to Send Email Using SendGrid with Azure to sign up for a free account.
Update SendGrid credentials in worker role properties
Earlier in the tutorial when you set the storage account credentials for the web role and the two worker roles, you may have noticed that worker role B had three settings that were not in the web role or worker role A. You can use that same UI now to configure those three settings (select Cloud in the Service Configuration drop-down list).
The following steps show an alternative method for setting the properties, by editing the configuration file.
Edit the ServiceConfiguration.Cloud.cscfg file in the
AzureEmailService project and enter the SendGrid user name and password values that you obtained in the previous step into the
WorkerRoleB element that has these settings. The following code shows the WorkerRoleB element.
There is also an AzureMailServiceURL setting. Set this value to the URL that you selected when you created your Azure Cloud Service, for example: "http://aescloud.cloudapp.net".
By updating the cloud configuration file, you are configuring settings that will be used when the application runs in the cloud. If you wanted the application to send emails while it runs locally, you would also have to update the ServiceConfiguration.Local.cscfg file.
Deploy the Application to Azure
To deploy the application you can create a package in Visual Studio and upload it by using the Azure Management Portal, or you can publish directly from Visual Studio. In this tutorial you'll use the publish method.
You'll publish the application to the staging environment first, and later you'll promote the staging deployment to production.
Implement IP restrictions
When you deploy to staging, the application will be publicly accessible to anyone who knows the URL. Therefore, your first step is to implement IP restrictions to ensure that no unauthorized persons can use it. In a production application you would implement an authentication and authorization mechanism like ASP.NET Identity, but these functions have been omitted from the sample application to keep it simple to set up, deploy, and test.
Open the Web.Release.config file that is located in the root folder of the
MvcWebRole project, and replace the ipAddress attribute value 127.0.0.1 with your IP address. (To see the Web.Release.config file in Solution Explorer you have to expand the Web.config file.)
You can find your IP address by searching for "Find my IP" with Bing or another search engine.
When the application is published, the transformations specified in the Web.release.config file are applied, and the IP restriction elements are updated in the web.config file that is deployed to the cloud. You can view the transformed web.config file in the AzureEmailService\MvcWebRole\obj\Release\TransformWebConfig\transformed folder after the package is created.
Configure the application to use your storage account when it runs in the cloud
Earlier in the tutorial when you set the storage account credentials for the web role and the two worker roles, you set the credentials to use when you run the application locally. Now you need to set the storage account credentials to use when you run the application in the cloud.
For this test run you'll use the same credentials for the cloud that you have been using for running locally. If you were deploying a production application, you would typically use a different account for production than you use for testing. Also a best practice for production would be to use a different account for the diagnostics connectionString than the storage connection string, but for this test run you'll use the same account.
You can use the same UI to configure the connection strings (just make sure that you select Cloud in the Service Configuration drop-down list). As an alternative, you can edit the configuration file, as explained in the following steps.
Open the ServiceConfiguration.Local.cscfg file in the AzureEmailService project, and copy the
Setting elements for
Open the ServiceConfiguration.Cloud.cscfg file in the AzureEmailService project, and paste the copied elements into the
Configuration Settings element for
WorkerRoleB, replacing the
Setting elements that are already there.
Verify that the web role and two worker role elements all define the same connection strings.
Publish the application
If it is not already open, launch Visual Studio and open the AzureEmailService solution.
Right-click the AzureEmailService cloud project and select Publish.
The Publish Azure Application dialog appears.
If you used the automatic method for importing storage account credentials earlier, your Azure subscription is in the drop-down list and you can select it and then click Next. Otherwise, click Sign in to download credentials and follow the instructions in Configure the application for Azure Storage to download and import your publish settings.
In the Common Settings tab, verify that your cloud service is selected in the Cloud Service drop-down list.
In the Environment drop-down list, change Production to Staging.
Keep the default Release setting for Build configuration and Cloud for Service configuration.
The default settings in the Advanced tab are fine for this tutorial. On the Advanced tab are a couple of settings that are useful for development and testing. For more information on the advanced tab, see Publish Azure Application Wizard.
In the Summary step of the wizard, click the save icon (the diskette icon shown to the right of the Target profile drop-down list) to save the publish settings.
The next time you publish the application, the saved settings will be used and you won't need to go through the publish wizard again.
Review the settings, then click Publish.
The Azure Activity Log window is opened in Visual Studio.
Click the right arrow icon to expand the deployment details.
The deployment can take about 5 minutes or more to complete.
When the deployment status is complete, click the Website URL to launch the application.
Enter some data in the Mailing List, Subscriber, and Message web pages to test the application.
Note: Delete the application after you have finished testing it to avoid paying for resources that you aren't using. If you are using a Azure free trial account, the three deployed roles will use up your monthly limit in a couple of weeks. To delete a deployment by using the Azure management portal, select the cloud service and click DELETE at the bottom of the page, and then select the production or staging deployment.
In the Azure Activity Log in Visual studio, select Open in Server Explorer.
Under Azure Compute in Server Explorer you can monitor the deployment. If you selected Enable Remote Desktop for all roles in the Publish Azure Application wizard, you can right click on a role instance and select Connect using Remote Desktop.
Promote the Application from Staging to Production
In the Azure Management Portal, click the Cloud Services icon in the left pane, and then select your cloud service and click the Dashboard tab.
Click Yes to complete the VIP (virtual IP) swap. This step can take several minutes to complete.
When the swap has completed, scroll down the Dashboard tab for the Production deployment to the quick glance section on the lower right part of the page. Notice that the Site URL has changed from a GUID prefix to the name of your cloud service.
Click the link under Site URL or copy and paste it to a browser to test the application in production.
If you haven't changed the storage account settings, the data you entered while testing the staged version of the application is shown when you run the application in the cloud.
Configure and View Tracing Data
Tracing is an invaluable tool for debugging a cloud application. In this section of the tutorial you'll see how to view tracing data.
Verify that the diagnostics connection string is configured to use your Azure Storage account and not development storage.
If you followed the instructions earlier in the tutorial, they will be the same. You can verify that they are the same either using the Visual Studio UI (the Settings tab in Properties for the roles), or by looking at the ServiceConfiguration..cscfg* files.
Note: A best practice is to use a different storage account for tracing data than the storage account used for production data, but for simplicity in this tutorial you have been configuring the same account for tracing.
In Visual Studio, open WorkerRoleA.cs in the WorkerRoleA project, search for
ConfigureDiagnostics, and examine the
private void ConfigureDiagnostics()
DiagnosticMonitorConfiguration config = DiagnosticMonitor.GetDefaultInitialConfiguration();
config.ConfigurationChangePollInterval = TimeSpan.FromMinutes(1d);
config.Logs.BufferQuotaInMB = 500;
config.Logs.ScheduledTransferLogLevelFilter = LogLevel.Verbose;
config.Logs.ScheduledTransferPeriod = TimeSpan.FromMinutes(1d);
In this code, the
DiagnosticMonitor is configured to store up to 500 MB of trace information (after 500 MB, the oldest data is overwritten) and to store all trace messages (LogLevel.Verbose). The
ScheduledTransferPeriod transfers the trace data to storage every minute. You must set the
ScheduledTransferPeriod to save trace data.
ConfigureDiagnostics method in each of the worker and web roles configures the trace listener to record data when you call the Trace API. For more information, see Using Trace in Windows Azure Cloud Applications
In Server Explorer, double-click WADLogsTable (expand Azure / Storage / yourstorageaccountname / Tables) for the storage account that you added previously. You can enter a WCF Data Services filter to limit the entities displayed. In the following image, only warning and error messages are displayed.
Add another worker role instance to handle increased load
There are two approaches to scaling compute resources in Azure roles, by specifying the virtual machine size and/or by specifying the instance count of running virtual machines.
The virtual machine (VM) size is specified in the
vmsize attribute of the
WorkerRole element in the ServiceDefinition.csdef file. The default setting is
Small which provides you with one core and 1.75 GB of RAM. For applications that are multi-threaded and use lots of memory, disk, and bandwidth, you can increase the VM size for increased performance. For example, an
ExtraLarge VM has 8 CPU cores and 14 GB of RAM. Increasing memory, cpu cores, disk, and bandwidth on a single machine is known as scale up. Good candidates for scale up include ASP.NET web applications that use asynchronous methods. See Virtual Machine Sizes for a description of the resources provided by each VM size.
Worker role B in this application is the limiting component under high load because it does the work of sending emails. (Worker role A just creates queue messages, which is not resource-intensive.) Because worker role B is not multi-threaded and does not have a large memory footprint, it's not a good candidate for scale up. Worker role B can scale linearly (that is, nearly double performance when you double the instances) by increasing the instance count. Increasing the number of compute instances is known as scale out. There is a cost for each instance, so you should only scale out when your application requires it.
You can scale out a web or worker role by updating the setting in the Visual Studio UI or by editing the ServiceConfiguration..cscfg* files directly. The instance count is specified in the Configuration tab of the role Properties window and in the
Instances element in the .cscfg files. When you update the setting, you have to deploy the updated configuration file to make the change take effect. Alternatively, for transient increases in load, you can change the number of role instances manually or configure Azure to automatically change the number of instances based on criteria you specify. For more information on autoscaling, see the last tutorial in this series.
In this section of the tutorial you'll scale out worker role B by using the management portal, but first you'll see how it's done in Visual Studio.
To do it in Visual Studio, you would right-click the role under Roles in the cloud project and select Properties.
You would then select the Configuration tab on the left, and select Cloud in the Service Configuration drop down.
Notice that you can also configure the VM size in this tab.
The following steps explain how to scale out by using the Azure Management Portal.
In the Azure Management Portal, select your cloud service, then click Scale.
Increase the number of instances for worker role B, and then click Save.
It can take a few minutes for the new VMs to be provisioned.
Select the Instances tab to see each role instance in your application.
You have now seen how to configure, deploy, and scale the completed application. The following tutorials show how to build the application from scratch. In the next tutorial you'll build the web role.
For links to additional resources for working with Azure Storage tables, queues, and blobs, see the last tutorial in this series.