Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

Generate CLIXML string from a PowerShell object without serializing to disk first

I have the following code which exports an object to an XML file, then reads it back in and prints it on the Information stream.

try{
  # Sample object
  $Person = @{
    Name = 'Bender'
    Age  = 'At least 1074'
  }
  $Person | Export-CliXml obj.xml
  
  $cliXml = Get-Content -Raw ./obj.xml
  Write-Host $cliXml
} finally {
  if( Test-Path ./obj.xml ) {
    Remove-Item -Force ./obj.xml -EV rError -EA SilentlyContinue
    if( $rError ) {
      Write-Warning "Failed to remove ./obj.xml: $($rError.Exception.Message)"
    }
    Remove-Variable -Force $rError -EA Continue
  }
}

There is a system-local parent session which watches its STDOUT for this output and reconstructs it to an object in its own session.

NOTE: I know a local PSRemoting session would work, but I need this to also work on systems which PSRemoting has either not yet been configured or will not be.

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

I’d like to cut out the middleman and instead of writing the object to disk. Unfortunately,
Import-CliXMl and Export-CliXml are the only cmdlets with CliXml in the name, and doing some .NET documentation sleuthing has turned up nothing so far.

Is there a way to simply serialize an object to a CliXml string without writing to disk first? I’ve considered using $Person | ConvertTo-Json -Compress -Depth 100 but this has two issues:

  1. Only captures nested objects up to 100 levels deep. This is an edge case but still a limit I’d like to avoid. I could always use another library or another format, but;

  2. I want these to be reconstructed into .NET objects of the same type they were before serialization. Recreating objects with CliXml is the only way I’m aware of that this can be done.

>Solution :

The CliXml serializer is exposed via the [PSSerializer] class:

$Person = @{
  Name = 'Bender'
  Age  = 'At least 1074'
}

# produces the same XML ouput as `Export-CliXml $Person`
[System.Management.Automation.PSSerializer]::Serialize($Person)

To deserialize CliXml, use the Deserialize method:

$cliXml = [System.Management.Automation.PSSerializer]::Serialize($Person)

$deserializedPerson = [System.Management.Automation.PSSerializer]::Deserialize($cliXml)
Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading