You've successfully subscribed to Florin Loghiade
Great! Next, complete checkout for full access to Florin Loghiade
Welcome back! You've successfully signed in
Success! Your account is fully activated, you now have access to all content.

Installing and Using PowerShell DSC on Linux

in

In the last two weeks I’ve been playing with PowerShell DSC for Linux and truth to be told I’m impressed on how stable it is since the last time I tried it. I started trying DSC for Linux first it came out and to be honest while it was nice, the bugs didn’t help that much and I always came up with something that made me revert back to a previous checkpoint be it compiling the OMI and DSC, pushing a configuration or breaking the OMI server after fiddling around the configuration files but hey that’s what you get when you’re trying out bleeding edge stuff right?

After doing some deployments with DSC I figured it was time to give the Linux version one more try to see what changed and how it handles and the results were very nice. This time I didn’t need to revert back to a previous checkpoint and everything ran smoothly on the first try.

For those of you that are new to this, Powershell DSC or Desired State Configuration is a declarative and idempotent platform that’s used to deploy, configure and manage server environments and it gives you the power to automate almost any task by declaring what you want and telling the system to make it so. The ‘make it so’ part comes believe or not from Star Trek. The inventor of PowerShell, Jeffrey Snover wanted to design a platform that grants the system administrators a captain seat from which he would give out orders and have his first officer and the rest of the crew ‘make it so’.

So basically there are two methods to hand out DSC configuration files to the target systems. The first method is Push, where you write a DSC configuration and then push it to the target system by running the Start-DscConfiguration cmdlet. The second and preferred method is Pull, where you configure a IIS server to be a OData interface that target systems are configured to contact in order to get their configuration files.

Hang on. What are configuration files?

When you write the DSC configuration in a PowerShell ISE or any other third party tool, you will produce at the end a .MOF (Management Object Format) file that can be interpreted by the Local Configuration Manager or LCM in short.

Here’s an example configuration:

configuration ExampleDSC
{
Import-DscResource –ModuleName 'PSDesiredStateConfiguration'
    Node localhost
    {
        Service StopBITS
        {
            Name = 'BITS'
            Ensure = 'Present'
            State = 'Stopped'
        }
    }

}
ExampleDSC
Start-DscConfiguration ExampleDSC -Wait -Verbose -Force

Let’s break it down. We declared a configuration named ‘ExampleDSC’ in the same way we would declare a function, imported the PSDesiredStateConfiguration resource that contains some builtin resources, specified a target node, called a DSC resource named ‘Service’ and finally we wrote the service name and we we want to do it with, which in this case we want the service named ‘BITS’ to be stopped. In order to run the configuration we simply call it by it’s name then push it.

PS D:\DSC> ExampleDSC

Directory: D:\DSC\ExampleDSC

Mode LastWriteTime Length Name
—- ————- —— —-
-a—- 1/19/2016 11:29 PM 1872 localhost.mof

PS D:\DSC> Start-DscConfiguration ExampleDSC -Wait -Verbose -Force
VERBOSE: Perform operation ‘Invoke CimMethod’ with following parameters, ”methodName’ = SendConfigurationApply,’className’ = MSFT_DSCLocalConfigurationManager,’namespaceName’ = root/Microsoft/Windows/DesiredStateConfiguration’.
VERBOSE: An LCM method call arrived from computer Workstation with user sid S-1-5-21-3098670248-3417488886-745665211-1001.
VERBOSE: [Workstation]: LCM: [ Start Set ]
VERBOSE: [Workstation]: LCM: [ Start Resource ] [[Service]StopBITS]
VERBOSE: [Workstation]: LCM: [ Start Test ] [[Service]StopBITS]
VERBOSE: [Workstation]: LCM: [ End Test ] [[Service]StopBITS] in 0.4160 seconds.
VERBOSE: [Workstation]: LCM: [ Skip Set ] [[Service]StopBITS]
VERBOSE: [Workstation]: LCM: [ End Resource ] [[Service]StopBITS]
VERBOSE: [Workstation]: LCM: [ End Set ]
VERBOSE: [Workstation]: LCM: [ End Set ] in 1.0650 seconds.
VERBOSE: Operation ‘Invoke CimMethod’ complete.
VERBOSE: Time taken for configuration job to complete is 1.14 seconds

OK, you stopped a service. Great. What else can it do?

This is just a very, very small part of DSC. You can use it to deploy and manage clusters, Active Directory, Exchange, System Center, Sharepoint and so on. You can use it to manage configuration drift where we tell the LCM to check the configuration after a period of time and if there’s a drift re-apply the part of the configuration that’s changed. In the example above we stopped the service BITS but I can just re-start it at any time. What if I want it to stay stopped forever without manually checking it? Well I can do that by telling the LCM to reapply the configuration if a unapproved change happened.
There are a lot of ways DSC can make your life easier and there’s no reason to not learn to use it.

While DSC is awesome on Windows, the idea behind it is to be cross-platform because in the real world we don’t manage only Windows machines, we manage Linux as well so the main goal of DSC is to learn one scripting language and use it everywhere. Plain and simple.

Now the main goal of this blog post is installing and using DSC on a Linux and first we need to know on which OS it’s supported which I listed below:

CentOS 5, 6, and 7 (x86/x64)
Debian GNU/Linux 6 and 7 (x86/x64)
Oracle Linux 5, 6 and 7 (x86/x64)
Red Hat Enterprise Linux Server 5, 6 and 7 (x86/x64)
SUSE Linux Enterprise Server 10, 11 and 12 (x86/x64)
Ubuntu Server 12.04 LTS and 14.04 LTS (x86/x64)

Source: https://github.com/Microsoft/PowerShell-DSC-for-Linux

Now that we know what we need for DSC to work, now it’s time to install it. For this example I will be using a CentOS 7.2 virtual machine that I created on my Hyper-V server.

====
Later edit:
You can now download the PowerShell DSC package from the Microsoft PowerShell GitHub repository and skip the build process entirely.

Here’s what you need to do:

wget https://github.com/Microsoft/PowerShell-DSC-for-Linux/releases/download/v1.1.1-70/dsc-1.1.1.packages.tar.gz
tar -zxvf dsc-1.1.1.packages.tar.gz
rpm -Uvh dsc-1.1.1-70.ssl_100.x64.rpm

Basically you download the PowerShell DSC packages from the GitHub repository, unpack them and install the one that can be used on your distribution. The example above installs PowerShell DSC for x64 distributions.
====

In order to get DSC running on Linux you need to install OMI (Open Management Infrastructure) which is like WMI but on Linux and PowerShell DSC. In order to get those up and running you have to install some development tools target machine in order to compile OMI and PowerShell DSC, and to make things simple I’ve made a simple script that will install all the required packages, download OMI and PowerShell DSC for Linux, compile them and start OMI as a daemon.
So just copy the script from below, paste it in a install.sh file, make it executable, run it and go get a coffee ?

yum -y groupinstall 'Development Tools'
yum -y install python
yum -y install python-devel
yum -y install pam-devel
yum -y install openssl-devel
mkdir omi
cd omi
wget https://collaboration.opengroup.org/omi/documents/33715/omi-1.0.8.tar.gz
tar -xvf omi-1.0.8.tar.gz
cd omi-1.0.8
./configure
make
make install 
cd /root/omi
wget https://github.com/Microsoft/PowerShell-DSC-for-Linux/releases/download/v1.1.0-466/PSDSC.tar.gz
tar -xvf PSDSC.tar.gz
cd dsc/
mv * /root/omi/
cd /root/omi
./configure && make
make reg

OMI_HOME=/opt/omi-1.0.8 /opt/omi-1.0.8/bin/omiserver -d

After the installation finishes and everything ran smoothly, the next step is to install the Linux DSC resources on your workstation and start writing the configuration files.

You can install the PowerShell DSC resources for managing Linux machines by either going to the PowerShell Gallery or if you have Windows 10 or WMF 5 installed you can use Find-Module nx* and install them from the PowerShell Console/ISE

Install-Module nx, nxComputerManagement, nxNetworking

You can see the resources by running Get-DSCResource cmdlet:

Get-DSCResource nx*

DSC-modules

As you can see, you have only have a handful resources but that’s a work in progress and you can expect more to appear as time goes. With the available DSC Resources you can extract tar/gzip files, create users, modify the firewall, set IP Addresses, start / stop services, install packages with different package managers, create files and so on.

If you want to see all the available parameters in order to get you started with the configuration file then you can run the command bellow and you will get a nice grid view showing you all the parameters that the resources expect.

Get-DscResource nx* | Select-Object FriendlyName -ExpandProperty properties | Out-GridView

DSC-OGV

In order to push the configuration remotely we need to establish a connection to the Linux Machine and to do that we need to create a CIMSession.

Here’s the code I used to establish a connection to the VM I created:

$RootCredentials = Get-Credential -UserName:'root' -Message 'Root Credentials'
 
$CIMOptions = New-CimSessionOption -SkipCACheck -SkipCNCheck -UseSsl -SkipRevocationCheck
 
$CIMSession = New-CimSession -Credential $RootCredentials -ComputerName '10.10.0.23' -Port 5986 -Authentication Basic -SessionOption $CIMOptions

What we need to keep in mind while reading the example from above is that For PUSH mode we need to use the root credentials then set the CIMSession options because this is a test environment and the certificates that were created in the OMI install are self signed and not trusted and we always need to use SSL. These are the constraints and it’s best to keep them that way for secure communications.
If you want to change the listening port and the certificates, you can do that by modifying the omiserver.conf file located in /opt/omi-1.0.8/etc/

Now we have an idea on how everything fits together and what does PowerShell DSC expects, it’s time to fire up the ISE and start writing the configuration. For this example I’ve written a configuration that will install all the components we need to run a LAMP server, start the services and then write a PHP file in /var/www/html/.

#requires -Modules CimCmdlets, PSDesiredStateConfiguration
#requires -Version 4
configuration LAMPServer
{
    Import-DSCResource -Module nx
    Import-DSCResource -Module nxComputerManagement
    Import-DSCResource -Module nxNetworking
 
    node 
    {
        nxPackage Apache
        {
            PackageManager = 'Yum'
            Ensure = 'Present'
            Name = 'httpd'
        }
        nxPackage MariaDB
        {
            PackageManager = 'Yum'
            Ensure = 'Present'
            Name = 'mariadb-server'
        }
        nxPackage PHP
        {
            DependsOn = '[nxPackage]Apache'
            PackageManager = 'Yum'
            Ensure = 'Present'
            Name = 'php php-mysql'
        }

        nxService Apache
        {
            DependsOn = '[nxPackage]Apache'
            Name = 'httpd'
            Enabled = $true
            Controller = 'systemd'
            State = 'Running'
        }
        nxService MariaDB
        {
            DependsOn = '[nxPackage]MariaDB'
            Name = 'mariadb'
            Enabled = $true
            Controller = 'systemd'
            State = 'Running'
        }
        nxFile PHPTest
        {
            DependsOn = '[nxPackage]Apache'
            Ensure = 'Present'
            Type = 'File'
            DestinationPath = '/var/www/html/test.php'
            Contents = ""
        }
    }
}

LAMPServer
 
$RootCredentials = Get-Credential -UserName:'root' -Message 'Root Credentials'
 
$CIMOptions = New-CimSessionOption -SkipCACheck -SkipCNCheck -UseSsl -SkipRevocationCheck
 
$CIMSession = New-CimSession -Credential $RootCredentials -ComputerName '' -Port 5986 -Authentication Basic -SessionOption $CIMOptions
 
Start-DscConfiguration -CimSession $CIMSession -Wait -Verbose -Path c:\LAMPServer
 
Get-DscConfiguration -CimSession $CIMSession
 
Test-DscConfiguration -CimSession:$CIMSession

DSC-Run

And that’s all folks! Everything was installed and started by just writing what we want and then telling the LCM to make it so ?

DSC-WorkingPHP

Have fun!