Enabling Notepad++ as an Editor for Azure Resource Manager Templates

When you begin working with Azure Resource Manager templates, you will immediately need a JSON  editor to work with the Azure Resource Manager template language. While your best option is Visual Studio (more on this in another post), it is not free and may not be an option if you do not have an MSDN subscription or generous employer. NOTE: Individuals, small teams, and others who qualify can also use Visual Studio Community Edition, which is free for non-commercial use or open source projects, academic research, training, education. More on that at https://www.visualstudio.com/en-us/products/visual-studio-community-vs.aspx.

One free option is to leverage Notepad++. While Notepad++ does not support JSON out-of-box, there is a fairly good JSON plug-in for Notepad++ available at  http://sourceforge.net/projects/nppjsonviewer/?source=typ_redirect. You install this plug-in like most others for Notepad++…by simply copying a .dll to the \plugins folder and re-launch Notepad++.

Now you can open an existing template from the samples available online. To enable the functionality Notepad++ json plugin, start by selecting your json template with Control+A, or Edit–> Select All.

Then, select Plugins –> JSON Viewer –> Show JSON Viewer.








This will parse the template and present it in the JSON Viewer in a left navigation pane.













While this is not ideal, it does provide some basic functionality for validating JSON syntax as you piece together new deployments from existing ARM JSON templates.

Inside the MS Cloud Episode 4 – Hybrid Identity with EMS

If you are interested in learning more about Microsoft’s Enterprise Mobility Suite, and come spend an hour with Azure expert and PowerShell automation Guru Wes Kroesbergen. Wes works with SoftChoice, billion dollar+ LAR, where he specializes in EMS deployment for clients of all sizes.

When it comes to EMS, my buddy Wes knows his stuff! He brings both technical expertise and real-world experience to what I think was an interesting session.

Watch epdisode 4 at http://ipn.tv/imc4/

Sample Azure Automation Runbooks from My #MVPvConf Session

I’ve had some requests for the Azure Automation runbooks I used in my Azure Automation webhooks demo in my MVP Virtual Conference session. To ensure they are easily accessible, I have published them to the Microsoft Technet Gallery. The runbook titles and links are listed below.

Start All VMs in Specified Azure Resource Group

Stop All VMs in Specified Azure Resource Group

The session recording should be available on the Channel 9 website (http://channel9.msdn.com) in the next few days.

Quick Tip: Using Azure Resource Manager PowerShell Cmdlets in Azure Automation

This tip addresses a problem you are sure to have if attempting to work with the Azure Resource Manager (ARM) PowerShell cmdlets within Azure Automation in May 2015. I should preface by sharing that I believe this situation may change as the story evolves with Azure Resource Manager (ARM) and PowerShell, as the Azure Automation team may still be working on optimizing the user experience.

The Problem

When you attempt to use Get-AzureVM and some other cmdlets in the ARM PowerShell module, they fail due to incorrect parameters. If like me, you test your runbooks in Visual Studio or the PowerShell ISE before copying into Azure Automation, this error will be confusing.

There are two issues here:

  • The ARM PowerShell module is not present in Azure Automation by default.
  • The ARM cmdlets (which support much of the Azure IaaS v2 functionality announced at Build and MS Ignite, such as JSON deployment templates) and the Azure Service Management cmdlets (used in most Azure IaaS v1 operations) functionality have cmdlets with the same names, but different parameters.

Step 1: Zip and Import the Azure Resource Manager PowerShell Module

If you installed the latest Azure PowerShell cmdlets, the default path on a 64-bit OS (as of May 2015) is shown below.

C:\Program Files (x86)\Microsoft SDKs\Azure\PowerShell\ResourceManager\AzureResourceManager

Zip up this directory and all the files and folders in it, which will include AzureResourceManager.psd1. As you zip the folder, the file name should default to AzureResourceManager.zip.

Step 2: Upload the Module to Azure Automation

To upload the ARM PowerShell module in the Azure Preview Portal, which is designed to support the new Azure IaaS v2 capabilities, perform the following steps:

1) Login to the Azure Preview Portal at https://portal.azure.com
2) Select Browse from the left navigation pane.
3) Then select Automation Accounts, followed by your Azure Automation account.
4) Next, click on Assets, then Modules
5) Click on Add a module and browse to the zip file containing the ARM module you zipped in the previous task.
6) Select Open, then OK to upload.


Give Azure Automation a few minutes to consume the module and extract the cmdlets. You will see a message in the Notifications area when the operation is complete.

New Problem

Once you upload the ARM PowerShell module, you have a new problem: the ARM and Azure Service Management (ASM) PowerShell modules have quite a few key cmdlets with the same names. Since the ASM cmdlets are present by default, those cmdlets seem to be called first, even after you have uploaded the ARM module to your Azure Automation subscription.

Workaround: Specify the path when calling ARM cmdlets

This simply means that when you wish to call a cmdlet in the ARM PowerShell Module, you must specify the path, like so


So to call Start-AzureVM from the ARM PowerShell module, you would type AzureResourceManager\Get-AzureVM

To see a working illustration of this concept, you can view and use a sample runbook I provided in the Microsoft Technet Gallery at the URL below:


I hope this helps. If you’ve encountered other challenges working with the ARM cmdlets and Azure IaaS v2 in Azure Automation, I would be interested to hear about your experience in the Comments section below.

Inside the Microsoft Cloud Podcast #1 – Show Notes

It’s official, we have just finished recording episode 1 of the Inside the Microsoft Cloud Podcast! We kicked things off with a recap of the a announcements from the Microsoft Build conference last week, along with a look at what to expect from the Microsoft Ignite conference in Chicago this week.

Watch the podcast on YouTube at https://youtu.be/1jGLb8VCGms. Show notes are below.

Build Announcements

Build Day 1


Build Day 2



MVP Virtual Summit


Surface Pro 4 Rumor Mill


Git Integration

GitHub Integration


MS Announcement


The E-Book


Git Integration for Visual Studio


Git Integration for PowerShell ISE


Automating Dev Box Creation



JSON (JavaScript Object Notation)


Azure IaaS Templates



Cinco de Mayo

http://en.wikipedia.org/wiki/Cinco_de_Mayo http://trekgeeks.com

How to stop and start Azure VMs in bulk

Starting and stopping Azure VMs in bulk is pretty easy in PowerShell, but you want to filter your VMs based on the correct property. VMs have a Status property that includes StoppedDeallocated, Stopped, RoleReady, etc. If you are attempting to identify VMs based on status, your PowerShell will have to write your script to filter on multiple criteria.

A better option is to use the PowerState property. Your VMs are going to have a PowerState of “Started” or “Stopped”, so turning them on (or off) in bulk based on this property is quite simple. You could take these one-liners into simple Windows scheduled tasks to turn your development and test environments down after quitting time and bring them back online before the team gets into the office the next morning, reducing your Azure spend on non-production compute resources.

Below are a handful of one-liners and a description of the nuances of each.

This first one-liner will shut down every VM in your subscription, but you will be prompted on the last / only VM in a cloud service with an “continuing will result in a new IP address for your deployment” message, and further direction that using the -StayProvisioned parameter will ensure your VM will keep it’s IP address. However, when you use that parameter, the VM remains provisioned, so you also keep getting billed. For test and dev environments, dynamic DNS registration and short time-to-live (TTL) on DNS records should be good enough to allow you to simply shutdown and deallocate to save dollars.

Get-AzureVM |  Where-Object {$_.powerstate -eq ‘Started’} | Stop-AzureVM

If you add the -Force parameter to the end of the one-liner (as shown below), the VMs are stopped and deallocated (meaning you are only being billed for the storage they consume) without the prompt.

Get-AzureVM |  Where-Object {$_.powerstate -eq ‘Started’} | Stop-AzureVM -Force

Replace the -Force parameter with -StayProvisioned as shown below and the annoying prompt is still avoided, but your VMs wind up in with a status of “Stopped” instead of “StoppedDeallocated”. This means the VMs will come back online with the same IP address, but the billing does not stop between power off and the next power on.

Get-AzureVM |  Where-Object {$_.powerstate -eq ‘Started’} | Stop-AzureVM -StayProvisioned

To start the VMs up again, you can simply reverse the flow with a couple of small changes, as shown below.

Get-AzureVM |  Where-Object {$_.powerstate -eq ‘Stopped’} | Start-AzureVM

Naturally, you can add multiple criteria to the Where-Object filtering to filter based on VM name, cloud service name and other properties to shut down specific subsets of your VMs. In a future post we will look at scheduled tasks, time-based actions and moving this process into Azure’s PowerShell Workflow based orchestration engine, Azure Automation.

How to find if an Azure VM exists via PowerShell

One task that can be help to optimize deployments in Azure is checking for the existence of a VM before you attempt to deploy. This can be particularly useful when you attempt to restart a failed deployment of multiple VMs. Because every VM in Azure resides within a cloud service, checking for a VM can be a bit more work than in an on-premises scenario with VMM and Hyper-V.

If you know the name of the service the VM should reside within your Azure subscription, the check is quick and easy.

if (!(Get-AzureVM -ServiceName "MyCloudService" -Name "MyVMName"))

On the other hand, sometimes you will not know which cloud service the VM resides in (as when generating random cloud service names in a bulk deployment). In this case, you will need to check every cloud service for the existence of the VM. The function below is one example of to determine if a VM exists within an Azure subscription if you do not know the name of the cloud service. The last line calls the function and provides the name of  a VM.

 Function Check-AllServices4VM ($vmName) {

 $cloudServices = Get-AzureService 

 ForEach ($Service in $cloudServices) {

 If (Get-AzureVM -ServiceName $Service.ServiceName -Name $vmName) {

 Write-Host "Azure VM by that name already exists in service " $Service.ServiceName " ...terminating"
    Write-Host "Azure VM does not exist is service " $Service.ServiceName
 } # end of function 

 # Call the function and provide VM name
 Check-AllServices4VM -vmName SQLClient

That’s all for today. Leave any thoughts in comments.

How to Create an Azure SQL Database via PowerShell

As I mentioned yesterday in “How to Create an Azure SQL Instance via PowerShell“, Azure SQL provides some cost advantages over running SQL in Azure VMs for scenarios where all you need is a database. In yesterday’s article, we created an Azure SQL database instance, as well as a firewall rule on the instance to allow remote connections.

Now, we are ready to create a database in our new Azure SQL instance. Start by connecting to your Azure subscription in the standard manner (see resources in the article linked above if connecting to your Azure sub in PowerShell is not familiar).

Then, we create a credential to store the user and password we will use to authenticate to the Azure SQL instance.

$User = “pzerger”
$PWord = ConvertTo-SecureString –String ‘Pa$$w0rd!’ –AsPlainText -Force
$Credential = New-Object –TypeName System.Management.Automation.PSCredential `
–ArgumentList $User, $PWord

Next, we will connect and authenticate to the instance.

$sqlContext = New-AzureSqlDatabaseServerContext `
-ServerName “xne7lwczta" -Credential $Credential

Then, we will select the level of service, which determines the max database size, connection and session count, and transaction rate. There are many levels of service across the Basic, Standard and Premium tiers. You can find a current list of available  https://msdn.microsoft.com/en-us/library/azure/dn741336.aspx.

In this example, I will specify S0, the lowest level of the Standard tier, and provide along with that the sqlContext object from the previous step, which stores the SQL instance name and credentials.

$S0 = Get-AzureSqlDatabaseServiceObjective `
-Context $sqlContext -ServiceObjectiveName S0

In the last step, we create the database. In this case, I am creating a database named “InsideTheMSCloud”.

New-AzureSqlDatabase -ConnectionContext $sqlContext `
-DatabaseName “InsideTheMSCloud" -Edition “Standard” -MaxSizeGB 1 `
-Collation “SQL_Latin1_General_CP1_CI_AS” -ServiceObjective $S0

Now we have a Azure (PaaS) SQL instance, a firewall rule to allow remote connections and a database. In the next post on this topic, we’ll do something with this database.

How to Create an Azure SQL Instance via PowerShell

I wanted to share a bit about Azure SQL (PaaS) in Azure, as I believe it will commonly used by IT Pros in the future, particularly as a logging and reference databasew when working with Azure Automation. One compelling reason to Azure SQL instance of SQL Server in Azure VMs is cost. If you just need a little database, you can have what you need in Azure SQL for as little as free or a few cents a month. SQL Server in Azure VMs is going to cost the price of the VM and the SQL license if you don’t bring your own. You can read about the differences between the two at http://azure.microsoft.com/en-us/documentation/articles/data-management-azure-sql-database-and-sql-server-iaas/.

To create an Azure SQL Server instance, start by connecting to your Azure subscription in PowerShell as you normally do. If you are unsure of the steps, see http://azure.microsoft.com/en-us/documentation/articles/powershell-install-configure/.

Next, we create an Azure SQL instance as follows. This creates a new Azure SQL Server instance, with a random name chosen by Azure.

#Create Azure SQL Server
$location = 'East US'
$login = 'pzerger'
$password = 'Pa$$w0rd!'
$newSqlServer = New-AzureSqlDatabaseServer -Location $location -AdministratorLogin $login `
-AdministratorLoginPassword $password -Version "2.0"

Get the name of the Azure SQL instance name like so:


All connections to this SQL instance will be blocked by default, so you need to create a firewall rule to allow all connections. For this one, I just create a rule to allow connections from any IP address.

New-AzureSqlDatabaseServerFirewallRule -ServerName $newSQLServer.ServerName `
-RuleName "Allow all IP addresses to connect" `
-StartIpAddress -EndIpAddress

Now we have an Azure SQL Server instance that allows connections from any IP Address. In a future post, we will connect and create a database and start making use of our resources.

Retrieve the latest version of a Gallery Image in Azure PowerShell

Here is a handy snippet I use fairly often. When you retrieve an Azure gallery image by name, you will find there are multiple versions of the image.

Get-AzureVMImage -Verbose:$false | Where-Object {$_.label -like “Windows Server 2012 Datacenter*”} | Select-Object Label, PublishedDate

You will typically find at least two versions of each image, which can be differentiated by date, as shown below.

Label       PublishedDate
—–         ————-
Windows Server 2012 Datacenter, February 2015 2/11/2015 2:00:00 AM
Windows Server 2012 Datacenter, March 2015 3/12/2015 2:00:00 AM

Finding the latest image is as simple as retrieving all of them and sorting in descending order based on the published date. The code below will arrange the images in descending order by published date, then retrieve the first in the list.

(Get-AzureVMImage -Verbose:$false | Where-Object {$_.label -like “Windows Server 2012 Datacenter*”}| Sort-Object –Descending PublishedDate)[0].ImageName

We can save this result to a variable and proceed with deployment.

$winImageName = (Get-AzureVMImage | where {$_.label –like “Windows Server 2012 Datacenter*”} | sort PublishedDate -Descending)[0].ImageName

I’ll follow this post with a many more in this vein, offering some tips to optimize your Azure scripting.