反序列化对象类型问题 - 特别是 Powershell 5 类 和 Import-CliXml

Deserialized Object type issues - specifically with Powershell 5 classes and Import-CliXml

我在使用 Import-CliXml 命令重新导入反序列化对象时遇到 Powershell 5 类 和对象类型的问题。

我有一个 Computer 类型的对象,我希望将其存储为 xml,然后在下次脚本为 运行

时重新导入它
class Computer 
{
    $Private:hostname
    $Private:ipAddress

    Computer([String] $hostname, [String] $ipAddress)
    {
        $this.hostname = $hostname
        $this.ipAddress = $ipAddress
    }
    static [Computer] reserialize([PSObject] $deserializedComputer)
    {
        return [Computer]::new($deserializedComputer.hostname, $deserializedComputer.ipAddress)
    }
}

我使用以下方法导出和导入对象:

$computer = [Computer]::new("test-machine", "192.168.1.2")
$computer | Export-CliXml C:\Powershell\exportTest.xml
$deserializedComputer = Import-CliXml C:\Powershell\exportTest.xml

我知道当这个对象被重新导入时它被反序列化并且基本上只是一个数据容器([Deserialized.Computer] 类型)。在我尝试使用我的重新序列化方法重新序列化它之前,我试图弄清楚如何对该对象进行类型检查。

例如,如果我尝试投射 $deserializedComputer,它会告诉我:

Cannot convert value "Computer" to type "Computer". Error: "Cannot convert the "Computer" value of type "Deserialized.Computer" to type 
"Computer"."

我明白为什么不能转换,我只是使用错误消息指出对象知道它的类型 [Deserialized.Computer]

我找不到从 $deserializedComputer.getMember() 返回的任何信息表明它是 [Deserialized.Computer] 类型,我能找到的唯一信息是它是 [PSObject] 类型,如何我可以键入检查此对象确实是 [Deserialized.Computer] 类型吗?

我应该添加类型 [Deserialized.Computer] 在 运行 时不存在,所以我不能在我的代码中直接使用它,否则我会简单地使用:

$deserializedComputer.getType() -eq [Deserialized.Computer]

使用(提示:gm 是 Get-Member 的别名)

$type = $deserializedComputer | gm | Select -Property TypeName -First 1

那么你应该能够访问像

这样的值
$type.TypeName

您还可以使用

键入检查以确保它是一台计算机
$deserializedComputer.ToString()

或者,如果您想要另一种方式,请使用

[type]$deserializedComputer.ToString()

编辑:

您可以通过以下方式查看

# you can also use $deserializedComputer.ToString() -eq [Computer].ToString()
if ([type]$deserializedComputer.ToString() -eq [Computer])
{

}

您的完整 class 看起来像:

class Computer 
{
    $Private:hostname
    $Private:ipAddress

    Computer(){}

    Computer([String] $hostname, [String] $ipAddress)
    {
        $this.hostname = $hostname
        $this.ipAddress = $ipAddress
    }
    static [Computer] reserialize([PSObject] $deserializedComputer)
    {
    # you can also use $deserializedComputer.ToString() -eq [Computer].ToString()
    if ([type]$deserializedComputer.ToString() -eq [Computer])
    {
       return [Computer]::new($deserializedComputer.hostname, $deserializedComputer.ipAddress)
    }
    return [Computer]::new()
    }
}

和Exporting/Importing

$filePath = "C:\Powershell\exportTest.xml"

$computer = [Computer]::new("test-machine", "192.168.1.2")
$computer | Export-CliXml $filePath
$deserializedComputer = Import-CliXml $filePath

和Reserialize方法

[Computer]::reserialize($deserializedComputer)