Modules/DSCParser.psm1
function ConvertTo-DSCObject { [CmdletBinding()] param ( [Parameter(Mandatory = $true,Position = 1)] [string] $Path ) #region Variables $ParsedResults = @() #endregion # Define components we wish to filter out $noisyTypes = @("NewLine", "StatementSeparator", "GroupStart", "Command", "CommandArgument", "CommandParameter", "GroupEnd", "Comment") $noisyParts = @("in", "if", "node", "localconfigurationmanager", "for", "foreach", "when", "configuration", "Where", "_") $noisyOperators = (".",",", "") # Tokenize the file's content to break it down into its various components; $parsedData = [System.Management.Automation.PSParser]::Tokenize((Get-Content $Path), [ref]$null) $componentsArray = @() $currentValues = @() for($i = 0; $i -lt $parsedData.Count; $i++) { if($parsedData[$i].Type -notin $noisyTypes -and $parsedData[$i].Content -notin $noisyParts) { $currentValues += $parsedData[$i] } elseif($parsedData[$i].Type -eq "GroupEnd") { $componentsArray+= ,$currentValues $currentValues = @() } } # Loop through all the Resources identified within our configuration $currentIndex = 1 foreach($group in $componentsArray) { # Display some progress to the user letting him know how many resources there are to be parsed in total; Write-Progress -PercentComplete ($currentIndex / $componentsArray.Count * 100) -Activity "Parsing $($resource.Content) [$($currentIndex)/$($componentsArray.Count)]" $keywordFound = $false $currentPropertyIndex = 0 foreach($component in $group) { if($component.Type -eq "Keyword") { $result = @{ ResourceName = $component.Content } $keywordFound = $true } elseif($keywordFound) { # If the next component is not an operator, that means that the current member is part of the previous property's # value; if($group[$currentPropertyIndex + 1].Type -ne "Operator" -and $component.Content -ne "=" -or ` ($group[$currentPropertyIndex + 1].Type -eq "Operator" -and $group[$currentPropertyIndex + 1].Content -eq ".")) { switch($component.Type) { {$_ -in @("String","Number")} { $result.$currentProperty += $component.Content } {$_ -in @("Variable")} { $result.$currentProperty += "`$" + $component.Content } {$_ -in @("Member")} { $result.$currentProperty += "." + $component.Content } } } elseif($component.Content -notin $noisyOperators) { switch($component.Type) { "Member" { $currentProperty = $component.Content.ToString() if(!$result.Contains($currentProperty)) { $result.Add($currentProperty, $null) } } } } } $currentPropertyIndex++ } if($keywordFound) { $ParsedResults += $result } $currentIndex++ } return $ParsedResults } |