Get-DSCConfigurationFromSystem.psm1
#region General Function Get-IsAdmin { $user = [Security.Principal.WindowsIdentity]::GetCurrent() If((New-Object Security.Principal.WindowsPrincipal $user).IsInRole([Security.Principal.WindowsBuiltinRole]::Administrator)) { $true } Else { $false } } #endregion #region Build-DSCConfigurationFromRegistry Function Replace-Properties { Param ( [Parameter(Mandatory=$true)] $Property ) $Property = $Property.tostring() $Property = $Property.replace('HKLM:','HKEY_Local_Machine') $Property = $Property.replace('HKCU:','HKEY_Current_User') $Property = $Property.replace('MultiString','REG_MULTI_SZ') $Property = $Property.replace('ExpandString','REG_EXPAND_SZ') $Property = $Property.replace('String','REG_SZ') $Property = $Property.replace('Binary','REG-BINARY') $Property = $Property.replace('DWord','REG_DWORD') $Property = $Property.replace('QWord','REG_QWORD') Return $Property } #end Function Function Get-RegistryKeyPropertiesAndValues { Param ( [Parameter(Mandatory=$true)] [string]$path ) $array = @() (Get-ItemProperty "Registry::$path").PSObject.Properties | Where-Object {$_.Name -notlike 'PS*'} | Select-Object Name, Value | % { $Key = Replace-Properties -Property $path If ($_.Name -eq '(default)') { If (-not $IgnoreDefault) { $ValueType = 'REG_SZ' $ValueData = (Get-Item "Registry::$path").GetValue("$($_.name)",$False, [Microsoft.Win32.RegistryValueOptions]::DoNotExpandEnvironmentNames) $Property = New-Object psobject -Property @{'Key' = $Key; 'ValueName' = $_.Name; 'ValueData' = $ValueData; 'ValueType' = $ValueType} $array += $Property } } Else { $Type = (Get-Item "Registry::$path").GetValueKind($_.Name) $ValueType = Replace-Properties -Property $Type $ValueData = (Get-Item "Registry::$path").GetValue("$($_.name)",$False, [Microsoft.Win32.RegistryValueOptions]::DoNotExpandEnvironmentNames) $Property = New-Object psobject -Property @{'Key' = $Key; 'ValueName' = $_.Name; 'ValueData' = $ValueData; 'ValueType' = $ValueType} $array += $Property } } Return $array } #end Function Function Get-ValuesInRegKey { Param ( [Parameter(Mandatory=$true)] [string]$path ) Get-ChildItem $path | ForEach-Object { Get-RegistryKeyPropertiesAndValues -path $_ } } #end Function Function Get-ValuesInRegKeyRecurse { Param ( [Parameter(Mandatory=$true)] [string]$path ) Get-ChildItem $path -Recurse | ForEach-Object { Get-RegistryKeyPropertiesAndValues -path $_ } } #end Function Function Get-DSCConfigurationFromRegistry { <# .SYNOPSIS This function converts a registry key and its values to the DSC Registry Resource format. If you want, it does this recursively .PARAMETER RegPath Path to the registry key. E.g. HKLM:\SOFTWARE\SomeSoftware .PARAMETER ExportPath Path to the file where the converted data will be stored. The data will be appended to the file if the file already exists .PARAMETER ForceValueReplacement Adds 'Force = $True' for each value in the output so that DSC will replace the data of the value if the value already exists. For more information have a look at technet: https://technet.microsoft.com/en-us/library/dn282133.aspx .PARAMETER IgnoreDefault If parameter is set, the default values will be ignored and won't show up in you DSC registry configuration .INPUTS This function does not allow any input .OUTPUTS This function exports data to a file. No output on the console. .NOTES Source: https://github.com/DominikBritz #> [CmdletBinding()] PARAM ( [Parameter(Position=0,Mandatory=$True)] [ValidateScript({Test-Path $_})] $RegPath, [Parameter(Position=1,Mandatory=$True)] [ValidateNotNullOrEmpty()] $ExportPath, [switch] $Recurse, [switch] $ForceValueReplacement, [switch] $IgnoreDefault ) #region Variables Set-Variable $IgnoreDefault -Scope Script #endregion $output = @() If ($Recurse) {$output += Get-ValuesInRegKeyRecurse -path $RegPath} If (-not $Recurse) {$output += Get-ValuesInRegKey -path $RegPath} If ($ForceValueReplacement) { ForEach ($Item in $output) { $Config = @" Registry $(Join-Path $Item.Key $Item.ValueName){ Ensure = "Present" Key = "$($Item.Key)" ValueName = "$($Item.ValueName)" Force = `$True ValueData = "$($Item.ValueData)" ValueType = "$($Item.ValueType)" } "@ Try { $Config >> $ExportPath } Catch { Throw $_ } #end Catch } #end ForEach } #end If Else { ForEach ($Item in $output) { $Config = @" Registry $(Join-Path $Item.Key $Item.ValueName){ Ensure = "Present" Key = "$($Item.Key)" ValueName = "$($Item.ValueName)" ValueData = "$($Item.ValueData)" ValueType = "$($Item.ValueType)" } "@ Try { $Config >> $ExportPath } Catch { Throw $_ } #end Catch } #end ForEach } #end Else } #end Function #endregion #region Get-DSCConfigurationFromWindowsFeature Function Get-DSCConfigurationFromWindowsFeature { <# .SYNOPSIS This function converts information of the windows features of the local system to the DSC WindowsFeature Resource format. .PARAMETER ExportPath Path to the file where the converted data will be stored. The data will be appended to the file if the file already exists .PARAMETER IncludeAllSubFeature Adds 'IncludeAllSubFeature = $True' for each value in the output. From Technet: Set this property to $true to ensure the state of all required subfeatures with the state of the feature you specify with the Name property .PARAMETER LogPath Indicates the path to a directory where you want the resource provider to log the operation. Each feature gets an own log file. .PARAMETER Credential Indicates the credentials to use to add or remove the role or feature .INPUTS This function does not allow any input .OUTPUTS This function exports data to a file. No output on the console. .NOTES Source: https://github.com/DominikBritz #> [CmdletBinding()] PARAM ( [Parameter(Position=0,Mandatory=$True)] [ValidateNotNullOrEmpty()] $ExportPath, [switch] $IncludeAllSubFeature, [string] $LogPath, [PSCredential] $Credential ) If (!(Get-IsAdmin)) {Throw 'You have to work with this function from an elevated powershell window'} If (!(Test-Path $LogPath)) { Try { New-Item -Path $LogPath -ItemType Directory -Force -ErrorAction Stop } Catch { Throw $_ } } $dism = Dism.exe /Online /Get-Features /Format:List /english | Where-Object {$_} $f = $dism[4..($dism.length-2)] $Features = for($i=0; $i -lt $f.length;$i+=2) { $tmp = $f[$i],$f[$i+1] -replace '^([^:]+:\s)' New-Object PSObject -Property @{ Name = $tmp[0] State = $tmp[1] } } foreach($item in $Name) { $Features | Where-Object {$_.Name -like $item -AND $_.State -like $State} } Foreach ($Feature in $Features) { If ($Feature.State -eq 'Enabled') { $DSCState = 'Present' } Else {$DSCState = 'Absent'} $Config = @" WindowsFeature $($Feature.Name) { Name = "$($Feature.Name)" Ensure = "$DSCState" } "@ If ($IncludeAllSubFeature) {$Config += "`n IncludeAllSubFeature = `$True"} If ($LogPath) {$Config += "`n LogPath = $(Join-Path $LogPath $($Feature.Name))"} Try { $Config >> $ExportPath } Catch { Throw $_ } #end Catch } #end ForEach } #end Function #endregion #region Get-DSCConfigurationFromServices Function Get-DSCConfigurationFromServices { <# .SYNOPSIS This function converts the properties of a Windows service into the DSC service format .PARAMETER ExportPath Path to the file where the converted data will be stored. The data will be appended to the file if the file already exists .INPUTS This function does not allow any input .OUTPUTS This function exports data to a file. No output on the console. .NOTES Source: https://github.com/DominikBritz #> [CmdletBinding()] PARAM ( [Parameter(Position=0,Mandatory=$True)] [ValidateNotNullOrEmpty()] $ExportPath ) $array = @() Get-Service * | ForEach-Object { $Service = $_ $Credential = $Null $StartupType = (Get-WmiObject -Class Win32_Service -Property StartMode -Filter "Name='$($Service.Name)'").StartMode If ($StartupType -eq 'Auto') { $StartupType = 'Automatic' } $StartName = (Get-WmiObject -Class Win32_Service -Property StartName -Filter "Name=`"$($Service.Name)`"").StartName Switch ($StartName) { 'LocalSystem' {$StartName = 'LocalSystem'; break} 'NT Authority\LocalService' {$StartName = 'LocalService'; break} 'NT AUTHORITY\NetworkService' {$StartName = 'NetworkService'; break} default {$Credential = $StartName} } If ($Credential) { $Config = @" Service $($Service.Name) { Name = "$($Service.Name)" Credential = "$Credential" StartupType = "$StartupType" State = "$($Service.Status)" } "@ } Else{ $Config = @" Service $($Service.Name) { Name = "$($Service.Name)" BuiltInAccount = "$StartName" StartupType = "$StartupType" State = "$($Service.Status)" } "@ } Try { $Config >> $ExportPath } Catch { Throw $_ } } } #endregion Export-ModuleMember -Function Get-DSCConfigurationFromRegistry Export-ModuleMember -Function Get-DSCConfigurationFromWindowsFeature Export-ModuleMember -Function Get-DSCConfigurationFromServices |