Hashtable - export : to CSV

This topic contains 6 replies, has 3 voices, and was last updated by Profile photo of Windows LiveUser32 Windows LiveUser32 1 year, 6 months ago.

  • Author
    Posts
  • #26829
    Profile photo of Windows LiveUser32
    Windows LiveUser32
    Participant

    Hi everyone,
    I am experimenting a little bit with Hashtables in PowerShell v2 and v3 and v4. I am asking for your help in regards of exporting multiple values to a CSV-file. Here's what I'm trying:
    Get the status of the Windows Defender Service via WMI:

    $WinDefend = Get-WmiObject -Namespace root\cimv2 -Class Win32_Service -Filter "Name LIKE 'WinDef%'"
    

    Store multiple values regarding the Service in a Hashtable:

    $SystemProps=[ordered]@{
    #$SystemProps=@{
    'WindowsDefender'=$WinDefend.ProcessID,$WinDefend.State,$WinDefend.StartMode;
    }
    

    If I try exporting the Hashtable to CSV I always end up with a "System.Object[]" in the column where those multiple values are stored. Below is what I've tried so far

    $SystemProps.GetEnumerator() | select name,value | Export-CSV C:\temp\props.csv
    new-object psobject -property $SystemProps | Export-Csv "C:\temp\props.csv" -NoTypeInformation
    

    Writing the values out to a txt-file works fine but I'm curious of how to do that with a CSV

    $SystemProps.GetEnumerator() | Out-String | out-file C:\temp\props.txt
    

    Thanks a lot,
    Steven

  • #26831
    Profile photo of tommymaynard
    tommymaynard
    Member

    You can turn it into an object using pscustomobject, and then successfully pipe that to a Csv. Notice, I've also created a separate keys for process, state, and startmode. I'm not sure if this will work (for you), so if not, take a look at the second option to leave the process, state, and startmode as a single value for the one, WindowsDefender, key.

    $WinDefend = Get-WmiObject -Namespace root\cimv2 -Class Win32_Service -Filter "Name LIKE 'WinDef%'"
    
    $SystemProps = [pscustomobject][ordered]@{
        WindowsDefenderProcess = $WinDefend.ProcessID
        WindowsDefenderState = $WinDefend.State
        WindowsDefenderStartMode = $WinDefend.StartMode;
    }
    
    $SystemProps | Export-Csv -Path C:\temp\props1.csv -NoTypeInformation
    $WinDefend = Get-WmiObject -Namespace root\cimv2 -Class Win32_Service -Filter "Name LIKE 'WinDef%'"
    
    $SystemProps = [pscustomobject][ordered]@{
        WindowsDefender = $WinDefend.ProcessID,$WinDefend.State,$WinDefend.StartMode -join ','
    }
    
    $SystemProps | Export-Csv -Path C:\temp\props2.csv -NoTypeInformation

    Box Prox wrote about this in 2014, and I've referenced the post numerous times when I hit the System.Object[] in my exported, Csv files. Here's the link: http://learn-powershell.net/2014/01/24/avoiding-system-object-or-similar-output-when-using-export-csv/.

    Most recently, I used it to a fix a problem with a DHCP/DNS function I wrote: http://tommymaynard.com/script-sharing-find-dns-servers-being-used-by-dhcp-scopes-2015. I even gave him credit at the bottom of that post.

    Anyway, let me know if this helps, and if you can't scroll left-right in the script windows, use the double-sided arrows to open it in a separate window.

  • #26833
    Profile photo of Windows LiveUser32
    Windows LiveUser32
    Participant

    Hey sir,
    thank you very much! Both approaches work with PowerShell v3. Unfortunately I didn't get them to work with PowerShell v2. The output I get is:

    "IsReadOnly","IsFixedSize","IsSynchronized","Keys","Values","SyncRoot","Count"
    "False","False","False","System.Collections.Hashtable+KeyCollection","System.Collections.Hashtable+ValueCollection","System.Object","6"
    

    Is this exspected behavior or am I doing something wrong?
    Thanks and best regards,
    Steven

  • #26834
    Profile photo of tommymaynard
    tommymaynard
    Member

    That's expected behavior prior to PowerShell 3.0, when creating a custom object with this option. There's different ways to create custom objects in the earlier versions of PowerShell. Here's how to do it in the different versions: http://blogs.technet.com/b/heyscriptingguy/archive/2013/11/07/a-powershell-object-lesson-part-3.aspx. I choose PowerShell 3.0, since I think that's when we were able to order our hash tables, such as what you did in your example.

  • #26835
    Profile photo of Windows LiveUser32
    Windows LiveUser32
    Participant

    Thank you very much sir! Exactly what I needed!

  • #26836
    Profile photo of Tim Curwick
    Tim Curwick
    Participant

    Stephen,

    No need to use a hashtable as an interim step.

    $WinDefend = Get-WmiObject -Namespace root\cimv2 -Class Win32_Service -Filter "Name LIKE 'WinDef%'"
    $WinDefend | Select ProcessID, State, StartMode | Export-Csv "C:\temp\props.csv" -NoTypeInformation
    

    If you need to change the column header, you do it like this:

    $WinDefend = Get-WmiObject -Namespace root\cimv2 -Class Win32_Service -Filter "Name LIKE 'WinDef%'"
    $WinDefend | Select @{ Label = 'WindowsDefenderProcess'; Expression = { $_.ProcessID} }, State, StartMode | Export-Csv "C:\temp\props.csv" -NoTypeInformation
    
  • #26837
    Profile photo of Windows LiveUser32
    Windows LiveUser32
    Participant

    Hi Tim,
    thanks, but my goal was just to play around with Hashtables, therefore I used it 🙂 With Tommy's help I now figured out that for outputting stuff to a CSV-File a custom PSObject is better choice than a Hashtable.So I learned two things in one catch. Looks like a good day from my perspective 🙂

    Greetings,
    Steven

You must be logged in to reply to this topic.