Modules/businessdev.ALbuild.Marketplace/Private/ConvertTo-BcHashTable.ps1

function ConvertTo-BcHashTable {
    <#
    .SYNOPSIS
        Converts a PSCustomObject (e.g. an API response) to a hashtable, optionally recursively.
    .DESCRIPTION
        Internal helper for the Marketplace submission flow (mirrors BcContainerHelper's ConvertTo-HashTable):
        Partner Center resources are read as PSCustomObjects that carry '@odata.*' metadata; to PUT them
        back they must be re-serialised as plain objects. Converting to a hashtable drops the read-only
        metadata and lets the caller edit/ConvertTo-Json them cleanly.
    .PARAMETER Object
        The object to convert.
    .PARAMETER Recurse
        Convert nested objects/arrays too.
    #>

    [CmdletBinding()]
    [OutputType([hashtable])]
    param(
        [Parameter(ValueFromPipeline)] $Object,
        [switch] $Recurse
    )
    process {
        $add = {
            param([hashtable] $Ht, [string] $Name, $Value, [bool] $Deep)
            if ($Ht.Contains($Name)) { return }
            if ($Deep -and ($Value -is [System.Collections.Specialized.OrderedDictionary] -or $Value -is [hashtable] -or $Value -is [System.Management.Automation.PSCustomObject])) {
                $Ht[$Name] = ConvertTo-BcHashTable $Value -Recurse
            }
            elseif ($Deep -and $Value -is [array]) {
                $Ht[$Name] = @($Value | ForEach-Object {
                        if (($_ -is [System.Collections.Specialized.OrderedDictionary]) -or ($_ -is [hashtable]) -or ($_ -is [System.Management.Automation.PSCustomObject])) { ConvertTo-BcHashTable $_ -Recurse } else { $_ }
                    })
            }
            else { $Ht[$Name] = $Value }
        }
        $ht = @{}
        if ($Object -is [System.Collections.Specialized.OrderedDictionary] -or $Object -is [hashtable]) {
            foreach ($k in $Object.Keys) { & $add $ht $k $Object[$k] $Recurse.IsPresent }
        }
        elseif ($Object -is [System.Management.Automation.PSCustomObject]) {
            foreach ($p in $Object.PSObject.Properties) { & $add $ht $p.Name $p.Value $Recurse.IsPresent }
        }
        return $ht
    }
}