Sunday, April 30, 2017

The case for multiple Azure Automation Accounts

Most of my recent work has, in some way, involved the use of the Azure Automation service.  It is a pretty versatile service that can be used for a lot of IT automation needs.  As I start to use Azure Automation in more complicated scenarios, I have run into some security considerations that has got me wondering if the right approach is to have multiple Automation accounts in a given environment.  The goal of this post is to discuss this a bit further.

In Azure automation, there are three "integration" points where security might come up as an issue.  The first is governing who has access to the particular automation account.  Microsoft has come up with a set of user roles that can help control access to the account itself.  Of course, you can always make use of azure custom roles to make further customization to the granularity.  The second is around the credential/secret access that the automation account has been setup with.  These elements are configured within an account and every runbook in the account could, in theory, access those resources.  The third is in the use of hybrid workers.  Workers are configured at the account level, and then, can be selected as the run destination for a given runbook.

Take the following scenario as an example.

I would like to execute startup/shutdown scripts across multiple environments (say dev/test/prod) and have them run by users as required. 

Working through the above defined integration points, the first point to consider would be that of user security.  At some point, someone has to be the owner of the Automation Account, and thus, that owner would effectively have access to all resources within it.  This goes the same even if RBAC is used (out of the box).  Users with the automation operator role would still have access to run all runbooks in the account regardless of the environment it is targeting, or that they actually have authority over.

Moving to the second point, run-as accounts are configured at the Automation account level.  Run-as accounts have no granular permissions and therefore can be accessed by any runbook.  While you can control who can author a runbook, you can't control what run-as accounts the runbook uses.  Further, you can enforce user security on this.  In an ideal state, a runbook could accept a run-as account as a parameter and then ensure that the user actually has access to use that account.  Permissions in Azure automation are not that granular.

The third aspect, hybrid worker, generally only comes into play when you are executing activities that require network access to the operating system itself.  When you setup a hybrid worker, you essentially get another prompt when running the runbook, requesting "where" you would like to execute the particular runbook.  Once again, there is no user level security here.  Everyone who can run a runbook can also select the hybrid worker group to run on.  Further, you cannot actually configure a runbook to ONLY run on a particular destination (unless you use a webhook or schedule).  So, even users with only the "automation operator role" can still run runbooks where they are not supposed to.

So what is the solution? When I first setup the build/release management in VSTS online, I was amazed at the amount of permissions, etc, you need to grant to make something even somewhat useable.  You could run into the scenario where you had access to run a build on a project, but no access to any agents to actually execute the build on.  Credentials could be stored as part of a release line, but not used by any other release lines. Permissions to view those could be granted only to the people that needed them.  To be honest, it seemed tedious, but in retrospect, that is the level of granularity that was required in order to truly make the system multi-tenant.

From an azure automation perspective, I feel like the easiest solution is to create multiple automation accounts.  One per environment that it is targeting.  Then grant permissions to the automation account as required for the people that need it.  Keeping runbooks in sync between environments is frustrating, but the integration is coming along with github and VSTS that will make things easier.  While I still feel a VSTS approach is better off in the long run, multiple automation accounts seems to solve the problem at an environment level quite nicely.

Monday, April 24, 2017

Azure Cost Optimizations: Azure VMs

Compute time is one of the most expensive services one can use in the Azure stack.  The goal of this post is to discuss some of the ways you can optimize the amount of compute you use.  Please note that the compute profile of your workloads will vary, so your mileage using any of the suggestions below will vary.

1) Monitor monitor monitor

Azure has recently released a few new features from a monitoring perspective.  Most of these capabilities are merging into what they call Azure Monitor.  What I particularly like about Azure monitor is the ability to see both host level and guest level metrics.  As with all performance monitoring of this type, you need to have a good understanding of how the data is sampled on the system.


As you can see, I've made a few changes to the sample rate for my VMs.  This was particularly important during load testing I was conducting at my client.

The key point here is that you can start to use these monitoring tools to help determine more appropriate VM sizes for your workloads.  Integrating tools such as OMS can greatly help as you can start to trend performance over time.

One tool that I have run into but have not had the chance to use is the Azure Virtual Machine Optimization Assessment.

2) Switch to batched/scheduled workloads

As you pay for compute only when your virtual machine is running, you can start to play around with batched and/or scheduled workloads.  The essence here is to find an orchestration tool that you can use to manage when your virtual machines are running.  Taking this one step forward, ideally the orchestration engine also only runs the virtual machine for the required amount of time.

Two services that one can look at here are Azure Batch and Azure VMSS.  The later here is more around autoscaling and trying to achieve performance curves that match closer to the demand curves.

3)  Shutdown/Startup VMs

One technique that I am particularly fond of is the automatic startup and shutdown of VMs when they are required.  There are several different ways to accomplish this in the Azure cloud, including using Azure Dev/Test Labs and Azure Automation.  The former has created a VM extension that can be used to autoshutdown the machines.  There is even some built-in runbooks for using tags to schedule startup and shutdown.

There are a few pros/cons to the above approaches which I can cover in another post, but suffice to say, one thing to consider here is the order in which startup/shutdown occur.  Many environments, even dev/test, can be complex and have dependencies.  Generally for this reason, I tend towards an Azure Automation approach to starting up and shutting down VMs.

There are a host of methods and processes for tuning VMs (not just in Azure).  You can use most of those techniques with Azure, just having to change how you get access to the underlying metrics you are relying on.  As always, starting and shutting down VMs can save quite a bit of money in the long run.

Thursday, April 20, 2017

Creating a new Managed Disk from a Managed Disk Snapshot

It turns out that the operation is quite easy.  The New-AzureRmDiskConfig has an option to reference a source resource id  This ID can be found in the portal (or via powershell) when you click on a managed disk.  Simply input that when you create a new disk (as shown below) and it will create a new disk based off of your snapshot.


$diskConfig = New-AzureRmDiskConfig -CreateOption Copy -SourceResourceId "id from portal" -Location westus -DiskSizeGB 64 -AccountType StandardLRS
$disk = New-AzureRmDisk -DiskName "name" -Disk $diskConfig -ResourceGroupName "rgname"


Official documentation can be found here.