Markus Sacramento
Markus Sacramento

Reputation: 364

Powershell change/edit value of Object in Variable

I create variables in a ForEach loop using data collected from a CSV file like this:

    New-Variable -Name $FlexVPN.'IP-adress' -Value (New-Object PSObject -Property @{
    IP = $FlexVPN.'IP-adress'
    Information = $FlexVPN.'Information'
    Priority = $FlexVPN.'Priority'
    RegisteredUp = $RegisteredUp
    RegisteredDown = $RegisteredDown
    ResponseTime = $Result = try{ Test-Connection -ComputerName $FlexVPN.'IP-adress' -Count $FlexVPN.'Priority' -ErrorAction Stop | Select ResponseTime} catch [System.Net.NetworkInformation.PingException] { $_.exception | PingFailed }})

What I'm then trying to do is to change the values of RegisteredUp and RegisteredDown depending of the respond of the ping.

I doesn't understand the New-Member stuff which I have tried but faild using. Now I tried Set-Variable but I don´t get how to only change a Object within the Variable?

Set-Variable -Name $FlexVPN.'IP-adress' -Value (New-Object PSObject -Property @{RegisteredDown = "TESTING"})

I don´t get any errors neither it´s working.

To explain further. If no respond on ping set Get-Date in RegisteredDown for that Variable. If respond on ping ser Get-Date in RegisteredUp for that Variable.

I then use if/else to use the result somehow in the next version ;)


Edit

# Clear variables after loop
Remove-Variable * -force -erroraction silentlycontinue

 
    function PingFailed { 
        
        # Add date and time when IP-address first didn't responded
            $FlexVPN.RegisteredDown = 'AnotherTest'

        # If only error should be printed
        if($PrintError -eq 'Yes'){Write-Host -ForegroundColor Red $FlexVPN.'IP-adress' "," $FlexVPN.'Information'}

##########################################################################
####################### NO CHANGES ABOVE THIS LINE #######################
##########################################################################

# Choose between printing output or not for all rows in CSV-file [Yes/No]
$PrintOutput = 'Yes'

# Choose between printing out error or not [Yes/No]
$PrintError = 'No'

##########################################################################
####################### NO CHANGES BELOW THIS LINE #######################
##########################################################################

# Import CSV-file to Powershell to use data in code
$FlexVPNlist = Import-Csv -Path $PSScriptRoot\PingIPEmail.csv -Header 'IP-adress', 'Information', 'Priority' -Delimiter ';' -Encoding UTF7

Foreach($FlexVPN in $FlexVPNlist) {

    New-Variable -Name $FlexVPN.'IP-adress' -Value (New-Object PSObject -Property @{
    IP = $FlexVPN.'IP-adress'
    Information = $FlexVPN.'Information'
    Priority = $FlexVPN.'Priority'
    RegisteredDown = 'Test'
    ResponseTime = $Result = try{ Test-Connection -ComputerName $FlexVPN.'IP-adress' -Count $FlexVPN.'Priority' -ErrorAction Stop | Select ResponseTime} catch [System.Net.NetworkInformation.PingException] { $_.exception | PingFailed }})

    if($PrintOutput -eq 'Yes'){
    if ($host.name -eq 'Windows PowerShell ISE Host') {if ($Result.ResponseTime -eq $null) { $Host.UI.RawUI.BackgroundColor = ($bckgrnd = 'Red') } else { $psISE.Options.RestoreDefaults() }}
    [PSCustomObject]@{
        "IP address" = $FlexVPN.'IP-adress'
        "Information" = $FlexVPN.'Information'
        "Priority" = $FlexVPN.'Priority'
        "Response time" = $Result.ResponseTime
        "RegisteredDown" = 'Test'
    }}
       
    }

}

My Second try above works fine until I catch an exeption during ping and goes to my function PingFailed. I want to run that function when an IP-address doesn´t respond and add Get-Date to RegisteredDown in those cases.

The error I recieve is:

At C:\Temp\Powershell scripts\PingIPEmail\PingIPEmail.ps1:49 char:13
+             $FlexVPN.RegisteredDown = 'AnotherTest'
+             ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
   + CategoryInfo          : NotSpecified: (:) [], SetValueInvocationException
   + FullyQualifiedErrorId : ExceptionWhenSetting`

Tried the other code

# Importing a csv
$FlexVPNList = Import-Csv -Path 'C:\Temp\Powershell scripts\PingIPEmail\PingIPEmail.csv' -Header 'IP-adress', 'Information', 'Priority' -Delimiter ';' -Encoding UTF7

Foreach($FlexVPN in $FlexVPNlist) {

$FlexVPN.GetType()                                # Object[]
$FlexVPN[0].GetType()                             # PSCustomObject
($FlexVPN[0] | gm -MemberType NoteProperty).Count # 3 Noteproperties

$FlexVPN | % {
    Add-Member -InputObject $_ -NotePropertyName 'RegisteredUp' -NotePropertyValue 1 -Force
    Add-Member -InputObject $_ -NotePropertyName 'RegisteredDown' -NotePropertyValue 1 -Force
}

($FlexVPN[0] | gm -MemberType NoteProperty).Count # 5 Noteproperties

 $Result = try{ Test-Connection -ComputerName $FlexVPN.'IP-adress' -Count $FlexVPN.'Priority' -ErrorAction Stop | Select ResponseTime} catch [System.Net.NetworkInformation.PingException] { $_ }

    if ($Result.ResponseTime -eq $null){
    if ($host.name -eq 'Windows PowerShell ISE Host') { $Host.UI.RawUI.BackgroundColor = ($bckgrnd = 'Red') }
    $FlexVPN.RegisteredDown = Get-Date
    [PSCustomObject]@{
        "IP address" = $FlexVPN.'IP-adress'
        "Information" = $FlexVPN.'Information'
        "Priority" = $FlexVPN.'Priority'
        "Response time" = $Result.ResponseTime
        "RegisteredUp" = $FlexVPN.RegisteredUp
        "RegisteredDown" = $FlexVPN.RegisteredDown
    }

    }

    if ($Result.ResponseTime -ge '0'){
    if ($host.name -eq 'Windows PowerShell ISE Host') { $psISE.Options.RestoreDefaults() }
    $FlexVPN.RegisteredUp = Get-Date
    [PSCustomObject]@{
        "IP address" = $FlexVPN.'IP-adress'
        "Information" = $FlexVPN.'Information'
        "Priority" = $FlexVPN.'Priority'
        "Response time" = $Result.ResponseTime
        "RegisteredUp" = $FlexVPN.RegisteredUp
        "RegisteredDown" = $FlexVPN.RegisteredDown
    }
    }

This code if I understand correctly reuse the same variable for each row in my CSV file. I want to create one variable for each row (name them the IP-address) so that I can reuse the values stored for as long as the script i running.

Upvotes: 0

Views: 2184

Answers (2)

Markus Sacramento
Markus Sacramento

Reputation: 364

Managed what I wanted by doing like this:

# Clear variables after loop
Remove-Variable * -force -erroraction silentlycontinue

# Importing a csv
$FlexVPNList = Import-Csv -Path 'C:\Temp\Powershell scripts\PingIPEmail\PingIPEmail.csv' -Header 'IP', 'Information', 'Priority' -Delimiter ';' -Encoding UTF7

$FlexVPNList | % {
    Add-Member -InputObject $_ -NotePropertyName 'RegisteredUp' -NotePropertyValue '' -Force
    Add-Member -InputObject $_ -NotePropertyName 'RegisteredDown' -NotePropertyValue '' -Force
    Add-Member -InputObject $_ -NotePropertyName 'ResponseTime' -NotePropertyValue '' -Force
}

Foreach($FlexVPN in $FlexVPNlist) {

$Ping = try{ Test-Connection -ComputerName $FlexVPN.IP -Count $FlexVPN.'Priority' -ErrorAction Stop | Select ResponseTime } catch [System.Net.NetworkInformation.PingException] { $_ }

 if($Ping.ResponseTime -ge '0'){ 
    $FlexVPN.RegisteredUp = Get-Date 
    $FlexVPN.ResponseTime = $Ping.ResponseTime
    }
    if($Ping.ResponseTime -eq $null){ $FlexVPN.RegisteredDown = Get-Date }

    New-Variable -Name $FlexVPN.IP -Value (New-Object PSObject -Property @{
    IP = $FlexVPN.IP
    Information = $FlexVPN.Information
    Priority = $FlexVPN.Priority
    RegisteredUp = $FlexVPN.RegisteredUp
    RegisteredDown = $FlexVPN.RegisteredDown
    ResponseTime = $Ping.ResponseTime
})

    [PSCustomObject]@{
        "IP address" = $FlexVPN.IP
        "Information" = $FlexVPN.Information
        "Priority" = $FlexVPN.Priority
        "Response time" = $FlexVPN.ResponseTime
        "RegisteredUp" = $FlexVPN.RegisteredUp
        "RegisteredDown" = $FlexVPN.RegisteredDown
    }

}

I can now do stuff If computer responded or not!

Upvotes: 1

Lieven Keersmaekers
Lieven Keersmaekers

Reputation: 58431

Looks like you are overcomplicating things. You can create a new variable (object) like this

$FlexVPN = [PSCustomObject] @{
    Information='Test'
}

Show the value of Information

$FlexVPN.Information 

Change the value of Information

$FlexVPN.Information = 'AnotherTest'

Show the changed value of Information

$FlexVPN.Information 

a valid use case for using new-variable would be if you dynamically create/use variables


Edit

your intent is not actual clear to me but following testbed might get you some new ideas to proceed from

# Mimick importing a csv
$FlexVPN = @'
IP-Adress,Information,Priority
1.1.1.1,FlexVPN,1
2.2.2.2,FlexVPN,2
'@ | ConvertFrom-Csv

$FlexVPN.GetType()                                # Object[]
$FlexVPN[0].GetType()                             # PSCustomObject
($FlexVPN[0] | gm -MemberType NoteProperty).Count # 3 Noteproperties

$FlexVPN | % {
    Add-Member -InputObject $_ -NotePropertyName 'RegisteredUp' -NotePropertyValue 1 -Force
    Add-Member -InputObject $_ -NotePropertyName 'RegisteredDown' -NotePropertyValue 1 -Force
}

($FlexVPN[0] | gm -MemberType NoteProperty).Count # 5 Noteproperties

Upvotes: 2

Related Questions