Azure Automation State Configuration – Installing Common DSC Modules
Azure Automation State Configuration (previously Azure Automation DSC), is a service provided by Azure that allows you to write, manage and compile PowerShell Desired State Configuration (DSC) configurations and assign these configurations to target virtual machines (or any server or workstation to be honest). On its own, State Configuration provides some basic configuration examples, but its true power comes form the ability for you to define your own configurations.
Azure Automation State Configuration
Azure Automation State Configuration (previously Azure Automation DSC), is a service provided by Azure that allows you to write, manage and compile PowerShell Desired State Configuration (DSC) configurations and assign these configurations to target virtual machines (or any server or workstation to be honest). On its own, State Configuration provides some basic configuration examples, but its true power comes form the ability for you to define your own configurations.
User created configurations need to be imported and compiled before the configuration is applied to a virtual machine. It is common when creating DSC configurations to rely on a variety of DSC Resources. The modules containing these resources need to be imported into Azure Automation for it to be able to compile any configuration. So how do we import and update these modules?
The first mechanism to manage the PowerShell modules is through the Azure Portal, by going to your Automation Account > Shared Resources > Modules. Here you can add modules from a zip file, update the built in Azure modules, or add modules from the PowerShell Gallery. This provides a simple mechanism particularly if you are starting; unfortunately, most production configurations will need multiple modules, making the Azure Portal difficult to use.
We can also manage modules via ARM templates. Define the template is relatively straight forward but requires a couple of tricks to get started. I will put together a separate blog post on how you can define your own ARM template.
Accelerating Adoption
I wanted to help those starting out with State configuration. My goal was to help accelerate new State Configuration deployments, by creating a “starter” ARM template that would install the most common PowerShell DSC modules that are in the PowerShell Gallery and the most common in my production DSC configurations. This ARM template could also be used to ensure that the modules are also updated on a regular basis.
So what modules are included? I selected 32 modules in the end. These cover the configuration of core Windows, Windows Server roles and features, security hardening, package management and Chocolatey. Most of the modules are maintained by Microsoft, however four modules, cChoco, cSpeculationControlFixes, UpdateServicesDSC and xSystemSecurity that are maintain by members of the community.
| Module Name | Author | Description |
|---|---|---|
| ActiveDirectoryCSDsc | Microsoft Corporation | This DSC Resource module can be used to install or uninstall Certificate Services components in Windows Server. |
| AuditPolicyDsc | Microsoft Corporation | The AuditPolicyDsc module allows you to configure and manage the advanced audit policy on all currently supported versions of Windows. |
| cChoco | Chocolatey Software Lawrence Gripper Javy de Koning | Chocolatey DSC Resources for use with internal packages and the community package repository. Learn more at http://chocolatey.org/ |
| CertificateDsc | Microsoft Corporation | This module includes DSC resources that simplify administration of certificates on a Windows Server |
| ComputerManagementDsc | Microsoft Corporation | The ComputerManagementDsc module is originally part of the Windows PowerShell Desired State Configuration (DSC) Resource Kit. This version has been modified for use in Azure. This module contains the xComputer and xDisk resources. These DSC Resources allow you to perform computer management tasks, like joining a domain or initializing disks. |
| cSpeculationControlFixes | Kieran Jacobsen | PowerShell DSC for enabling Speculation Control fixes on Windows Server |
| DFSDsc | Microsoft Corporation | DSC resources for configuring Distributed File System Replication and Namespaces. |
| GPRegistryPolicy | Microsoft Corporation | Module with cmdlets to work with GP Registry Policy .pol files |
| GPRegistryPolicyParser | Microsoft Corporation | Module with parser cmdlets to work with GP Registry Policy .pol files |
| NetworkingDsc | Microsoft Corporation | Module with DSC Resources for Networking area |
| PackageManagementProviderResource | Microsoft Corporation | Module with DSC resources for the package management. |
| PSDscResources | Microsoft Corporation | This module contains the standard DSC resources. Because PSDscResources overwrites in-box resources, it is only available for WMF 5.1. Many of the resource updates provided here are also included in the xPSDesiredStateConfiguration module which is still compatible with WMF 4 and WMF 5 (though that module is not supported and may be removed in the future). |
| SecurityPolicyDsc | Microsoft Corporation | This module is a wrapper around secedit.exe which provides the ability to configure user rights assignments |
| SqlServerDsc | Microsoft Corporation | Module with DSC Resources for deployment and configuration of Microsoft SQL Server. |
| StorageDsc | Microsoft Corporation | This module contains all resources related to the PowerShell Storage module, or pertaining to disk management. |
| UpdateServicesDsc | Michael Greene | Module with DSC Resources for deployment and configuration of Windows Server Update Services. |
| WindowsDefender | Microsoft Corporation | Windows Defender module allows you to configure Windows Defender settings. |
| xActiveDirectory | Microsoft Corporation | The xActiveDirectory module is originally part of the Windows PowerShell Desired State Configuration (DSC) Resource Kit. This version has been modified for use in Azure. This module contains the xADDomain, xADDomainController, xADUser, and xWaitForDomain resources. These DSC Resources allow you to configure and manage Active Directory. |
| xDhcpServer | Microsoft Corporation | Module with DSC Resources for DHCP Server area |
| xDismFeature | Microsoft Corporation | Module with DSC Resources for Deployment Image Servicing and Management features. |
| xDnsServer | Microsoft Corporation | Module with DSC Resources for DNS Server area |
| xFailOverCluster | Microsoft Corporation | Module containing DSC resources used to configure FailOver Clusters. |
| xInternetExplorerHomePage | Microsoft Corporation | This DSC Resources can easily set an URL for the home page of Internet Explorer |
| xPendingReboot | Microsoft Corporation | This module identifies pending reboots in Windows Server and acts on them. |
| xPSDesiredStateConfiguration | Microsoft Corporation | The xPSDesiredStateConfiguration module is a part of the Windows PowerShell Desired State Configuration (DSC) Resource Kit, which is a collection of DSC Resources produced by the PowerShell Team. This module contains the xDscWebService, xWindowsProcess, xService, xPackage, xArchive, xRemoteFile, xPSEndpoint and xWindowsOptionalFeature resources. |
| xRemoteDesktopAdmin | Microsoft Corporation | Module with DSC Resources for enabling administrative Remote Desktop Connections |
| xSmbShare | Microsoft Corporation | Module with DSC Resources for SmbShare area |
| xSystemSecurity | Arun Chandrasekhar | Handles Windows related security settings like UAC and IE ESC. xUAC enables or disables the User Account Control prompt, while xIEEsc enables or disables IE Enhanced Security Configuration. |
| xTimeZone | Microsoft Corporation | This DSC Resources can easily set the System Time Zone. |
| xWebAdministration | Microsoft Corporation | Module with DSC Resources for Web Administration |
| xWindowsEventForwarding | Microsoft Corporation | This module can be used to manage configuration of a Windows Event Forwarding server in a Collector role. |
| xWindowsUpdate | Microsoft Corporation | Module with DSC Resources for Windows Update |
| xWinEventLog | Microsoft Corporation | Configure Windows Event Logs |
Want to get started and use the template?
You will need an Azure Automation account to start.
You can then use the Deploy to Azure button on the Git Repository or download the latest release and deploy using Azure CLI or PowerShell.
What to contribute?
The project is up on GitHub and I welcome everyone to make suggestions and recommendations. If you need a had with your first PR, check out this guide from egghead.io. I have connected this project to Azure DevOps build pipelines so all PRs will be validated for any issues.
PowerShell 5, DSC, SABnzbd and Sonarr (Part 1)
I have been trying to do a lot more with PowerShell DSC of late, including writing my own DSC resources.
Last week, I decided to write some resources for SABnzbd and Sonarr. Why? Well firstly for practice, but also because no one else has looked at building up packages for these apps (there wasn’t even Chocolatey packages).
I am not going to go into detail on implementing classes in PowerShell, instead checkout:
- Lee Holmes - Playing with Classes in PowerShell v5 Preview
- Trevor Sullivan - Implementing a .NET Class in PowerShell v5
- Jacob Benson - Creating a Class based DSC Resource using PowerShell
- David O'Brien - Windows PowerShell DSC - classes - introduction (part 1)
- David O'Brien - Windows PowerShell DSC - classes - resource basics (part 2)
- Microsoft MSDN - Writing a custom DSC resource with PowerShell classes
SABnzbd
The module cSABnzbd contains a single resource: cSABnzbdInstall. This resource specifying:
- Ensure: <String> { Ensure | Absent }
- ServiceCredential: <PSCredential>
If you opt for Ensure to be “Present”, then the resource will install and update SABnzbd. That is right, as new versions are released, it will be automatically updated.
The ServiceCredential allows for us to control what account the SABnzbd services run as. If not specified, LocalHost will be used.
GetLatestVersion()
SABnzbd hosts both its source code and its binary releases in GitHub. This is great! GitHub provides a simple REST API that allows us to very easily and dynamically get the latest release for a project.
If we want to get information on the latest release for a particular repository, we simply perform a get request on https://api.github.com/repos/{owner}/{repo}/releases/latest. The response will contain things like the version name, the release date and the assets in the release. The GitHub API doesn’t need any authentication credentials or tokens; these requests can be performed anonymously.
Performing the API request for sabnzbd the URL for us would be https://api.github.com/repos/sabnzbd/sabnzbd/releases/latest, and the returned information looks like:
The function is pretty simple:
Get()
The Get() function is quite easy to implement. We simply need to call Get-Package, and sets the result against the ensure parameter. We then return the object as required. The result is:
Test()
The Test() is also pretty simple. We use Get-Package again to see if the package is installed or not.
If Ensure = ‘Present’, then we need to check:
- If no package was returned, then return false
- If it is installed, compare the installed version to the version number returned using GetLatestVersion()
If Ensure = ‘Absent’, then we simply compare $Package to $null.
Set()
Now the Set() function is more complex.
If Ensure = ‘Present’, then we need to:
- Find the latest .exe in the release information using GetLatestVersion()
- Download the file, this is listed under the assets (look for a .exe).
- Silently run setup using the /S switch
- Install and start the services (optionally running under the user account specified with ServiceCredential).
If we don’t want SABnzbd installed, then we simply call the uninstall.exe.
Using and Configuring SABnzbd
You should be able to access SABnzbd via http://localhost:8080. When you connect the first time, you will be stepped through the initial setup wizard. I haven’t included any resources for specifying any settings like servers, scheduling or custom folders, you can do this as you would normally do. For more help, try the User Manual.
Getting the module
The module can be found on:
You will need PowerShell 5 or greater installed due to the use of Classes.
If you encounter any issues, please raise an issue on the GitHub page.
In the next post we will take a look at Sonarr.
Kieran Jacobsen
Presentation: Azure Automation invades your data centre
I recently had the pleasure to present on Azure Automation and hybrid workers to the Melbourne Azure Group. I really want to thank all of those who attended, Chris Padgett for inviting me to present and Microsoft for the use of their facilities.
My presentation, Azure Automation invades your data centre, covered off the ins and outs of Azure Automation and extending its reach to your own data centre with hybrid workers. I also spoke about using web hooks and the Azure Automation Authoring Toolkit.
If you haven’t looked at Azure Automation or hybrid workers, I thoroughly recommend that go and take a look. There are a number of excellent resources out there for you to make a start, including:
- Azure Automaton - PluralSight: https://app.pluralsight.com/library/courses/microsoft-azure-automation/table-of-contents
- Azure Automation - Ignite Australia: https://channel9.msdn.com/Events/Ignite/Australia-2015/ARC311
- Hybrid Workers: https://azure.microsoft.com/en-us/documentation/articles/automation-hybrid-runbook-worker/#
- Web Hooks: http://blog.coretech.dk/jgs/azure-automation-using-webhooks-part-1-input-data/
- Azure Automation Authoring Toolkit: https://www.powershellgallery.com/packages/AzureAutomationAuthoringToolkit
You can find the runbooks I used in my presentation up on GitHub, https://github.com/poshsecurity/PoshSecurityAzureAutomation and you can download the slides or view them with SlideShare here.
Kieran Jacobsen
Enabling Mobile Device Management with Office 365
Microsoft recently announced that they would be including a Mobile Device Management (MDM) platform as part of Office 365. What this means is that organisations, both small and large now have an extremely easy and powerful MDM available to them, without any additional charge to their Office 365 licencing. Administrators can manage Android, iOS and Windows Phone devices, and enforce various corporate policies and standards.
To support the new MDM functionality, you will need to create two new DNS records in each of your Office 365 domains. I have updated the Posh-Office365CloudFlare script to support the creation of these two additional records. You can create these records via the -MDMEnable parameter.
The process for creating the entries is as simple as:
Register-Office365.ps1 -CloudFlareApiToken <token> -CloudFlareEmailAddress <email> -Domain <domain> -MDMEnable
Just a quick note, I am yet to fully test out the new MDM functionality as none of my existing tenants have enabled for it yet.
Kieran Jacobsen
Automating Office 365 deployments in CloudFlare
A few weeks ago, I wrote about Posh-CloudFlare, a PowerShell module I created for managing CloudFlare hosted domains. Since then, I was working on extending an Office 365 deployment, and realized that what was needed was a script which could automate the configuration of new domains. With that in mind, I developed a new PowerShell script, Posh-Office365CloudFlare.
Let's understand the process for the addition and configuration of a new domain for Office 365.
The process starts with the Office 365 Portal. We navigate to the Domains section, click the "Add Domain" button, and after ignoring the introduction, we proceed to step 1. This step starts with us entering our domain name, let's use our old favorite contoso.com. Now we will be asked to verify that we own this domain, either through the creation of a TXT record or an MX record. The typical method is to use is that of a TXT record, created at the root of our desired domain with a value something like "MS=mx********".
After we create the domain, and the wizard successfully sees the appropriate record, we will be allowed to proceed to the next step. Step 2 isn't one that I usually make use of. I typically don't want to modify my users email domains, nor do I want to add new users at this time. I skip this step and move straight on to step 3.
Step 3 starts with another quick introduction screen, and then we will be asked if we would like the DNS for this domain to be managed by Microsoft. Obviously, we are going to answer no and move on. Finally, we reach an important step, we are asked what we want to do with this domain. First, "Outlook for email, calendar, and contacts", or in other words, email; the second, "Lync for instant messaging and online meetings", which is kind of obvious.
If you select “Outlook for email, calendar, and contacts”, then we will be told to create the following records in contoso.com:
- MX - @.contoso.com - which points to contoso-com.mail.protection.outlook.com (priority 0)
- CNAME – autodiscover.contoso.com – which points to autodiscover.outlook.com
- CNAME – msoid.contoso.com – which points to clientconfig.microsoftonline-p.net
- TXT – @.contoso.com – which contains a SPF record
If you select “Lync for instant messaging and online meetings”, then we will need to create the following records for contoso.com:
- CNAME - sip.contoso.com - which points to sipdir.online.lync.com
- CNAME - lyncdiscover.contoso.com - which points to webdir.online.lync.com
- CNAME – msoid.contoso.com – which points to clientconfig.microsoftonline-p.net
- SRV - _sip._tls.contoso.com - with its appropriate port, weight, priority and target
- SRV - _sipfederationtls._tcp.contoso.com - with its appropriate port, weight, priority and target
Reviewing this list of records, we will notice that the only record that changes for each domain is the MX record. The record consists of the domain name we want to add, with dashes replacing the original dots in the domain name. As you can see in the above example, cotoso.com's MX record points to contoso-com.mail.protection.outlook.com, where as awesomecompany.net would point to awesomecompany-net.mail.protection.com.
What about some records that could actually help our users? What if I said we could redirect sub domains of our own to the Outlook Web Access page? Wouldn't it be awesome if a user entered https://mail.contoso.com into their browser, and ended up with the Outlook Web Access? This can be achieved by creating a CNAME record that points to mail.office.com. Let's have our script create entries for mail and webmail perform this redirection.
Now back to the script.
This was a simple script, it doesn't have any complex logic, it will need the following information:
- CloudFlare API Token and email address; this is obvious as we need to talk to the CloudFlare Client API.
- The domain name.
- Do we want to create mail records? Lync records or both?
This is a very, very simple script, we just need to have a set of New-CFDNSRecord calls, with various controls depending on what we require.
For example, creating the MX record is as simple as:
This script only took an hour or so for testing and development time, however there was quite a bit of effort directed to changes in the Posh-CloudFlare and the New-CFDNSRecord CMDLet. If you look at the diff's between the last few versions, you will notice the following changes:
- The CMDLet now accepts input from the pipeline (in this case via property name).
- Restructure the CMDLet into Begin/Process/End (required for proper handling of pipeline input).
- Implementation of parameter sets.
- Cleanup of the validation of parameters.
I added parameter sets to New-CFDNSRecord with the aim to remove the somewhat faulty validation that I had previously. Whilst this sounded, and looked like it was simple, it actually took a few tried to ensure that the CMDLet would function appropriately. This was really interesting and deserves its own post in the future.
Parameter validation was updated in all of the CMDLets to improve email address validation. Previously, validation consisted of testing for an "@" character. Now I am using a regular expression.
Finally, I have spent some time cleaning up the code, not just within New-CFDNSRecord, but across all of the CMDLets. I have been trying, where possible to use ISE Steroids to ensure that everything I right is neat and presentable; it is a fantastic resource.
My final thought on all of this journey is, why couldn't Microsoft have implemented something like this? Microsoft has integrated the process with a bunch of other DNS providers, including the likes of GoDaddy, Network Solutions, 1 and 1 and even Yahoo Small Business. Why can't it also look at CloudFlare?
You can find the finished script over at GitHub, at Posh-Office365CloudFlare, the script is called Register-Office365.ps1. I have included comment based help with examples.
Kieran Jacobsen