Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to include all properties of all array objects in csv in powershell

I have a Powershell script that reads a text file with single line descriptions of shares and their properties.

It then, for each share, adds an object to an array, with properties.

I end up with an array of shares, many with common properties but also some that only appear on a few shares.

When I pipe the finished array to Export-CSV, the resulting CSV only has columns matching the properties of the first object in the array.

Any ideas/help gratefully received.

Here is the code:

$shares_only = gc \\server\share\SHARES.txt | where {$_ -match '^*TYPE = DISK'}

$share_index = @()

$shares_only |foreach {

    $sharename = ($_.Split(" ")[1])
    $_ -match '\([\w\s.,"=<>()\/\*\+\-]*\);'|out-null

    $shareparams = $matches[0]

    $paramlist = ($shareparams.Substring(1,($shareparams.Length -3))).Split(",")

    $obj = $null
    $obj = New-Object System.Object

    $obj | Add-Member -type NoteProperty -Name NAME -Value $sharename

    $paramlist | foreach {
        $obj `
        | Add-Member -type NoteProperty -Name ($_.Split("=")[0]) -Value ($_.Split("=")[1])
    }
    $share_index += $obj
}

$share_index | Select * | Export-CSV -notype \\server\share\Shares.csv

Here is the first two objects in the array as an example (using $share_index[0..2] to output to console):

NAME          : _ACCTEST_
TYPE          :  DISK 
PREFIX        :  (<USERCODE>) 
AREABYTES     :  184320 
ACCESS        :  ALL 
FAMILY        :  ACCTESTPACK 
DOWNSIZEAREA  :  TRUE 

NAME              : _HOME_
TYPE              :  DISK 
PREFIX            :  (<USERCODE>) 
COMMENT           :  Private user files 
AREABYTES         :  184320 
ACCESS            :  ALL -EXTRACT 
FAMILY            :  <FAMILY> 
DOWNSIZEAREA      :  TRUE 
ALLOWGUESTACCESS  :  TRUE 

And here are the first 3 rows of the CSV:

"NAME","TYPE ","PREFIX ","AREABYTES ","ACCESS ","FAMILY ","DOWNSIZEAREA "
"_ACCTEST_"," DISK "," (<USERCODE>) "," 184320 "," ALL "," ACCTESTPACK "," TRUE "
"_HOME_"," DISK "," (<USERCODE>) "," 184320 "," ALL -EXTRACT "," <FAMILY> "," TRUE "

You can see that COMMENT and ALLOWGUESTACCESS properties are missing even although they are in the array for the _HOME_ share.

EDIT: Accepted slightly modified version of @JPBlancs answer, so last 2 lines of my code is now:

$fixed_index = $share_index | Sort-Object -Property @{expression={(($_.psobject.Properties)|Measure-Object).count}} -Descending | ConvertTo-CSV -notype
$fixed_index | ConvertFrom-CSV | Sort -Property Name | Export-CSV -notype \\server\share\Shares.csv 

So, done as suggested, then converted to CSV in a new object. Then, convert that object back from CSV, retaining the new properties, sort again on Name to get the alphabetical list I need, then Export to CSV again.

Gives me, for example:

"NAME","TYPE","PREFIX","PUBLIC","COMMENT","AREABYTES","ACCESS","FAMILY","DOWNSIZEAREA","ALLOWGUESTACCESS"
"_ACCTEST_"," DISK "," (<USERCODE>) ","",""," 184320 "," ALL "," ACCTESTPACK "," TRUE ",
"_HOME_"," DISK "," (<USERCODE>) ",""," Private user files "," 184320 "," ALL -EXTRACT "," <FAMILY> "," TRUE "," TRUE "
like image 614
Graham Gold Avatar asked Oct 15 '25 18:10

Graham Gold


2 Answers

I did something like this

$a = "" | select "P1","P2"
$b = "" | select "P1","P2","P3"
$c = "" | select "P1","P2","P3","P4"
$array = $a,$b,$c
$array | Export-Csv c:\temp\t.csv

gives as you remark:

#TYPE Selected.System.String
"P1","P2"
,
,
,

So the idea is to sort the objects by the properties count :

$array | Sort-Object -Property @{expression={$_.psobject.properties.count}} -Descending| Export-Csv c:\temp\t.csv

It gives :

#TYPE Selected.System.String
"P1","P2","P3","P4"
,,,
,,,
,,,

In the case of the question (object created adding members to a System.Object) you can use :

Sort-Object -Property @{expression={(($_.psobject.Properties)|Measure-Object).count}} -Descending
like image 134
JPBlanc Avatar answered Oct 17 '25 09:10

JPBlanc


Export-Csv and ConvertTo-Csv appear to only take the union of properties between objects sent to them. I think you will have to parse the text file and compile a list of all properties and when you create your objects set any missing property values to null.

like image 35
Andy Arismendi Avatar answered Oct 17 '25 09:10

Andy Arismendi



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!