我有一个程序可以获取给定用户的VM信息。它使用菜单系统,该函数REFRESH_LIST
创建一个数组,创建一个包含VM信息(ip地址,名称等)的对象,并将其放入该数组中,因此该数组是与VM数量一样大的对象数组用户拥有的。
然后,我使用该数组填充一个表,以将所有信息显示到屏幕上。我还有另一个功能START_INSTANCE
,该功能将根据VM的名称启动VM,但为了检查并确保用户仅启动分配给他们的VM,我想返回阵列并检查输入的VM名称是否存在在数组中。
我的问题是数组是在一个函数中构建的,而我在另一个函数中需要它。在阅读中,我发现这是一个范围问题,$script:var
我构建了简单的测试函数,并在将相同的变量应用于$script:var
数组时得到了在其他函数中可用的变量,但该变量在其他任何地方仍然不可用。
数组有什么特别之处吗?或者不仅仅是范围?
FUNCTION GET_HELP {
ECHO ""
ECHO " refresh : REFRESH VM LIST"
ECHO " start : START INSTANCE : start <instance-id>"
ECHO " stop : STOP INSTANCE : stop <instance-id>"
ECHO " q : QUIT"
ECHO ""
}
FUNCTION INSTANCE_START {
$i=0
$CHECK=""
$a.Length
While ($i -le $a.Length) {
echo $CHECK
If ($a[$i].INSTANCEID -contains $INSTANCEID) {
$CHECK = "TRUE"}
$i = $i+1
Echo $CHECK
}
echo $CHECK
IF ($CHECK = "TRUE") {
#Start-EC2Instance -InstanceId
"STARTING " + $INSTANCEID
ECHO $CHECK}
ELSE {
$CHECK=""
"NO"}
$INSTANCEID = ""
}
FUNCTION INSTANCE_STOP {
#Stop-EC2Instance -InstanceId
}
FUNCTION REFRESH_LIST {
Clear-Host
" LOADING VM LIST FOR "+$USERNAME
$date = get-date -format "MM/dd/yyyy HH:mm:ss"
$Global:a = @()
(Get-EC2Instance).instances | ? {$_.Tags.Key -eq "NAME" -and $_.Tags.Value -eq $TEST_USER} | ForEach-Object {
$instobj = New-Object System.Object
$instobj | Add-Member -Type NoteProperty -Name STATE -value $_.state.name
$instobj | Add-Member -type NoteProperty -name INSTANCEID -value $_.InstanceID
$instobj | Add-Member -type NoteProperty -name IPADDRESS -value $_.PublicIPAddress
IF ($_.state.name -eq 'running'){
$time=New-TimeSpan -Start $_.LaunchTime -End $date
$val="{0}d {1}h {2}m" -f $time.Days, $time.Hours, $time.Minutes
$instobj | Add-Member -Type NoteProperty -Name TIME -value $val}
else{$instobj | Add-Member -Type NoteProperty -Name TIME -value ""}
$a += $instobj}
For ($i=0; $i -le $a.Length-1; $i++){
$instanceTags = Get-EC2Tag -Filter @{ Name="resource-id"; Values=$a[$i].INSTANCEID }
$a[$i] | Add-Member -type NoteProperty -name PROJECT -value $instanceTags.Where({$_.Key -eq "Project"}).Value
$a[$i] | Add-Member -type NoteProperty -name NAME -value $instanceTags.Where({$_.Key -eq "Name"}).Value
$a[$i] | Add-Member -type NoteProperty -name SOFTWARE -value $instanceTags.Where({$_.Key -eq "Oracle SW"}).Value
}
Clear-Host
echo $date
$a | sort STATE, PROJECT, NAME |Format-Table STATE, INSTANCEID, IPADDRESS, PROJECT, NAME, SOFTWARE, TIME -AutoSize
}
#REGION MAIN
REFRESH_LIST
DO {
$SELECTION = Read-Host ">"
$COMMAND,$INSTANCEID = $SELECTION.split(' ',2)
SWITCH ($COMMAND) {
'-h' {GET_HELP}
'refresh' {REFRESH_LIST}
'start' {INSTANCE_START}
'stop' {'STOPPING INTANCE'}
'q' {BREAK}
DEFAULT {'ENTER -h FOR HELP'}
}}
until ($COMMAND -eq 'q')
#ENDREGION
解决此问题的一种方法是在$Global:
范围内分配数组:
$Global:arr
一些示例代码:
function one {
$Global:arr = @(1, 2, 3)
}
function two {
one
$arr
}
two
输出:
1
2
3
请参阅ss64或运行help about_Scopes
以获取更多详细信息。
在您发布的代码中,您可以尝试:
$Global:a = @()
在 REFRESH_LIST
这个小例子更能反映您的代码:
function one {
$Global:a = @(1,2,3)
}
function two {
echo $a.Length
}
one
two
输出在哪里 3
如评论中所述,这也适用于$Script
,在您的情况下更可取。但是,为了确保每次调用数组的相同实例,每次使用时都需要在决定将其声明为($Global:
或$Script:
)的作用域之前添加前缀
本文收集自互联网,转载请注明来源。
如有侵权,请联系 [email protected] 删除。
我来说两句