Powershell 所有VM PowerCLI信息输出/控制台和自定义对象工作不正常
我希望使用vSphere PowerCLI获取所有虚拟机,并将这些虚拟机输出一些附加信息。但是我没有让输出正常工作 我已经尝试过将其作为控制台输出,但是我没有得到带有操作系统和IP地址的名称Powershell 所有VM PowerCLI信息输出/控制台和自定义对象工作不正常,powershell,powercli,Powershell,Powercli,我希望使用vSphere PowerCLI获取所有虚拟机,并将这些虚拟机输出一些附加信息。但是我没有让输出正常工作 我已经尝试过将其作为控制台输出,但是我没有得到带有操作系统和IP地址的名称 $Object = New-Object PSObject -Property @{ Name = $name OS = $info.OSFullName IP = $info.IPAddress } Connect-VIServer -Server VMServer -C
$Object = New-Object PSObject -Property @{
Name = $name
OS = $info.OSFullName
IP = $info.IPAddress
}
Connect-VIServer -Server VMServer -Credential admin -Password ASecretPWnoOneKnows
$allnames = Get-VM
foreach($name in $allnames)
{
$info = Get-VMGuest $name | select OSFullName, IPAddress
Add-Member -InputObject $Object
}
这是我迄今为止的“最佳方法”
我的结果应该是
SomeVMname SomeOS SomeIP
但由于没有正确处理自定义对象,我只得到了整个字符串或错误的长度:
因此,如果有人能以任何一种方式帮助我,将控制台输出或输出到一个我也可以输出到csv的对象中,我将非常高兴您已经非常接近于实现这一目标了。只需将$object
创建和检索移动到ForEach
循环中即可
Connect-VIServer -Server VMServer -Credential admin -Password ASecretPWnoOneKnows
$allnames = Get-VM
$Output = foreach($name in $allnames)
{
$Object = [PSCustomObject][ordered]@{
Name=$name.Name
OS=$name.Guest.OSFullName
IP=$name.Guest.IPAddress -match "\." -join " "
}
$Object
}
$Output # To output to the console
$Output | Export-Csv -path "file.csv" -NoTypeInformaton # Csv output
暗指有关处理IPAddress
属性和删除不必要命令(即Get-VMGuest
)的一些想法,以达到预期目标。他使用快捷方式创建将保存虚拟机属性的对象$row
。但是,使用数组替换加加法技术存在固有的低效性,因为每次循环迭代时都会创建一个较大的新数组对象。对于较小的数据集,这可能无关紧要,但对于较大的数据集,这可能是非常重要的
创建[PSCustomObject]
后,只要对象未被销毁和/或那些属性定义保留在对象上,就可以编辑属性中的值。这意味着您可以在循环的每次迭代期间为相同属性设置所有新值(如果愿意)。我添加了[ordered]
属性,以便$object
属性顺序在输出中保持一致
我添加了$Output
变量来存储循环每次迭代期间$Object
的值$Output
成为一个对象数组,其中包含要跟踪的三个属性。现在,您的导出Csv
将把这些属性值转换为Csv文件的字符串
我删除了Get-VMGuest
命令,因为$name
变量是一个包含您已经需要的所有信息的对象。Guest
属性提供了Get-VMGuest
提供的信息
您可以将IPAddress
值强制转换为字符串,因为有时可能存在多个IP,因为该属性是数组。您可以选择只获取一个索引值($Name.Guest.IPAddress[0]
);但是,您必须小心,因为您想要的IP地址可能位于另一个索引中。[string]
cast将使用空格分隔符返回该属性的所有值。我使用了-join
操作符,并使用了空格分隔符<代码>IP地址
也可能包含IPv6地址。我只想捕获IPv4地址,所以我使用了正则表达式匹配,例如$Name.Guest.IPAddress-match“\”
,它匹配文本
字符。您可以结合多种技术来获得所需的数据
考虑以下对象和示例:
$name.guest
IPAddress OSFullName
--------- ----------
{1.1.1.1, 2.2.2.2, fe80::ffff:ffff:ffff:ffff} Windows StackOverflow
$name.guest.IPAddress # Retrieves all IPs
1.1.1.1
2.2.2.2
fe80::ffff:ffff:ffff:ffff
$name.guest.IPAddress[0] # Retrieves the first IP in the array
1.1.1.1
$name.guest.IPAddress -match "\." # Retrieves all IPv4 IPs
1.1.1.1
2.2.2.2
$name.guest.IPAddress -match "\." -join " " # Retrieves all IPv4 separated by space
1.1.1.1 2.2.2.2
按照代码的结构方式,似乎您试图创建的属性的值是通过引用而不是通过值。为了进一步解释,您似乎希望$Object
的属性值随着$info
属性值的自动更改而更新,而无需显式赋值。我不知道这是否是你的意图,但我相信这会增加你想要完成的事情的复杂性。我这样做不是为了你的代码。每次循环迭代时,我都显式地设置$Object
属性值
我也没有看到您的导出Csv
命令;但是,您描述了具有Length
属性的输出。当您使用[string]
对象作为输入对象导出Csv时,可能会发生这种情况。由于导出Csv的目的是将属性值转换为字符串,因此常规字符串的唯一属性值是Length
。所以这是意料之中的。您可以在下面看到此行为:
$str = "this is a string"
($str | Get-Member).where({$_.MemberType -eq "Property"})
TypeName: System.String
Name MemberType Definition
---- ---------- ----------
Length Property int Length {get;}
$str | ConvertTo-Csv
#TYPE System.String
"Length"
"16"
你已经非常接近完成这项工作了。只需将
$object
创建和检索移动到ForEach
循环中即可
Connect-VIServer -Server VMServer -Credential admin -Password ASecretPWnoOneKnows
$allnames = Get-VM
$Output = foreach($name in $allnames)
{
$Object = [PSCustomObject][ordered]@{
Name=$name.Name
OS=$name.Guest.OSFullName
IP=$name.Guest.IPAddress -match "\." -join " "
}
$Object
}
$Output # To output to the console
$Output | Export-Csv -path "file.csv" -NoTypeInformaton # Csv output
暗指有关处理IPAddress
属性和删除不必要命令(即Get-VMGuest
)的一些想法,以达到预期目标。他使用快捷方式创建将保存虚拟机属性的对象$row
。但是,使用数组替换加加法技术存在固有的低效性,因为每次循环迭代时都会创建一个较大的新数组对象。对于较小的数据集,这可能无关紧要,但对于较大的数据集,这可能是非常重要的
创建[PSCustomObject]
后,只要对象未被销毁和/或那些属性定义保留在对象上,就可以编辑属性中的值。这意味着您可以在循环的每次迭代期间为相同属性设置所有新值(如果愿意)。我添加了[ordered]
属性,以便$object
属性顺序在输出中保持一致
我添加了$Output
变量来存储循环每次迭代期间$Object
的值$Output
成为一个对象数组,其中包含要跟踪的三个属性。现在,您的导出Csv
将把这些属性值转换为Csv文件的字符串
我快速眼动