117 lines
4.4 KiB
PowerShell
117 lines
4.4 KiB
PowerShell
function ConvertTo-Hashtable {
|
|
<#
|
|
.SYNOPSIS
|
|
Used to convert an object into a hashtable
|
|
|
|
.EXAMPLE
|
|
$json | ConvertFrom-Json | ConvertTo-HashTable
|
|
|
|
.EXAMPLE
|
|
[xml]$someXmlVariable | ConvertTo-HashTable
|
|
|
|
.PARAMETER InputObject
|
|
This is the object to convert
|
|
|
|
.PARAMETER Recursing
|
|
This indicates that we are calling ourselves, so don't convert the intermediary objects to a PSCustomObject
|
|
|
|
.LINK
|
|
https://4sysops.com/archives/convert-json-to-a-powershell-hash-table/
|
|
#>
|
|
[CmdletBinding()]
|
|
[OutputType([System.Collections.Hashtable])]
|
|
param (
|
|
[Parameter(ValueFromPipeline)]
|
|
$InputObject,
|
|
[switch]$Recursing
|
|
)
|
|
|
|
# Return null if the input is null. This can happen when calling the function
|
|
# recursively and a property is null
|
|
if ($null -eq $InputObject) {
|
|
return $null
|
|
}
|
|
|
|
# We don't mess with existing hashtables
|
|
if ($InputObject -is [System.Collections.Hashtable]) {
|
|
return $InputObject
|
|
}
|
|
|
|
$properties = [System.Collections.Hashtable]@{}
|
|
|
|
# Let's get us some XML out of there heck yeah
|
|
if ($InputObject -is [System.Xml.XmlNode]) {
|
|
$properties = [System.Collections.Hashtable]@{}
|
|
$element = $InputObject
|
|
if ($element.HasAttributes) {
|
|
$properties.Attributes = [System.Collections.Hashtable]@{}
|
|
$attributes = $element.Attributes
|
|
foreach ($attribute in $attributes) {
|
|
$name = $attribute.Name
|
|
if (![string]::IsNullOrWhiteSpace($attribute.Prefix)){
|
|
$name = $name.Replace("$($attribute.Prefix):","")
|
|
}
|
|
$properties.Attributes[$name] = $attribute.Value
|
|
}
|
|
}
|
|
if (!$element.IsEmpty) {
|
|
# This should handle "innerText only" nodes as well
|
|
if ($element.HasChildNodes) {
|
|
$nodes = $element.ChildNodes
|
|
foreach ($node in $nodes) {
|
|
#Write-Host $node
|
|
$name = $node.Name
|
|
if (![string]::IsNullOrWhiteSpace($node.Prefix)){
|
|
$name = $name.Replace("$($node.Prefix):","")
|
|
}
|
|
if ($name -eq '#text') {
|
|
$properties["#text"] = $element.InnerText
|
|
} else {
|
|
$properties[$name] = (ConvertTo-Hashtable $node -Recursing)
|
|
}
|
|
}
|
|
} else {
|
|
# Was the next line but discovered those get handled above easily
|
|
# $properties["#text"] = $element.InnerText
|
|
}
|
|
}
|
|
if (![string]::IsNullOrWhiteSpace($element.BaseURI)) {
|
|
$properties["BaseURI"] = $element.BaseURI
|
|
}
|
|
if (![string]::IsNullOrWhiteSpace($element.NamespaceURI)) {
|
|
$prefix = "schema"
|
|
if (![string]::IsNullOrWhiteSpace($element.Prefix)) {
|
|
$prefix = $element.Prefix
|
|
}
|
|
$properties[$element.Prefix] = $element.NamespaceURI
|
|
}
|
|
} else {
|
|
# Check if the input is an array or collection. If so, we also need to convert
|
|
# those types into hash tables as well. This function will convert all child
|
|
# objects into hash tables (if applicable)
|
|
if ($InputObject -is [System.Collections.IEnumerable] -and $InputObject -isnot [string]) {
|
|
$collection = @(
|
|
foreach ($object in $InputObject) {
|
|
(ConvertTo-Hashtable -InputObject $object -Recursing)
|
|
}
|
|
)
|
|
|
|
# Return the array but don't enumerate it because the object may be pretty complex
|
|
Write-Output -NoEnumerate $collection
|
|
return
|
|
} elseif ($InputObject -is [psobject]) { # If the object has properties that need enumeration
|
|
# Convert it to its own hash table and return it
|
|
foreach ($property in $InputObject.PSObject.Properties.Where({$_.MemberType -eq 'NoteProperty' -or $_.MemberType -eq 'Property'})) {
|
|
$properties[$property.Name] = (ConvertTo-Hashtable -InputObject $property.Value -Recursing)
|
|
}
|
|
} else {
|
|
# If the object isn't an array, collection, or other object, just return it and hope for the best
|
|
return $InputObject
|
|
}
|
|
}
|
|
if ($Recursing) {
|
|
return $properties
|
|
} else {
|
|
return (New-Object PSCustomObject -Property $properties)
|
|
}
|
|
} |