Un paseo por las nubes

Un blog acerca de Cloud Computing...
Looking for a Surface 2 Pro 256GB using the Azure Cloud Power

SurfaceSince some weeks ago I have been trying to find a way of buying a Surface 2 Pro 256GB to definitively replace my development laptop. Some videos I have seen on YouTube like having 4 external displays brought my attention and after asking Joe Brinkman and Alberto Diaz about their experience working with the tablet as a dev machine both answered that definitively can replace my laptop (of course with the docking station). The final decision was taken after seeing another thread in the Surface Forums about the gaming experience like playing Call of Duty Ghosts on a Surface Pro 2.If that beast can move those types of games, for sure that can replace my current laptop.

And the problem started…

Looking for a Surface 2 on the stores

I have been trying to find a Surface 2 Pro 256GB in order to have the 8GB RAM in almost all the stores on Internet, and was really surprising that this model is Out of Stock in almost all of them. When finally found that the Microsoft Store at UK, I started to evaluate the problem of not getting the correct warranty if I’m in another country, different AC plugs than Spain, etc. The price it’s not low so the risk of having a problem without a store/warranty was not an option.


So the final decision was to buy it on Spain but same problem. Out of stock. I call the Microsoft Store and they didn’t know about when they could arrive. Bad thing.

I’m a developer, I don’t like doing things twice

I have been checking the Microsoft Store website twice a day since two weeks ago, and I was starting to be tired of doing it. So I was wondering if I could automate the process and receive some type of alert when the devices were in stock again. And then I found the how to create my new minion.

Looking into how the Store page works, I noticed that a GET WebAPI call is done to show the availability of the product:


More interesting was the result of that WebAPI call, since it’s an XML with the stock status for that product:


Idea! Idea! Idea!

If I didn’t want to check the website twice a day, what I would like was just to receive an alert of when the devices were in stock again. Would be nice to receive an e-mail on such event, and would love get an SMS on my mobile!

I always compare Azure and other cloud services like a Lego store. The pieces are there to build solutions, you only need to know about them. So let’s put some pieces in place:

  • Azure Mobile Services: in order to have a scheduled task looking for the device stock at the store. There are other options but the scheduler provided by Mobile Services is sufficient for this purpose and also free when using 1 scheduled task;
  • SendGrid: in order to receive an e-mail notification for stock changes. Again, there are other options but SendGrid offers a free tier for Azure subscribers that allows to accomplish this also for free;
  • Twilio: in order to receive SMS notifications for stock changes. Again, you can signup Twilio for free –no credit card needed- and send up to 1000 SMS (Azure subscribers get $10 when adding credit later to Twilio).

Cool, I love free stuff.

Adding some code to a scheduled task

So with the pieces in mind, the API keys from SendGrid and Twilio in my Notepad++, I started to create an empty Azure Mobile service through the management console.


The only thing inside the mobile service is just an scheduled task configured to run once per hour (my minions must work harder than me!!).


Finally the script code for the scheduler task. Note that I have hidden the API keys, e-mails and phone numbers:

function CheckAvailability() {
    try {
        var url = "http://surface.microsoftstore.com/store/mseea/es_ES/DisplayPage/id.ProductInventoryStatusXmlPage/productID.287012200?_=13";
        var request = require("request");
        request(url, function(error, r, body) {
                if (error) { return console.error(error); }
                if (r.statusCode != 200) { return console.error(r); }
                var xml2js = require('xml2js');
                var parser = new xml2js.Parser();                        
                parser.parseString(body, function (err, result) {
                    if (err) { return console.error(err); } 
                    if (result.InventoryStatusResponse.availableQuantity != "0") {
                    } else {
    catch(e) {

var SendGrid = require('sendgrid').SendGrid;

function sendNotifications(inventoryStatusResponse) {

function sendSMS(inventoryStatusResponse) {
    var httpRequest = require('request');
    var account_sid = "Your_Twilio_Account_SID_here";
    var auth_token = "Your_Twilio_Auth_Token_here";
    var from = "+345550000";
    var to="+3465550001";
    var message = 'The new Surface 2 Pro 256GB is now available at Microsoft Store. Units available: ' 
                    + inventoryStatusResponse.availableQuantity;
    // Create the request body
    var body = "From=" + from + "&To=" + to + "&Body=" + message;
    // Make the HTTP request to Twilio
        url: "https://" + account_sid + ":" + auth_token +
             "@api.twilio.com/2010-04-01/Accounts/" + account_sid + "/Messages.json",
        headers: { 'content-type': 'application/x-www-form-urlencoded' },
        body: body
    }, function (err, resp, body) {
        if (err) { return console.error(err); }

function sendEMail(inventoryStatusResponse) {
    console.log('Surface 2 Pro 256GB available at Microsoft Store. Units available: ' 
        + inventoryStatusResponse.availableQuantity + '. Sending notifications...');
    var api_user = 'Your_SendGrid_ApiUser';
    var api_key = 'Your_SendGrid_ApiKey';
    var sendgrid = new SendGrid(api_user, api_key);       
        to: 'foo@mydomain.com',
        from: 'bar@mydomain.com',
        subject:  'Surface 2 Pro 256GB available at Microsoft Store!',
        text:     'The new Surface 2 Pro 26GB is now available at Microsoft Store. Units available: ' 
                    + inventoryStatusResponse.availableQuantity
    }, function(success, message) {
        // If the email failed to send, log it as an error so we can investigate
        if (!success) {
        else {
            console.log('Email notification sent!');

Finally, by commenting the line checking for the availableQuantity != “0”, I got my initial notifications arriving to my devices:




The implementation shown above can be considered a proof of concept –BTW, probably I should not use the Store WebAPI without Microsoft confirmation- of things you can you can do by integrating different cloud services available today, and start using them for free.

The world has changed and is now cloud-connected.

Have you started to think cloud?

Saludos y Happy Coding!

Adding NewRelic support to a DNN Website running as an Azure Cloud Service

screensIn my last blog post announcing the DNN Azure Accelerator 2013 Q4 release, I commented that I was going to publish some posts about how to setup external startup tasks in order to include persistent changes on the cloud service instances without the need of rebuilding the cloud service package.

I will start today with a walkthrough to show how to add NewRelic monitoring to the deployed DNN instance by configuring an external startup task, step by step. I will be doing the same for MS Application Insights as well as other tips and tricks to increase the performance on IIS, just be a little patient these days Smile.

Signup for NewRelic Standard for free

One of the advantages of signing up for Azure, is that there is a lot of free stuff included with your subscriptions, thanks to the agreements done with third party companies like NewRelic. In this case, with each Azure subscription NewRelic gives a Standard subscription for one application giving you fully functional app performance management (includes server and real user management).

In order to activate your NewRelic Standard for free, follow these steps:

  1. In the Windows Azure Management console, click on “New > Store” to open the Store dialog. Once there scroll down until you find the NewRelic, and click on the Next button

    NewRelic Signup
  2. Select from the dropdown list the datacenter location where you want to use the services. You should use the same location where your DNN site will reside –or is currently running on.
  3. Click next to review the purchase of the free service, and click Finish to start provisioning.
  4. After a few seconds, the service will appear in the “Add-ons” section of the Management Portal. The most interesting links at the bottom will: show your current API Key and License Key, needed to deploy the agents later; redirect to the NewRelic Management portal where you can monitor your site once it’s deployed.


At this point, you have provisioned your free NewRelic Standard subscription. Let’s start configuring the DNN Cloud Service to start reporting in the “Applications” section.

Creating the external startup task for the DNN Azure Accelerator

In the NewRelic’s website, you can found how to modify an Azure cloud service package to start monitoring, and in fact, you can go that way by downloading the DNN Azure Accelerator source code from CodePlex. But in this case, instead of rebuilding the cloud service package with Visual Studio, what we are going to use is the new external startup task feature introduced in the latest release.

The steps to build the NewRelic external startup task are in summary:

  • Create a PowerShell cmdlet that will be executed on the role startup
  • Zip the cmdlet with the NewRelic’s agent and upload it to a public URL location
  • Specify the URL and License Key parameters in the “Startup.ExternalTasks” and “Startup.ExternalTasks.KeyValueSettings” configuration settings.

Let’s see one by one.

Create the PowerShell cmdlet

NewRelic provides two different type of agents depending on what you are going to monitor: the .NET Agent, that collects information of your .NET application, real time user monitoring, etc.; and the Server Agent, that collects information from a virtual machine perspective like CPU, memory, running processes, etc.

In this case we will simplify the PowerShell cmdlet to configure only the .NET Agent, but with some modifications you can deploy the server agent as well. Note that for the server agent you would need more than the free tier if you deploy more than one instance on the cloud service (I’m not 100% sure of this, something to ask to NewRelic’s sales support).

The following PowerShell script will install the NewRelic’s .NET Agent into a cloud service running the DNN Azure Accelerator. The license key, the application description and environment are taken from the new Role configuration setting “ExternalStartupTask.KeyValueSetting” that was introduced in the latest build. This value is a collection of key/value pairs, semicolon separated.

#    New Relic installation script for DNN Azure Accelerator (cloud services) - v2.18.35.0
#    This script install only the New Relic .NET Agent. The license key, the application description 
#   and environment are taken from the Role configuration setting "Startup.ExternalTasks.KeyValueSettings" 
#   (it's a collection of key=value pairs, separated by semicolon).

$scriptPath = split-path -parent $MyInvocation.MyCommand.Definition;
$newRelicAgentInstallationPath = Join-Path $scriptPath "NewRelicAgent_x64_2.18.35.0.msi"
$logPath = Join-Path $scriptPath "NewRelicInstall.log"

[void] [System.Reflection.Assembly]::LoadWithPartialName("Microsoft.WindowsAzure.ServiceRuntime")

# Writes in the installation log
function Append-Log($text)
    $((Get-Date -Format "yyyy-MM-dd HH:mm:ss") + " - " + $text) >> $logPath
    foreach ($i in $input) {
        $((Get-Date -Format "yyyy-MM-dd HH:mm:ss") + " - " + $i) >> $logPath


# Retrieves configuration settings from the cloud service configuration
function Get-ConfigurationSetting($key, $defaultValue = "")
    if ([Microsoft.WindowsAzure.ServiceRuntime.RoleEnvironment]::IsAvailable)
        Append-Log "The Role Environment is available. Looking the setting: " + $key
        return [Microsoft.WindowsAzure.ServiceRuntime.RoleEnvironment]::GetConfigurationSettingValue($key)
    } else {
        Append-Log "The Role Environment isn't available"
    return $defaultValue

# Retrieves the external startup key/value pairs        
function Get-StartupTaskKeyValueParameters()
    $setting = Get-ConfigurationSetting -key "Startup.ExternalTasks.KeyValueSettings"
    Append-Log $("Startup.ExternalTasks.KeyValueSettings: " + $setting)
    $kvSettings = @{}

    $matches = [regex]::Matches($setting, "\s*(?<KEY>[^\=\s]+)\=\s*(?<VALUE>[^\;]+)(\;|$)", @("Ignorecase"));
    foreach ($match in $matches) {
        $kvSettings.Add($match.Captures[0].Groups["KEY"].Value.Trim(), $match.Captures[0].Groups["VALUE"].Value.Trim());

    return $kvSettings

# Installs a .msi file
function Install-MsiFile($msifile, $arguments)
    Start-Process `
         -file  $msifile `
         -arg $arguments `
         -passthru | wait-process

Append-Log "Getting startup task parameters..."
$settings = Get-StartupTaskKeyValueParameters
$licenseKey = $settings["NewRelic.LicenseKey"]
if (!$licenseKey) {
    Append-Log "ERROR: license key not specified. The NewRelic installation cannot be performed"
Append-Log $("License key: " + $licenseKey)

# New Relic Agent installation:
Append-Log "Installing New Relic .NET agent..."
Install-MsiFile $newRelicAgentInstallationPath $(" /norestart /quiet NR_LICENSE_KEY=" + $licenseKey + " INSTALLLEVEL=50 /lv* E:\nr_install.log")

# Modify the configuration file (application name and host in case we are in staging)
Append-Log "Changing the .NET agent configuration file..."
$path = Join-Path (get-item env:"ALLUSERSPROFILE").Value "New Relic\.NET Agent\newrelic.config"
[XML]$newRelicConfig = Get-Content $path

# Application name:
$newRelicConfig.configuration.application.name = $(if ($settings["NewRelic.AppDescription"]) { $settings["NewRelic.AppDescription"] } else { "My DNN Website" })
# Log level (info by default). We will set this to warning
$newRelicConfig.configuration.log.level = "warning"

# If we are in staging, we have to set the staging host
if ($settings["NewRelic.Environment"] -eq "Staging") {
    $newRelicConfig.configuration.service.SetAttribute("host", "staging-collector.newrelic.com")

# Restart IIS in order to load the new configuration
Append-Log "Restarting IIS..."
IISRESET >> $logPath
NET START W3SVC >> $logPath

Append-Log "Done!"

Zip the .NET agent and the script in one file

Note that in the previous script, the .NET agent .msi file was the release, that can be downloaded via NuGet. If you keep this script up to date, you only need to change the $scriptPath variable to match the latest version available. Also note that the script filename must be in the format “Task???.ps1” to tell the DNN Azure Accelerator that must execute this task.

You can download the full zipped external task from this URL:

Specify the settings in the service configuration file

Once you have uploaded the .zip file to a public location –test the URL from your browser first to verify that works-, you need to specify the following settings in the service configuration:

  • “Startup.ExternalTasks”: specify the public internet URL from where the .zip file containing the external startup task will be downloaded
  • “Startup.ExternalTasks.KeyValueSettings”: parameters for the NewRelic external startup task in the following format:

    ”NewRelic.LicenseKey=<LICENSEKEY>; NewRelic.AppDescription=<APPDESCRIPTION>; NewRelic.Environment=<DEPLOYMENTSLOT>”

    where the:
    <LICENSEKEY> is your NewRelic license key that appears in the “Connection info” window of the addon in the Azure Management portal (see step 4 of NR provisioning above)
    <APPDESCRIPTION> is a descriptive name for your DNN deployment
    <DEPLOYMENTSLOT> is the deployment slot of your cloud service: Production | Staging

You can specify these values on a running deployment with the latest DNN Azure Accelerator release and all the configuration will be done automatically, since the modification of the external startup tasks settings recycles the current worker role agents executing again all the startup tasks –the operation will take some minutes to finish.


If you are going to update your deployment from a previous version using a deployment upgrade, you can use the preferred service configuration files from the “/packages” subfolder. Note that you will need to manually replace the “@@” variables in the .cscfg. You can use the one that was previously uploaded to Azure Storage in the “dnn-packages” container as a guide.

Deploy the service with the Accelerator’s wizard

If you are going to deploy a complete new cloud service or you are going to update your current deployment by redeploying the service using the Accelerator wizard, you will need to manually specify the NewRelic startup tasks settings before running the wizard. In order to do this, open in the “/packages” subfolder the .cscfg file that you will use later for deploying in the wizard. As example, if I want to use the “Medium” packages to deploy “Medium-Sized” instances, I need to edit the “/packages/DNNAzureSingleAndMedium_2013Q4.cscfg” file –just use notepad.exe to edit these files-, and locate the “Startup.ExternalTasks” entries, and fill the settings with the values specified in the previous step:



Now run the wizard and follow all the steps until you have your site running. A few minutes later you will notice that in the NewRelic management portal the application starts reporting:



In this article we can follow how we can easily customize the cloud service deployments by using external startup tasks. The example shows how to add the New Relic .NET monitoring agent to a DNN instance running on Azure cloud services, without rebuilding the cloud service package.

Don’t miss the following article where I will be posting a similar one to add Microsoft Application Insights in the same way.

Saludos y Happy coding! and BTW, Happy New Year friends!!!

DNN Azure Accelerator 2013 Q4 Released

cloudWithOThe new version of the DNN Azure Accelerator 2013 Q4 is already available for download with new features and fixes. The package is available as usual at CodePlex:


In this version, the most interesting feature is the ability of specifying the location of external startup tasks without the need of rebuilding the cloud service packages. This functionality was best described in a previous post called “Configuring external startup tasks on an Azure cloud service”.

In the next days I will be posting some examples of startup tasks, like automating the installation of NewRelic or MS Application Insights agents, modifying IIS performance settings, etc.

Release Notes

New Features


  • Fixed an issue on the web role startup, causing an cycling error on deployments using the latest Guest OS agent releases (the symbolic link was not being correctly deleted from the temporal storage)
  • Added "Generate security audits" local security policy for the DNN appPool (needed by WCF services)
  • Changed defualt VHD size to 32GB on the wizard
  • Fixed the password verification on the wizard UI to allow passwords longer than 16 chars

Un saludo & Happy Coding!

¡Ya tenemos ganador de La Guerra de los Drones!

LaGuerraDeLosDrones_Logo_WhiteYa tenemos ganador del concurso de La Guerra de los Drones. Felicidades Marcos Lora Rosa (@magicheron), de La Garriga, Barcelona. Ha conseguido finalizar con éxito y en tiempo el desarrollo de la aplicación ARDrone Draw para Windows Phone 8 y publicarla en la Store. ¡Tu AR Drone 2.0 ya está en camino!

¿Cómo funciona la App?

La aplicación ganadora ha sido diseñada para Windows Phone 8 que permite al usuario controlar al dispositivo AR Drone 2.0 en el modo tradicional, que se basa en unos joysticks virtuales en la pantalla de la aplicación, o en un modo más innovador y divertido que se basa en dibujar trazados en pantalla y hacer que el drone lo siga. El interfaz de la app está muy ´limpio y cuidado así como las animaciones de los menús en los cambios de modo.


photo 1

photo 3

En el video siguiente puedes observar una demo de este modo de vuelo de “dibujo”, en el que al trazar en pantalla las curvas y pulsar el botón de iniciar animación, el ARDrone reproduce la trayectoria dibujada en pantalla.

De nuevo, nuestra más sincera enhorabuena y felicidades por el buen trabajo realizado.

¿Y no ha habido más ganadores?

Pues al cierre de esta edición el único concursante que había conseguido cumplir con todas las bases del concurso -desde la implementación hasta la publicación en la Store- había sido Marcos, por lo que decidimos cerrar esta primera edición del concurso premiando el esfuerzo.

¿Y el resto de apps que estaban en desarrollo o cerca de su finalización? No desesperéis. Hemos tomado nota del poco tiempo que ha habido para la implementación y publicación, pero tampoco queríamos perjudicar a los que habían conseguido cumplir con todos los requisitos. La solución a la que hemos llegado es una segunda edición del concurso, en la que tendréis más tiempo. Permaneced en sintonía.


Desde aquí agradecemos a Parrot y a Microsoft España el apoyo en la celebración de este concurso. Por supuesto, a todas las comunidades técnicas que se han involucrado dando charlas y dedicando parte de su tiempo a compartir un buen rato desarrollando apps de una forma diferente. Y por supuesto a ti, que has estado ahí y sin el que este concurso no hubiera tenido sentido.

Aprovechamos para desearos unas felices fiestas y un próspero año 2014.

La Guerra de los Drones.

Materiales del evento ARDrone + Azure Mobile Services

LaGuerraDeLosDrones_Logo_WhiteMadre mía la de cosas que tengo que hacer para poner las cosas al día. Aquí va una de las que estaban pendientes -mejor tarde que nunca- con los materiales del evento de TenerifeDev sobre el desarrollo de aplicaciones para ARDrone 2.0 y Windows Azure Mobile Services.


Imágenes del evento

Aquí os dejo algunas imágenes, aunque podéis acceder a todas las imágenes del evento a través de la web de TenerifeDev.




Configuring external startup tasks on an Azure cloud service

PaaSTaskWindows Azure cloud services support startup tasks to perform operations before a role starts, like installing a component, enabling a Windows feature, register a COM component, etc. by using .cmd files or just running Powershell scripts. The documentation for running startup tasks in Windows Azure is available on MSDN.

They are really powerful to setup things needed by your role. Since the startup tasks are packaged in your cloud service, the problem comes when you want to use the same cloud service for hundreds of deployments, and you need to customize at least some of these startup tasks per deployment. Or you just simply want to customize the startup tasks without rebuilding and/or redeploying your cloud service.

After thinking on different approaches to implement this scenario without adding more complexity to the application lifecycle management, a good way of doing it would be to have the opportunity to specify startup tasks on a location outside the cloud service package. In summary, to have a startup task that downloads a set of external startup tasks from an Uri and executes them in order.

Let’s see how this can be achieved.

You can download the example code from this Url: http://sdrv.ms/1dY86lt

Adding a startup task to download external startup tasks

ExternalStartupTasksIn the attached example, there is a solution containing a worker role and a cloud service project. The main aspects of this implementations are in the files:

  • ServiceDefinition.csdef
  • ServiceConfiguration.*.cscfg
  • WorkerRole.cs
  • scripts/SetupExternalTasks.cmd
  • scripts/SetupExternalTasks.ps1

Let’s check one by one to fully understand how this works.


In the service definition file (ServiceDefinition.csdef), what we are going to do is to specify a new startup task as follows:

      <Task executionContext="elevated" commandLine="scripts\SetupExternalTasks.cmd" taskType="simple">
          <Variable name="EMULATED">
            <RoleInstanceValue xpath="/RoleEnvironment/Deployment/@emulated" />
          <Variable name="EXTERNALTASKURL">
            <RoleInstanceValue xpath="/RoleEnvironment/CurrentInstance/ConfigurationSettings/ConfigurationSetting[@name='Startup.ExternalTasksUrl']/@value" />

The startup task executes a script located on “scripts/SetupExternalTasks.cmd” in “simple” mode (the worker role OnStart event will not occur until the task completes, but you can change this behavior by modifying this attribute or by adding another task with the desired taskType). Two variables are passed:

  • EMULATED: to check if the task is being executed on the emulator or on Azure;
  • EXTERNALTASKURL: the Url of a zip file containing the external startup tasks;


This Url is configured in the ServiceConfiguration.*.cscfg files as any other setting:



As the startup tasks are executed before the role starts, any change on this setting would recycle the role to execute them again. The following code just do this:

        public override bool OnStart()
            // Set the maximum number of concurrent connections 
            ServicePointManager.DefaultConnectionLimit = 12;

            // For information on handling configuration changes
            // see the MSDN topic at http://go.microsoft.com/fwlink/?LinkId=166357.

            // Setup OnChanging event
            RoleEnvironment.Changing += RoleEnvironmentOnChanging;

            return base.OnStart();

        /// <summary>
        /// This event is called after configuration changes have been submited to Windows Azure but before they have been applied in this instance
        /// </summary>
        /// <param name="sender">The sender.</param>
        /// <param name="e">The <see cref="RoleEnvironmentChangingEventArgs" /> instance containing the event data.</param>
        private void RoleEnvironmentOnChanging(object sender, RoleEnvironmentChangingEventArgs e)
            // Implements the changes after restarting the role instance
            foreach (RoleEnvironmentConfigurationSettingChange settingChange in e.Changes.Where(x => x is RoleEnvironmentConfigurationSettingChange))
                switch (settingChange.ConfigurationSettingName)
                    case "Startup.ExternalTasksUrl":
                        Trace.TraceWarning("The specified configuration changes can't be made on a running instance. Recycling...");
                        e.Cancel = true;


Now let’s take a look to the task that is executed at the beginning. The variables are checked to skip this setup if you are running on a development environment –you may want to remove/comment the first line- or if the Url setting is empty:

if "%EMULATED%"=="true" goto SKIP

cd %ROLEROOT%\approot\scripts
md %ROLEROOT%\approot\scripts\external

reg add HKLM\Software\Microsoft\PowerShell\1\ShellIds\Microsoft.PowerShell /v ExecutionPolicy /d Unrestricted /f
powershell .\SetupExternalTasks.ps1 -tasksUrl "%EXTERNALTASKURL%" >> ExternalTasks.log 2>> ExternalTasks_err.log


Then a folder “external” is created to store all the downloaded stuff inside, to don’t interfere with other scripts in the solution while downloading. Finally the powershell script is called with the Url as parameter. Both standard and error outputs are redirected to log files.


Finally, the powershell script that does all the work is called. Note that the script supports three types of external files: a “.cmd” file; a “.ps1” file; or a “.zip” file that can contain one or more startup tasks:

 param (
    [string]$tasksUrl = $(throw "-taskUrl is required."),
    [string]$localFolder = ""

# Function to unzip file contents
function Expand-ZIPFile($file, $destination)
    $shell = new-object -com shell.application
    $zip = $shell.NameSpace($file)
    foreach($item in $zip.items())
        # Unzip the file with 0x14 (overwrite silently)
        $shell.Namespace($destination).copyhere($item, 0x14)

# Function to write a log
function Write-Log($message) {
    $date = get-date -Format "yyyy-MM-dd HH:mm:ss"
    $content = "`n$date - $message"
    Add-Content $localfolder\SetupExternalTasks.log $content

 if ($tasksUrl -eq "") {

if ($localFolder -eq "") {
    $localFolder = "$pwd\External"

# Create folder if does not exist
Write-Log "Creating folder $localFolder"
New-Item -ItemType Directory -Force -Path $localFolder
cd $localFolder

$file = "$localFolder\ExternalTasks.cmd"

 if ($tasksUrl.ToLower().EndsWith(".zip")) {
    $file = "$localFolder\ExternalTasks.zip"
 if ($tasksUrl.ToLower().EndsWith(".ps1")) {
    $file = "$localFolder\ExternalTasks.ps1"

# Download the tasks file
Write-Log "Downloading external file $file"
$webclient = New-Object System.Net.WebClient

Write-Log "Download completed"

# If the tasks are zipped, unzip them first
 if ($tasksUrl.ToLower().EndsWith(".zip")) {
    Write-Log "Unzipping $localFolder\ExternalTasks.zip"
    Expand-ZIPFile -file "$localFolder\ExternalTasks.zip" -destination $localFolder
    Write-Log "Unzip completed"

    # When a .zip file is specied, only files called "Task???.cmd" and "Task???.ps1" will be executed
    # This allows to include assemblies and other file dependencies in the zip file
    Get-ChildItem $localFolder | Where-Object {$_.Name.ToLower() -match "task[0-9][0-9][0-9].[cmd|ps1]"} | Sort-Object $_.Name | ForEach-Object {
        Write-Log "Executing $localfolder\$_"        
        if ($_.Name.ToLower().EndsWith(".ps1")) {
            powershell.exe "$localFolder\$_"
        elseif ($_.Name.ToLower().EndsWith(".cmd")) {
            cmd.exe /C "$localFolder\$_"
 elseif ($tasksUrl.ToLower().EndsWith(".ps1")) {
    powershell.exe $file
 elseif ($tasksUrl.ToLower().EndsWith(".cmd")) {
    cmd.exe /C $file

 Write-Log "External tasks execution finished"

In the case of a “.zip” file, the scripts expects the startup tasks with the name “Task???.cmd” or “Task???.ps1”, and executes them in order. Note that you can package file dependencies in the zip file such as .msi files, assemblies, other .cmd/.ps1 files, etc. and only the tasks with this pattern will be called by the script.

Seeing it in action

The attached example downloads an external .zip file located at https://davidjrh.blob.core.windows.net/public/code/ExternalTaskExample.zip. This .zip file contains two tasks “Task001.cmd” and “Task002.cmd”. After starting the role, we can verify that in the “scripts” subfolder the following files are created:


The “ExternalTasks_err.log” is empty (0Kb in size), indicating that the execution was successful. We can open the “ExternalTasks.log” to verify that our tasks executed as expected. In this case, the tasks are simply showing some echoes:


Inside the “external” subfolder we can found all the downloaded .zip file, the unzipped contents and another log about the downloading and task processing steps:



What if I need to get a configuration setting value from an external task?

In the case you need to get a service configuration value from a external task, you can use the awesome power of combining Powershell with managed code. The following Powershell function allows you to get a configuration setting value from inside your external startup in a .ps1 file:

[void] [System.Reflection.Assembly]::LoadWithPartialName("Microsoft.WindowsAzure.ServiceRuntime")

function Get-ConfigurationSetting($key, $defaultValue = "")
    if ([Microsoft.WindowsAzure.ServiceRuntime.RoleEnvironment]::IsAvailable)
        return [Microsoft.WindowsAzure.ServiceRuntime.RoleEnvironment]::GetConfigurationSettingValue($key)
    return $defaultValue

Once you have defined the function, you can use it with the following syntax. Note that the second parameter for the default value is optional.

$mySetting = Get-ConfigurationSetting "SettingName" "myDefaultValue"


Downloading and executing external startup tasks increase the versatility of the role startup tasks since you don’t need to repackage and upload your cloud services to change the behavior. By simply changing a setting they are automatically downloaded and executed previous starting the worker role.

You can download the example code from this Url: http://sdrv.ms/1dY86lt

Un saludo & Happy Coding!

[Evento] ¡Construye la mejor App y llévate un AR Drone 2.0!

LaGuerraDeLosDrones_Logo_WhiteAtención a la última frikada que estamos organizando a nivel nacional entre todas las comunidades técnicas de Microsoft. Se trata de un concurso de desarrollo de aplicaciones para Windows Phone y Windows RT con el objetivo de controlar remotamente drones AR Drone 2.0 de Parrot.

Partiendo del SDK que ofrece Parrot, de código open source disponible en GitHub y de todo el SDK de desarrollo para Visual Studio, los desarrolladores de las mejores 9 apps serán obsequiados con un AR Drone 2.0. En este enlace puedes encontrar las bases del concurso.


Durante las próximas semanas comenzarán en cada una de las ciudades una serie de formaciones técnicas GRATUITAS sobre cómo programar tu aplicación. De hecho, los drones ya están en las sedes de cada comunidad para que puedas realizar las pruebas oportunas. En la web del concurso puedes informarte acerca de todos los eventos transcurrirán próximamente.

Así que ya sabes: piensa en una idea, ven a las sesiones para aprender cómo desarrollarla, publícala y gana tu AR Drone 2.0.

¿Friki? Ya verás los videos que vamos a ir colgando…

…¿alguien dijo drones recibiendo señales desde un servidor en Windows Azure?

EvoqContentAgradecer a DNN Corp. por la instancia de Evoq Content in the Cloud, que permiten alojar la web actual del concurso.



Evento en TenerifeDev

Titulo: Desarrollando apps de control de AR.Drones en Windows Phone y Windows 8
Descripción: aprende a desarrollar aplicaciones para dispositivos móviles de plataforma Windows y compite con otros equipos a nivel nacional a ver quien construye la app más innovadora. En esta sesión se realizara una introducción al desarrollo de ambas plataformas, centrándonos finalmente en un ejemplo de app para el AR.Drone con el SDK. Veremos en directo como depurar línea a línea de código mientras el cuadricóptero revolotea por la sala. Anímate, forma un equipo, implementa tu idea, y hazte con uno de los 9 drones que hay de premio a las mejores apps.

LogoFecha: 8 de Noviembre de 2013
Hora: 17:00
Lugar: Sala de Grados de la ETSII, La Laguna
Inscripción gratuita pero por razones de aforo es necesario registrarse previamente
URL de registro al evento: http://bit.ly/TenerifeDevDrones
Organiza: TenerifeDev (http://www.tenerifedev.com) – Alberto Díaz, Jose Fortes, Santiago Porras, David Rodriguez

La dirección de la ETSII, recuerda a aquellos alumnos interesados en participar en este evento, que los estatutos de la Universidad de La Laguna (Art. 1.3, Art. 99),  establecen que la ULL "está al servicio del desarrollo integral de los pueblos, de la paz y de la defensa del medio ambiente" y que "en ningún caso se fomentará la investigación en aspectos específicamente bélicos o militaristas" por lo que la ETSII no apoyará proyectos fuera de estas directrices. Entendemos que las aplicaciones de los drones pueden ser útiles en muchos otros aspectos, por lo que animamos a los alumnos interesados a participar en proyectos ligados a las funciones que los estatutos establecen para la Universidad.

Welcome OS Family 4: Windows Server 2012 R2, IIS 8.5 and .NET Framework 4.5.1

logo-net-451This week has been an awesome one for those using Windows Azure to deploy their services. As soon as Microsoft announcing the general availability of Windows Server 2012 R2, the image was available on all Azure Datacenters worldwide to start creating new devices with the latest OS, not only for the Virtual Machines flavor (IaaS), also for Cloud Services (PaaS). This converts Microsoft’s Cloud in the first one allowing to deploy VMs with it.

The new features included in this OS version are really awesome, and if you are publishing a website on Azure via VMs or Cloud Services you will be really-really happy, because two new enhancements included: IIS 8.5 and .NET Framework 4.5.1.

And that isn’t all, seems that Windows Server 2012 deploys a 30% faster than other previous Windows Server OS images on Azure, so deployment operations like redeploying a hosted service, creating staging environments, etc. will be done faster!! Did I mention new price cuts for memory intensive instances?

Application performance

On this framework release, some “most requested features” have been included, like the x64 edit and continue feature, the ADO.NET connection resiliency (I will write a separate blog post only for this one), etc. You can find an overview of this improvements on this MSDN blog post, but I would like to highlight two features because directly affects the performance of DNN running on Windows Azure, a subject that as you may know, I have been working on for the past years. Microsoft has delighted us by running and documenting the performance improvements using DNN Platform, so let’s summarize the results.

ASP.NET App Suspend

Until now, when an application hosted on IIS was idle for some time (20mins by default), the site was terminated in order to preserve server resources. The problem was that with applications like DNN that takes some seconds to warm-up to serve the first web request (let’s call this “cold startup”), a site with low traffic would appear really slow because would spend more time warming the application pool than serving the contents. The workarounds were to increase the Idle Time-out property of the pool, or when not having access to the IIS configuration, to use external periodic webrequests to avoid the application being shutting down. But this techniques were in detriment of server’s resources and many hosters were banning this type of webrequests to not end up with the server shared resources.

This new feature allows applications hosted on IIS 8.5 to be suspended instead of being terminated, so when the site is shutdown because of the idle timeout, instead of completely killing the worker process, all the state is saved into disk. A new webrequest to the application pool causes to bring the worker process again back into memory, and for the case of DNN, this means around a 90% of improvement. This really rocks!!

ASP.NET App Suspend

Check this video to see the experiment done by Microsoft guys that led to the numbers above.


If you want to know more about this new feature, check this MSDN blog post from The .NET Team.

Multi-core JIT (MCJ) for ASP.net

The second great improvement in application performance with the .NET Framework 4.5.1 release is the Multi-core JIT support for applications using Assembly.LoadFrom and Appdomain.AssemblyResolve like DNN Platform, so if your are using a Medium sized or greater VM on Azure (VMs with more than one core), you will notice a good improvement on cold startups.


Enabling the awesome features

The Multi-core JIT feature is enabled by default if you use Windows Server 2012 R2 or just upgrade to .NET Framework 4.5.1, so you don’t need to do anything to turn it on. The ASP.net App Suspend feature can be enabled on IIS 8.5 in the application pool advanced settings:


New service package for cloud services

While using Virtual Machines (IaaS), this can be easily achieved by deploying the new Windows Server 2012 R2 server image. But to get these benefits on a Cloud Service (PaaS) when using the DNN Azure Accelerator you will need to use the latest accelerator’s service package because as fix was needed.



What fix? I tested today that while changing the OS to Windows Server 2012 R2 instance, the service was cycling on the startup tasks. The cause of this was that the ocsetup.exe used to install the remote management service -that is needed to setup WebDeploy- is no longer included on the system32 folder on WinSrv2012 R2.

The new way of enabling features is by using “dism”, so after doing the following changes on the startup task (check http://forums.iis.net/t/1171432.aspx for more info), all worked fine:

   1:  if "%EMULATED%" == "true" goto SKIP
   2:  if not "%ENABLED%" == "true" goto SKIP
   4:  dism /online /enable-feature /featurename:IIS-WebServerRole 
   5:  dism /online /enable-feature /featurename:IIS-WebServerManagementTools
   6:  dism /online /enable-feature /featurename:IIS-ManagementService
   7:  reg add HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\WebManagement\Server /v EnableRemoteManagement /t REG_DWORD /d 1 /f  
   8:  net start wmsvc >> SetupIISRemoteMgmt_log.txt 2>> SetupIISRemoteMgmt_err.txt
   9:  sc config wmsvc start=auto
  11:  :SKIP
  13:  EXIT /B 0

The new packages are available as an addon to the current DNN Azure Accelerator that you can download from CodePlex, called “DNN Azure Accelerator OS Family 4 packages”. Just download the .zip file and unzip it into the “/packages” folder in the accelerator. You will see those packages in the package selection step in the wizard.


After deploying an instance with one of this new packages, you will notice that the DNN site is running on top of IIS 8.5.


Hope this helps. If you have any question, just drop a comment on the post.


P.S. Have you seen the IIS 8.5 default page? Not yet? Here a screenshot Smile


¡Windows Azure MVP 2013!

Wow! Wow! Wow!!

MicrosoftMVPLogoVerticalHoy hay motivo de celebración. Cual ha sido mi satisfacción al ir a comprobar la bandeja de entrada y ver un correo con asunto “¡Enhorabuena MVP de Microsoft 2013!”, casi me da un patatús de alegría.

Para los que no sepan de qué va el tema –cosa harto difícil para aquellos que leen este blog- se trata de un nombramiento por parte de Microsoft en reconocimiento a la contribución realizada en las comunidades técnicas a lo largo del pasado año, en este caso en concreto en el área de Windows Azure.


En este enlace de MSDN se encuentra más información acerca de este anuncio, así como en el propio portal de Microsoft MVP.

Quiero agradecer a todos los que han puesto de un modo u otro su granito de arena para que haya sido posible. A la familia que cada vez me ve menos el pelo pero siguen demostrándome todo su apoyo; a los amigos que siguen estando ahí en todo momento; a los compañeros de trabajo que considero como parte de la familia; a los compañeros de TenerifeDev con los que tantos buenos ratos he pasado; a todos los que me han dado su apoyo leyendo este blog, dándome sus opiniones y convertirme en mejor profesional; y por supuesto a Microsoft, tanto por el reconocimiento como por su apoyo a la comunidad, algo que llega a convertirse en un estilo de vida.

Y en especial a ti Carmen, que has sido y eres la que me ha soportado durante tanto tiempo delante de la pantalla sin bajar la palanca de la luz. Te quiero.

¡Un saludo y Happy Coding!

David Rodriguez

Posted: 1/10/2013 20:35 por David Rodríguez | con no comments
Archivado en:
Windows Azure PowerShell: One script to rule them all

Are you in mobility and you have lots of SQL Azure DB Servers to manage? Does your public IP address change often and you’re sick of having to manually change the SQL Azure firewall rules?

Good news, I’m going to show you a PowerShell script to automatically add a firewall rule to ALL your SQL Azure servers in ALL your subscriptions for your current public Internet IP Address.

PowerShellDownloadBefore start, just be sure that you have installed the latest Windows Azure PowerShell package, that you can download from http://www.windowsazure.com/en-us/downloads/#cmd-line-tools

Setup your WA PowerShell subscriptions

The first part after downloading the Windows Azure PowerShell package is to setup the subscriptions you have access to. You will need to do this process only once, since the configuration settings will be stored in your profile, but perhaps you would like to revisit it later to add more subscriptions.

Configuring subscriptions by importing a .publishsettings file

The fastest way to setup the subscriptions is by importing a .publishsettings file containing an encoded management certificate data and subscription Ids:

1) Download your publish settings file:

PS C:\> Get-AzurePublishSettingsFile

This will open a browser that, after introducing your LiveId, will automatically download your .publishsettings file. This file contains credentials to administer your subscriptions and services, so be sure to store it in a secure location or delete after use.

2) Import your .publishsettings file:

PS C:\> Import-AzurePublishSettingsFile MyAzureCredentials.publishsettings

These settings will be stored inside “C:\Users\<UserName>\AppData\Roaming\Windows Azure PowerShell” folder.

Configuring subscriptions by using self-signed management certificate

Another way to setup your subscriptions would be to use your own self-signed management certificates, to avoid the automatic creation of management certificates in all your subscriptions and giving you more control on which subscriptions you are going to manage via PowerShell.

1) Create and Upload a Management Certificate for Windows Azure. Follow the instructions described in this MSDN article.

2) Run the following PowerShell script to access your subscription from PowerShell:

$subscriptionId = '<type your subscriptionId here>'
$subscriptionName = '<type a subscription name here>'
$thumbprint = '<paste your management certificate thumbprint here>'
$mgmtCert = Get-Item cert:\\CurrentUser\My\$thumbprint
Set-AzureSubscription -SubscriptionName $subscriptionName -SubscriptionId $subscriptionId -Certificate $mgmtCert

You can repeat this operation for each subscription you want to manage from PowerShell.

Finally, with both ways of configuring your Azure Subscriptions, you can verify which subscriptions you have setup by running “Get-AzureSubscription” Cmdlet.


One script to rule them all

Now that we have setup the subscriptions, the intention is to create a firewall rule in ALL the SQL Azure servers under ALL my subscriptions for my current public IP address, in order to manage them by using SQL Server Management Studio or whatever other tool.

Based on Alexander Zeitler’s blog post on the matter, I have added some modifications to build the following script that you can save in .ps1 file (I have called it RuleThemAll.ps1 Smile).

# Set a RuleName
$ruleName = "David Laptop"
# Get your public Internet IP Address
$externalIP = (New-Object net.webclient).downloadstring("http://checkip.dyndns.com") -replace "[^\d\.]"
# Loop all your subscriptions
Get-AzureSubscription | ForEach-Object { 
    Select-AzureSubscription $_.SubscriptionName
    # Loop all your SQL DB servers
    Get-AzureSqlDatabaseServer | ForEach-Object {
        $rule = Get-AzureSqlDatabaseServerFirewallRule -ServerName $_.ServerName -RuleName $ruleName
        if (!$rule) {
            New-AzureSqlDatabaseServerFirewallRule $_.ServerName -RuleName $ruleName -StartIpAddress $externalIP -EndIpAddress $externalIP 
        else {
            Set-AzureSqlDatabaseServerFirewallRule $_.ServerName -RuleName $ruleName -StartIpAddress $externalIP -EndIpAddress $externalIP 

After a while, you will have the rule enabled in all your servers in all your subscriptions.


Hope this helps,

David Rodriguez

Posted: 25/9/2013 11:40 por David Rodríguez | con no comments
Archivado en:
DNN Azure Accelerator 2013 Q3 Released

DNNPoweredByAzureHi, today I have released a new version of the DNN Azure Accelerator, the tool to deploy DNN Platform instances on Windows Azure by using cloud services (PaaS model).

You can download the latest version from CodePlex:

New features

The new features included in this release need deeper details:

  • Packages and solution upgraded to Azure SDK 2.1: all the packages has been rebuilt by using the latest Azure SDK version available, that comes with more features and support for the latest cloud services features. Check the Azure SDK 2.1 release notes for more information. Note that the previous Accelerator packages were built using the SDK 1.8;
  • Changed the use of a mapped network drive for a symbolic link: to avoid remapping issues executing “net.exe use” and “net.exe delete” commands, the new method for mapping the network location has been introduced by using a symbolic link to the network share. As a consequence, you will no longer see the X: mapped network drive. To access the drive contents:
    • From the webrole that mounted the drive, you can access the drive contents by browsing F: drive (or B: if it’s the first mount)
    • From any webrole, included the one that mounted the drive, you can access the drive contents by browsing “C:\Resources\Directory\<RoleDeploymentId>.DNNAzure.SitesRoot\root”. Note that the alias “C:\Resources\Directory\sites\root” is also available, and it’s the one being used by IIS
  • Support for Web Platform Installer custom feeds: now you can specify a custom feed Url for Web Platform Installer, so you can automate the installation of custom addons using this way. To build your own custom feeds, check this blog post.

Another important thing that changed on this release, is that Azure Connect is no longer supported in favor of Virtual Network, so the Connect step in the Wizard has been removed. The new step to setup Virtual Network through the wizard has not been included in this release, but you can get it working by including your virtual network settings directly on the .cscfg files before starting to create the cloud service. For more information about how this can be achieved, check the Windows Azure Virtual Network Configuration Schema documenation.

Release notes

New Features

  • Packages and solution upgraded to Azure SDK 2.1
  • Changed the use of a mapped network drive for a symbolic link to avoid remapping issues (you will not see the mapped X: drive anymore)
  • Support for Web Platform Installer custom feeds
  • Rebranding changes


  • Fix for the CA2 certificate thumbprint that was being ignored
  • Fix for WebDeploy and FTP services while working on HA mode
  • Fixes around the drive unmount/mount logic when a failure is detected
  • Fix to include the databaseOwner and objectQualifier settings while creating the portal aliases for the Offline site
  • Fix to shorten the symbolic link path length (see http://geeks.ms/blogs/davidjrh/archive/2013/06/18/path-too-long-when-using-local-storage-in-an-azure-cloud-service.aspx for more info)
  • Implemented the RoleEnvironment.StatusCheck to programatically change the instance status from Busy to Ready after successfully setting up the IIS
  • Fix on the Compete for the lease process, causing a "Value cannot be null" exception after a deployment upgrade
  • Fix to modify the default connection limit to a higher value to avoid inrole caching connection timeouts
  • Fix to avoid 404 errors while calling the automatic installation process
  • Fix to add support for East US and West US in the accelerator Wizard


  • Azure Connect has been deprecated in favor of Virtual Networks. All Azure Connect support has been removed


Un saludo y happy coding!

[Event] CloudBurst 2013: the Sweden Windows Azure Group Developer Conference

CloudBurst2013CloudBurst is a Windows Azure developer conference run by the Sweden Windows Azure Group (SWAG). The event features two days of sessions from Windows Azure community and industry leaders and provides real-world content for Windows Azure developers and those wanting to explore the platform. The focus will be on developing Windows Azure applications and real-world cloud-based solutions.

The event will run for two days on September 19 - 20, 2013 at the headquarters of Microsoft in Stockholm, where the "top" Azure MVPs will share sessions around the Windows Azure platform. Organizers for SWAG are the two Swedish Windows Azure MVPs Alan Smith and Magnus Mårtensson.

The event is free to attend and if can’t go to Stockholm for the date don’t worry, the event will be streamed via Microsoft World Wide Events. You have all the information on the CloudBurst 2013 website:

CloudBurst 2013 event information

And don’t loose the “DNN Cloud Services – Under the Hood” session!

ReadySetGoIt is my pleasure to participate as a speaker in a session to discuss how we implemented DNN Cloud Services on the Windows Azure platform. For an hour I will be showing some details of the most interesting subsystems as the DNN Verification Extension Service created using Azure cloud services and messaging queues; how we have deployed about 20,000 instances of product trials with Windows Azure Pack for Windows Server on Virtual Machines and all fully automated; or how we have built a backend system using a CQRS pattern and able to deploy DNN instances on any infrastructure, from web Sites to Cloud Services.

See you in Stockholm!

Un saludo y “Happy Kodning”!!

PS: Did I tell you that you can still get an Aston Martin? Smile

[Evento] CloudBurst 2013: estos suecos se han vuelto locos!!

CloudBurst2013CloudBurst es una evento para desarrolladores de Windows Azure organizada por el grupo de usuarios de Windows Azure de Suecia (SWAG). El evento transcurre durante dos días llenos de sesiones de líderes de la comunidad e industria de Windows Azure, ofreciendo contenido de mundo real para desarrolladores de Windows Azure y también para aquellos que deseen explorar la plataforma.

El evento se desarrollará durante dos días, entre el 19 y 20 de septiembre de 2013 en la sede de Microsoft de Estocolmo, donde los “top” Azure MVPs compartirán sesiones alrededor de la plataforma. Los organizadores del grupo de usuarios SWAG son los dos Windows Azure MVPs Alan Smith y Magnus Mårtensson.

La asistencia al evento es totalmente gratuita y si te queda algo lejos no te preocupes, que también habrá streaming en directo a través de Microsoft World Wide Events. Tienes toda la información en el sitio web de CloudBurst 2013:

Información y registro de CloudBurst 2013

¡Y esta vez la lío con ellos!

ReadySetGoEs para mí un placer poder participar como ponente en una de las sesiones para hablar de cómo hemos implementado DNN Cloud Services sobre la plataforma Windows Azure –en este en post de MSDN Spain puedes encontrar información relativa al tema. Durante una hora mostraré los detalles de los subsistemas más interesantes como el DNN Extension Verification Service creado usando Azure cloud services y colas de mensajería; cómo hemos creado cerca de 20.000 instancias de pruebas de producto con Windows Azure Pack para Windows Server sobre Virtual Machines y todo de forma totalmente automatizada; o cómo hemos construido un sistema de backend mediante un patrón CQRS capaz de desplegar DNN sobre cualquier infraestructura, desde Web Sites hasta Cloud Services.

Nos vemos en septiembre.

Un saludo y “Happy Kodning”!!

P.D. ¿Te había dicho que todavía puedes conseguir un Aston Martin? Smile

“Path too long” when using local storage in an Azure Cloud Service

imageIt is insane that in 2013 we still try to workaround the 260 character limit in a file path, more when the conversations are centered on services, scaling and other meta-cloud philosophies.

But this problem is still here and working with VMs hosted in the cloud is no different, on-premise problems will appear in the same way when online. I would recommend the “Long Paths in .NET” series from Kim Hamilton where this matter is deeply discussed. The post is from more than 6 years ago…and this is not solved yet.

So let’s talk about the problem I had. When using local storage on an Azure web or worker role, the root location for this storage while running on Azure starts with a path that can “eat” almost the half of the MAX_PATH -note that I’m not referring to the problem when playing on DevFabric in your local environment, whose solution is commented on this MSDN blog post. This will be something like:


As example:


The problem is that the RoleDeploymentId is 32 char length, and if you want to keep some sanity on your role names and storage names you will use something that has some meaning. In my case, the path was “eating” 108 chars, almost the half of the max path. While creating some recursive folders inside that temp path the “Path too long” error will appear sooner than later.

Techniques from the past to solve problems from the past

After playing a little bit with Subst.exe, didn’t convince me because I was trying to keep distance from mounting and managing drives between different user sessions. But then César Abreu give an interesting idea: why not use old style DOS format for the paths?

Interesting approach, so after some reading on the Fsutil.exe documentation on TechNet, I did some tests on a running instance:

1) Enable the short name behavior for volume C:


2) Add a short name to the local storage folder


3) Verify


I finally created a simple two line startup task to be executed with elevated privileges and that would give me an additional 83 characters.

REM Enable short names on volume C:
fsutil.exe 8dot3name set c: 0

REM Add a short name to the local storage folder
fsutil.exe file setshortname "C:\Resources\Directory\%RoleDeploymentID%.MyWebRole.MyLocalStorage" S

The first line enables the short name behavior for volume C:. I noticed that this is enabled for other volumes on an Azure role, but is not enabled by default on C: drive. The second line simply sets the folder short name as “S”. With this I can use then the path “C:\Resources\Directory\S” instead of the long one, and worked like a charm. Note that you can’t do the same for “Resources” and “Directory” folder names, since they are in use during the role startup, and would give you an error while trying to do the operation.

Hope this helps!

Windows Azure: disponibilidad general de Infraestructura como Servicio (IaaS)

imageUno de los acrónimos que más está de moda en nuestros mundos de Azure es del de “GA”, que significa el cambio de un servicio en modo “Preview” a disponibilidad general (del inglés General Availability), pasando de ser un servicio con soporte limitado a un producto totalmente soportado, con sus SLAs, precios definitivos, etc. Pues hoy es uno de esos días en los que oyes por ahí: ¡Hey, que Windows Azure IaaS es ahora GA!

Y es que también es normal encontrarnos con alguna sorpresa cuando un producto pasa a ser GA, normalmente como “regalito” que acompaña el lanzamiento. Lo que era menos de esperar era que esos anuncios incluyeran co-lateralmente mejoras en precios en otros servicios como cloud services. ¿Más barato? Oh yeah!

Aquí podéis ver en detalle el anuncio de Scott Guthrie en su blog con todo lujo de detalles. No voy a copiar aquí todos ellos, sino que voy a hacer incidencia en lo que me parecen los 3 grandes noticiones de esta puesta en marcha de IaaS en Windows Azure.

Nuevas plantillas de VM

Una de las grandes novedades es que a partir de ahora ya puedes desplegar una máquina con SQL Server, BizTalk Server o Sharepoint sin tener que hacer frente al pago de la licencia completa del software de servidor, sino que continuando con el modelo de pago por uso, existe la modalidad del pago de un sobrecoste adicional al precio de hora estándar de computación. Hora que usas, hora que pagas. No lo usas, no lo pagas. Fácil.

En el caso de SQL Server, nos encontraremos con plantillas de SQL Server 2012 Standard y Enterprise desplegados sobre Windows Server 2008. Si bien ya hay precio para la edición Web, no hay plantilla para desplegarlo.

Para BizTalk también encontraremos plantillas para las ediciones de evaluación, la Standard y Enterprise. Para el caso de Sharepoint, aún no están disponibles los precios, aunque sí que está la plantilla de Sharepoint Server 2003 Trial.


Nuevos tamaños de máquina XXL y XXXL (A6 y A7)

Otra de las grandes novedades es la posibilidad de desplegar instancias de uso intensivo de memoria, viniendo a duplicar el tamaño ExtraLarge que teníamos hasta ahora en lo que a memoria RAM se refiere. De este modo, los tamaños de instancias irán desde A0 hasta A7, cada una duplicando en memoria a la anterior. OJO: no me preguntéis dónde se dejaron A5 (esto trataré de averiguarlo):



Nuevos precios reducidos, ¡y no sólo para IaaS, también para PaaS!

Por último, una de las terceras grandes novedades es el anuncio de una reducción de precios de un 21% sobre Windows Azure Virtual Machines (IaaS) y de un 33% de reducción de precios en soluciones desplegadas bajo modelo PaaS (toma ya! un 12% de rebaja adicional si despliegas DNN en modelo PaaS con el Accelerator!!!). Estos nuevos precios casan con la oferta actual bajo demanda de Amazon, tanto para máquinas Windows como Linux.

Cabe recalcar que si bien Windows Azure Virtual Machines (IaaS) está disponible generalmente desde hoy 16 de abril, se continuará ofreciendo el precio con descuento de la Preview hasta el 31 de Mayo. Los nuevos precios de GA tendrán efecto a partir del 1 de junio.

Precios para modelo IaaS


Precios para modelo PaaS


Toda la información de los nuevos tamaños de máquina y sus precios los puedes encontrar en este enlace: https://www.windowsazure.com/en-us/pricing/details/virtual-machines/


En este post he comentado las que me parecieron las tres principales novedades incluidas en este lanzamiento, pero hay muchas otras y otros pequeños huevos de pascua –¿comenté que ahora los VHD de S.O. son de 127Gb, o que puedes cambiar el nombre del usuario “Administrator”?-, así que no olvides visitar el post original de Scott Guthrie.

Por lo que he podido experimentar después de haber desplegado cerca de 100 servidores en modo IaaS desde su salida en modo Preview en Junio de 2012, el servicio de Windows Azure Virtual Machines ha ido mejorando en rendimiento, confiabilidad y disponibilidad. De hecho, el principal problema que podíamos encontrarnos a fecha de hoy era que al estar en modo Preview, no era un producto totalmente soportado con sus acuerdos de niveles de servicio. Con el lanzamiento de hoy, esto lo cambia todo, ya que todas los despliegues que tuvieras pasan a tener soporte y por lo tanto, pasa a ser un lugar donde puedes poner tus despliegues de producción.

Veremos qué más sorpresas nos traen nuestros amiguetes de Microsoft en los próximos meses. Están que lo petan con tanto anuncio.

¡Un saludo y happy coding!

Posted: 16/4/2013 16:19 por David Rodríguez | con no comments
Archivado en:
Pidiendo una de camarones mientras tu sitio autoescala en Azure

CamaronesAzureDespués de la salida de la última versión 6.4 del DotNetNuke Azure Accelerator que, recordemos, añade soporte para alta disponibilidad de tus sitios web con DotNetNuke en Azure, llega el momento de probar opciones de autoescalabilidad para ajustar la capacidad a la demanda y como no, ahorrar en costes.

No sé si todos sabréis de una de las últimas adquisiciones de Microsoft. Se trata de la startup MetricsHub, cuyo principal foco es la monitorización y automatización de escalado de despliegues realizados sobre Windows Azure, para sacar el mayor partido posible a la flexibilidad y valor a nuestras soluciones en la nube. Lo mejor de esta adquisición es que como resultado final todos los clientes de Windows Azure pueden activar la versión preliminar de estos servicios a través de la Store de forma…GRATUITA!!!

Las características más destacables de estos servicios serían las siguientes:

MetricsHub Dashboard ActiveScale desde MetricsHub Notificaciones
Completo cuadro de mandos con un resumen de los datos más importantes de tu servicio en la nube ActiveScale mantiene tu servicio en condiciones cuando la carga aumenta, del mismo modo que decrementa los costes Envío de alertas a través de correo electrónico e integración con PagerDuty

Ver video

Ver video

Ver video

metrics_hubSi quieres saber más sobre esta adquisición sigue este anuncio en los blogs de MSDN: “Microsoft Acquires MetricsHub”.

En este artículo veremos un paso a paso sobre cómo activar la monitorización de nuestro sitio DotNetNuke desplegado sobre Windows Azure, así como habilitar las opciones de autoescalado y notificaciones para poder irnos a tomar tranquilamente una tapa de camarones a la playa mientras las máquinas trabajan por nosotros.

IMPORTANTE: para que las funciones de autoescalado funcionen correctamente, debes haber desplegado tu sitio web al menos con la versión 6.4 del DotNetNuke Azure Accelerator.

Activando MetricsHub en nuestra suscripción

Para comenzar a examinar las opciones de autoescalado de nuestra instancia DotNetNuke sobre Windows Azure en modo PaaS (una instancia desplegada como un “cloud service” con el Accelerator, no como un Azure Website), lo primero que tenemos que hacer es habilitar las opciones de monitorización en nuestra suscripción. Para ello realizaremos los siguientes pasos:

  1. Iniciar sesión en la consola de administración de Windows Azure en https://manage.windowsazure.com
  2. En la barra de comandos inferior, pulsamos sobre “Nuevo” y luego en “Store”
  3. En la pantalla de selección de Add-ons, buscar “Active Cloud Monitoring” (ahora mismo aparece como el primero de la lista)
  4. Al pulsar siguiente, nos congratula ver que efectivamente el servicio es GRATUITO. Pero OJO: en la región, indica la misma localización donde tienes ubicados tus servicios cloud, ya que de lo contrario puede incurrir en gastos de tráfico saliente desde tus cuentas de almacenamiento donde se está guardando la información de diagnóstico.
  5. Al pulsar siguiente, podemos volver a ver cómo el servicio es gratuito. Aún no se han ofrecido detalles de cómo evolucionará este servicio. Por ahora, el límite que he podido constatar es de que no admite monitorización de más de 150 servidores, límite más que aceptable.
  6. Al pulsar sobre finalizar, se comienza a desplegar nuestro servicio “Active Cloud Monitoring”, y al cabo de unos segundos ya está todo listo para comenzar a configurar la monitorización
  7. Al pulsar sobre el Add-on, nos lleva al Dashboard del servicio en Azure, aunque no será desde este portal donde accedamos a toda la información. Para hacer esto último, pulsamos sobre el enlace de visitar la web de “MetricsHub, Inc” para los pasos siguientes:
  8. Una vez en el sitio de MetricsHub, el primer paso es configurar qué subscripciones y/o servicios queremos monitorizar. Para ello es necesario que subamos el fichero “.publishsettings” generado por nuestro portal (que contendrá un certificado de administración serializado y los ids de suscripción que puede administrar). Este proceso se realiza en dos pasos automáticos siguiendo las instrucciones en pantalla
  9. Llegó la hora de indicar qué suscripciones y/o servicios queremos monitorizar. Seleccionamos los que queremos –más tarde podremos añadir o quitar desde las opciones de administración de la cuenta- y le damos al botón de comenzar, proceso que tarda unos minutos en finalizar.
    Por el momento el servicio monitorizará cloud services (PaaS), Windows Azure Websites, espacio en cuentas de almacenamiento y máquinas virtuales (IaaS). Para estas últimas, tendrás que hacer el paso adicional de instalar un agente local que envíe los datos de monitorización. Como el DNN Azure Accelerator funciona sobre PaaS, no tendrás que realizar ninguna operación adicional de este tipo.

Jugueteando con la monitorización

Una vez que está todo configurado, es el momento de permitirle unos minutos al servicio para que comience a obtener los datos de diagnóstico. Una de las cosas que me llama la atención es que toda la interfaz de usuario se ha implementado mediante “Responsive design”, con lo que puedes acceder desde cualquier dispositivo móvil sin problemas ya que éstas se ajustan dinámicamente al tamaño de pantalla en cada dispositivo.


Una vez que le hemos dado tiempo a obtener datos, veremos como las gráficas de monitorización comienzan a funcionar dentro de cada servicio.

Como ejemplo, veamos la monitorización de un site de DNN desplegado en modo de alta disponibilidad con un mínimo de 2 instancias ExtraSmall. Veremos 3 niveles de monitorización de un servicio cloud –que podremos personalizar añadiendo más o menos datos a las gráficas y tablas de datos-.

El primer nivel de monitorización es a nivel general del servicio cloud:


Como vemos, el uso de memoria está bastante ajustado ya que en el ejemplo usamos máquinas ExtraSmall con sólo 768Mb de RAM.

Al pulsar sobre el role “DNNAzure” accedemos al segundo nivel de monitoración a nivel de Role, donde podemos a nivel general las estadísticas para cada uno de los roles de uso de CPU, memoria, operaciones de lectura y escritura en disco así como tráfico de red entrante y saliente, todo en una sola pantalla muy bien consolidado.


Por último, al pulsar sobre el nombre de una de las instancias de role, por ejemplo “DNNAzure_IN_0”, accederemos al tercer nivel de monitorización a nivel de instancia, donde podremos monitorizar hasta a nivel de proceso!!!


Habilitando el autoescalado con ActiveScale

Bueno, la tapa de camarones y la caña están servidas sobre la mesa y queremos tomárnosla tranquilamente. ¿Qué hacemos? Pues activamos el autoescalado para no tener que preocuparnos de si el rendimiento del sistema es el adecuado a la vez que reducimos los costes a la carga de cada momento.

Para ello, accedemos a la configuración de ActiveScale desde el nivel 1 (cloud service) o nivel 2 (role) de monitorización del cloud service:


Y aquí las opciones más interesantes del servicio, no sólo porque permiten autoescalado automático basándose en el uso del site, sino que además permite habilitar tareas automáticas de mantenimiento de salubridad del sistema –que denominan “Automatic Healing”, como por ejemplo, reiniciar una instancia de role si se está por encima de un umbral de CPU durante un tiempo determinado, etc.


Habilitando las notificaciones

Bueno, además de que el sistema se ajuste a la carga, se autorecupere, etc. queremos recibir notificaciones de alerta por correo electrónico, por SMS, iOS messages, etc. si alguno de los servicios sufre algún incidente. ¿Qué hacemos? Alegremente vemos que este servicio también está incluido dentro de MetricsHub. Para habilitarlo, accedemos al menú de notificaciones desde la página de inicio pulsando sobre el menú “All Issues”.


Desde aquí podemos ver el histórico de incidencias en todos los servicios, tanto actuales como pasadas:


Pulsando sobre el botón de “Get Email Notifications…” podemos configurar cada una de las reglas para el envío de alertas por correo electrónico. Las opciones de activación de estas reglas se pueden parametrizar a través de la supervisión de umbrales de contadores, además de poder combinarlos entre ellos para la configuración de una regla:


Para acceder a la configuración de notificaciones por SMS, etc. simplemente tienes que crear una cuenta en PagerDuty. Este servicio es de pago, contando con una trial de 30 días.


Después de haber puesto en marcha un ejemplo de despliegue y hacer algunas pruebas de carga sobre el sistema he podido ver que efectivamente el servicio autoescala hacia arriba y abajo pasado el tiempo configurado. Las notificaciones llegan como se esperan y el detalle de las mismas es muy bueno. Acceder al interfaz de usuario desde dispositivos móviles cuando no estás delante de tu PC de sobremesa es genial, sobretodo cuando se comporta tan bien mostrando gráficas y todo tipo de detalles.

Recordando que este servicio se ofrece en modo “preview” de forma gratuita, sólo queda esperar qué se nos ofrecerá en un futuro. Yo por ahora, “lo compro” Smile

Me voy a por la tapa de camarones.

Un saludo y Happy Coding!

DotNetNuke Azure Accelerator 6.4 Released!

DNNCloudThe new DotNetNuke Azure Accelerator 6.4 is now available on CodePlex with very interesting new features, such as the awaited high availability, the automated SSL certificates setup, FTP and WebDeploy management, as well as a last-minute addition that allows to set the site offline to perform maintenance tasks. To download the latest version follow this link:

Download DotNetNuke Azure Accelerator 6.4

Release notes

New features

  • Changed the packages to use OSVersion=3 by default: Windows Server 2012 and IIS 8
  • Added Support for active and passive FTP. You can enable it in the wizard on the remote option settings step
  • Added a new package supporting co-located cache. Note that you still will need a DNN caching provider that implements it.
  • Changed IIS 8 settings to use site pre-load
  • Changed the appPool Startup mode to AlwaysRunning (see thishttp://blogs.msdn.com/b/vijaysk/archive/2012/10/11/iis-8-what-s-new-website-settings.aspx for more info)
  • Modified all the packages to support High Availability: now you can safely increase or decrease the number of roles serving the website. The VHD drive will be dinamically attached, shared and connected between all the workers. The process will recover from failures when the VM acting as SMB server goes down for whatever reason.
  • Support for App_Offline to do safer DNN upgrades stopping incoming webrequests. When you change the configuration setting "AppOffline.Enabled" to "true", the site will appear as offline but will be published on port 12242. You can then run the upgrade on that port (portal aliases will be dinamically added). After finishing the upgrade, set the "AppOffline.Enabled" to "false" to re-enable the site.
  • App_Offline file can be customized by dropping an HTML file on "/Portals/_default/App_Offline.htm
  • Added a new step in the wizard to setup SSL configuration, allowing to upload the SSL certificate and CA's certificates
  • Now you can reload the packages in the wizard without having to restart the process
  • The last subscription used will be the default one when launching again the wizard




Getting Started

The summary of steps for deploying DNN Community on Windows Azure is:

    1. You can sign-up for a free 3 month trial here http://www.windowsazure.com/es-es/pricing/free-trial/
    1. Download the DotNetNuke Wizard Accelerator package and uncompress it
    2. Run DNNAzureWizard.exe and follow the steps

If you have any comment or you find an issue, remember to visit the CodePlex discussion forums.

Enjoy it!

DotNetNuke Azure Accelerator 6.4 ya disponible!

DNNCloudYa está disponible en CodePlex la última versión del DotNetNuke Azure Accelerator con una serie de características muy interesantes, como la tan esperada Alta Disponibilidad, la configuración automatizada de certificados SSL, el acceso a los contenidos mediante FTP y WebDeploy, así como un añadido de última hora para poner el site offline para realizar tareas de mantenimiento. Para acceder a la descarga de esta última versión puedes seguir el siguiente enlace:

Descargar DotNetNuke Azure Accelerator 6.4

Notas de la versión

Nuevas características

  • Modificados todos los paquetes para soportar Alta Disponibilidad: ahora puedes aumentar o disminuir el número de instancias de rol de forma segura. La unidad VHD será montada y compartida dinámicamente, mientras que los roles cliente buscan y se conectan al recursos compartido del mismo modo. Este proceso se recuperará automáticamente de posibles caídas cuando la máquina virtual que actúa como servidor de ficheros se cae por cualquier motivo (fallo, actualización automática, sustitución del servidor por uno nuevo, etc.)
  • Modificados todos los paquetes para usar OSVersion=3 por defecto (Windows Server 2012 e IIS 8)
  • Añadido soporte para FTP activo y pasivo. Puedes habilitar la configuración automática de los servicios FTP en el paso de opciones de administración remota en el asistente
  • Modificadas las opciones de IIS 8 para usar pre-carga del site
  • Modificada las opciones del pool de aplicaciones para poner el modo de inicio a AlwaysRunning (ver http://blogs.msdn.com/b/vijaysk/archive/2012/10/11/iis-8-what-s-new-website-settings.aspx para más información)
  • Añadido un nuevo paquete con soporte para co-located cache. Nótese que aún así necesitarás un Caching Provider que implemente Windows Azure Cache no incluido en la solución
  • Soporte para App_Offline para realizar operaciones de mantenimiento, como las mismas actualizaciones de DotNetNuke, de forma más segura al no recibir webrequests durante dicho proceso. Cuando cambias la opción de configuración “AppOffline.Enabled” a “true” a través de la consola de administración de Windows Azure, el site aparecerá offline en los puertos 80 y 443, mientras que es publicado en el puerto 12242. De este modo puedes realizar el update en dicho puerto (se añadirán dinámicamente portal aliases para el mismo). Al finalizar las tareas de mantenimiento, vuelve a configurar la opción “AppOffline.Enabled” a “false” para volver a habilitar el site.El App_Offline puede ser personalizado creando un fichero en la ruta “/portals/_default/App_Offline.htm”
  • Añadido un nuevo paso en el asistente para configurar las opciones de SSL, permitiendo subir tanto el certificado del site como el de las entidades emisoras de los mismos.
  • Ahora puedes volver a cargar la lista de paquetes en el asistente sin tener que volver a iniciar el mismo
  • La última suscripción usada será la que esté seleccionada por defecto la próxima vez que inicies el asistente




Si tienes alguna sugerencia o comentario, o detectáis alguna incidencia, recordad visitar los foros de discusión en CodePlex.

¡Que lo disfrutéis!

¡Vuelve el Megathon 2013!

Por segundo año consecutivo, tendrá lugar el Megathon Windows, un hackathon que se celebra de manera simultánea en varias ciudades, donde tendrás la oportunidad de crear apps para Windows 8 y Windows Phone, aprender y conocer a otros programadores y ganar fabulosos premios.

Además como novedad, este año hemos preparado una serie de cursos y webcasts gratuitos de desarrollo de apps para Windows 8 y Windows Phone previos al evento para que puedas empezar a prepararte a fondo para el gran día.

¡Accede a la web del Megathon Windows para apuntarte a los cursos y no olvides registrarte en alguna de las ciudades que ya tenemos confirmadas!

¡Empieza a prepararte! ¡Contamos contigo!

[DNN Azure Accelerator] Le damos la bienvenida a la Alta Disponibilidad

high_availabilityUna de las características más solicitadas en el DotNetNuke Azure Accelerator es la posibilidad de poder hacer despliegues en alta disponibilidad (añadiendo dos o más roles) y que además no existan problemas de recuperación en caso de que el acceso a los contenidos almacenados en el VHD sea interrumpido. Si bien en la actualidad se podían hacer despliegues de más de un servidor para servir los contenidos (modo webfarm), en el caso de que el servidor que montaba la unidad VHD cayera por algún motivo –como que Microsoft hiciera un mantenimiento planeado haciendo un upgrade del cloud service- podía acabar en que el site dejara de estar disponible.

Todo esto tiene su raíz en la exclusividad que mantiene sobre el blob el role que monta el VHD, a través del mantenimiento de leases sobre el mismo, no permitiendo a los demás roles montarlo en modo lectura/escritura.

Nuevas características en el DNN Azure Accelerator

Antes de comenzar a detallar cómo funciona el nuevo sistema de “competición por el lease”, echemos un vistazo a las nuevas características implementadas en el Accelerator desde su última versión y que he ido añadiendo a lo largo de los últimos meses:

  • Solución actualizada al Azure SDK 1.8 (October 2012)
  • Modificado el sistema operativo predeterminado de los paquetes a OSVersion=3 (Windows Server 2012, IIS 8)
  • Añadido soporte para servicio FTP (activo y pasivo)
  • Corregida la causa por la que en determinadas ocasiones el site no se iniciaba correctamente tras reiniciar el role (ver este enlace para más información)
  • Añadido nuevo paquete con soporte para co-located caché
  • Añadido soporte de pre-carga del sitio y modo de inicio del appPool en AlwaysRunning, características de IIS8 (ver este enlace para más información)
  • Arquitectura modificada añadiendo soporte para Alta Disponibilidad

Antes de empaquetar la nueva versión, voy a realizar algunos cambios en la interfaz de usuario para acomodar las nuevas opciones de configuración como las del servicio FTP, etc.

Alta Disponibilidad: compitiendo por el lease

A la espera de que Microsoft saque la solución definitiva a este problema de leases sobre los VHD, la nueva implementación realizada en el DNN Azure Accelerator minimiza estos efectos para estar dentro de los márgenes del SLA de alta disponibilidad de Windows Azure.

La solución está basada en la actualización del post de Dinesh Haridas -artículo en el que está inspirado el DNN Azure Accelerator- en el que se introduce una aproximación a la alta disponibilidad con una técnica de competición por el VHD.

Por simplificación, centremos el problema de la alta disponibilidad en las operaciones alrededor del VHD donde residen los contenidos del site. Estas operaciones serán realizadas entre dos roles: SMBServer, que actúa como el servidor de contenidos; SMBClient, que actúa como servidor que se conecta a la unidad compartida por el servidor de contenidos.

El resumen de las operaciones realizadas en el role que comparte los contenidos es:

  • SMBServer (1 o más instancias)
    • Cada X segundos (en el evento OnRun), intenta montar el VHD (Compete for the lease)
      • Si tiene éxito:
        • comparte la unidad con un “NET SHARE”
        • Cada X segundos sigue comprobando que tiene el lease. Si no lo tiene, elimina el share y vuelve al principio

Tal y como se observa, todos los roles que actúan como servidor de ficheros están continuamente compitiendo por el lease del VHD. El lease actual, que se mantiene durante 60seg por el driver del servidor que monta con éxito el VHD, asegura que la unidad siga estando en posesión del mismo servidor mientras sea posible. Por este motivo, en caso de caída del role que comparte los contenidos, la recuperación completa toma entre 60 y 90seg. Si tenemos en cuenta que ésto sólo ocurre cuando actualizamos el servicio –o cuando Microsoft realiza una operación de mantenimiento, normalmente una vez cada 2 o 3 meses-, si bien no es perfecto, entra dentro de los márgenes del SLA de Azure.

El resumen de las operaciones realizadas en el role que actúa como cliente es:

  • SMBClient (1 o más instancias)
    • Cada X segundos (en el evento OnRun), intenta mapear una unidad de red con el share del role SMBServer, iterando sobre todas las instancias del mismo
      • Si tiene éxito:
        • Cada X segundos escribe en un fichero de log en la carpeta “\logs”. Si ocurre un error al escribir dicha entrada, elimina la unidad mapeada y vuelve al principio

En el caso del servidor SMBClient, se hacen varios reintentos de escritura en el log antes de comenzar de nuevo el proceso de mapeo para evitar falsos positivos.


En el archivo adjunto está la solución simplificada que sirve de demostración por si a alguien le interesan los detalles.

  • AcceleratorHADemo.zip (334Kb) – Descargar

Implementación en el Accelerator

La implementación final en el Accelerator también está disponible en CodePlex. Cabe destacar las siguientes características en la implementación final:

  • El código de creación del site en el IIS se ha movido justo después del intento exitoso de mapeo de la unidad de red en el webrole
  • Existen tres cloud services distintos dentro de la solución:
    • DNNAzureSMB: mantiene worker roles (SMBServer) y webroles (DNNAzure) separados para cada operación. Si bien lo normal es usar el menor número de servidores posible, hay escenarios donde, por rendimiento, no se desea sobrecargar a un webrole con las tareas de servir también los archivos al resto de instancias. Es por ello que se sigue manteniendo esta solución.
    • DNNAzureSingle: al desplegar este cloud service, los webroles (DNNAzure) actúan también como servidores de contenidos compitiendo por el lease del VHD. Para ello se mantienen dos threads: uno para competir por el lease y realizar las tareas propias del SMBServer y otro para realizar el mapeo de red y las tareas propias del SMBClient. Este será normalmente el paquete a desplegar en la mayoría de los escenarios.

Aún queda una problemática por solucionar, y es el escenario donde se usa FTP o WebDeploy y has desplegado más de una instancia de los webroles. Esto es debido a que estos protocolos requieren afinidad a nivel de protocolo de comunicaciones y la implementación actual del Load Balancer de Azure no permite especificar la misma. Como “workaround” para esta incidencia –y hasta que Microsoft lo solucione a nivel de Load Balancer- la solución pasaría por añadir un tercer webrole para estos servicios que requieren afinidad y desplegar sólo una instancia del mismo. 


Con esta versión se soluciona el problema de alta disponibilidad en el DNN Azure Accelerator así como el problema de actualización del servicio, ya esté en alta disponibilidad como si no, con lo que será una actualización recomendada para todos los despliegues que actualmente estén usando el DNN Azure Accelerator.

En breve realizaré un empaquetado y estará disponible como descarga en CodePlex. Si tienes alguna sugerencia, no olvides dejar tus comentarios, ya sea en este mismo blog o como una entrada en el área de discusiones de CodePlex.

Un saludo y Happy Coding!

Más artículos < Página anterior - Página siguiente >