Well, when working with AD in i.e. ADSI you don't get single objects in return but collections.
So if adding a property of such an object, it will be presented to PoSH as multivalued and thus entered as a collection instead of a value.
For this example I've done an LDAP query to an AD returning a DN object, $objDN.
Now this collection has some properties I'm interested in.
Path Properties
---- ----------
LDAP://CN=... {operatingsystem, countrycode, cn, lastlogoff...}
LDAP://CN=... {operatingsystem, countrycode, cn, lastlogoff...}
The properties property is obviously a collection.
PS U:\> $objDN[0].properties
Name Value
---- -----
operatingsystem {Windows Server 2008 R2 Standard}
countrycode {0}
cn ...
lastlogoff {0}
flags {16}
dscorepropagationdata {2016-06-15 15:31:24, 2015-12-28 18:53:43, 2015-12-28 18:53:37, 2015-12-28 18:53:33...}
dnshostname ...
usncreated {1548162366}
objectguid ...
...
But all values of the properties is also collections, *even* when they are single valued.
So using one of the values will look kind if weird on some occasions.
Pure string handling is ok.
PS U:\> $objDN[0].properties.operatingsystem
Windows Server 2008 R2 Standard
But Custom Object will look funny.
PS U:\> $objComp = @{}
PS U:\> $objComp.OS = $objDN[0].properties.operatingsystem
PS U:\> $objComp.Purchase = "2015-01-01"
PS U:\> $objComp.Modell = "Dell Lattitude"
PS U:\> $objComp
Name Value
---- -----
Modell Dell Lattitude
Purchase 2015-01-01
OS {Windows Server 2008 R2 Standard}
The .OS property can still be used as a string when needed, but it looks darned ugly. And the value is actually a string.
The collection type:
PS U:\> $objComp.OS
Windows Server 2008 R2 Standard
PS U:\> $objComp.OS.gettype()
IsPublic IsSerial Name BaseType
-------- -------- ---- --------
True False ResultPropertyValueCollection System.Collections.ReadOnlyCollectionBase
The type of the single value:
PS U:\> $objComp.OS[0]
Windows Server 2008 R2 Standard
PS U:\> $objComp.OS[0].gettype()
IsPublic IsSerial Name BaseType
-------- -------- ---- --------
True True String System.Object
So for single valued collections, simply just use the first entry of the collection.
$objComp.OS = $objDN[0].properties.operatingsystem[0]
PS U:\> $objComp
Name Value
---- -----
Modell Dell Lattitude
Purchase 2015-01-01
OS Windows Server 2008 R2 Standard
The Power of Powershell
Tuesday, December 6, 2016
Tuesday, April 12, 2016
Duh...
Remember me having some issues with Custom Objects not beeing ordered in PoSH v2?
$propertyOfSven = @{}
$propertyOfSven.first = "Sven"
$propertyOfSven.last = "Karlsson"
$propertyOfSven.phone = "040-11 12 13"
> $propertyOfSven
Name Value
---- -----
last Karlsson
phone 040-11 12 13
first Sven
> $sven = New-Object PSObject -Property $propertyOfSven
> $sven
last phone first
---- ----- -----
Karlsson 040-11 12 13 Sven
Well, why don't we just Sort the object output (thanks to Bill Stewart)?
> $sven = New-Object PSObject -Property $propertyOfSven | Select-Object first,last,phone
> $sven
first last phone
----- ---- -----
Sven Karlsson 040-11 12 13
And done.
$propertyOfSven = @{}
$propertyOfSven.first = "Sven"
$propertyOfSven.last = "Karlsson"
$propertyOfSven.phone = "040-11 12 13"
> $propertyOfSven
Name Value
---- -----
last Karlsson
phone 040-11 12 13
first Sven
> $sven = New-Object PSObject -Property $propertyOfSven
> $sven
last phone first
---- ----- -----
Karlsson 040-11 12 13 Sven
Well, why don't we just Sort the object output (thanks to Bill Stewart)?
> $sven = New-Object PSObject -Property $propertyOfSven | Select-Object first,last,phone
> $sven
first last phone
----- ---- -----
Sven Karlsson 040-11 12 13
And done.
Tuesday, March 15, 2016
Objects made easy
Ok, so you've noticed me struggle.
But that's how you learn.
In my last post I was trying to simplify the creation of objects in various way but I forgot about the golden rule, KISS (Keep It Simple, Stupid).
That is, if it looks complex, write a function...
So the only way to create an object in PowerShell v2 with ordered properties is like this, right?
So lets make it a an advanced function.
function New-CustomObject
{
param (
[array]$PropertyArray
)
$Object = New-Object PSObject
foreach ($Property in $PropertyArray){
$Object | Add-Member -MemberType 'NoteProperty' -Name $Property -Value $null
}
return $Object
}
Then putting the new function to use
$Kalle = New-CustomObject -PropertyArray "First","Last","Phone"
$Kalle.First = "Kalle"
$Kalle.Last = "Svensson"
$Kalle.Phone = "555 - 55 55 55"
And I'm done
But that's how you learn.
In my last post I was trying to simplify the creation of objects in various way but I forgot about the golden rule, KISS (Keep It Simple, Stupid).
That is, if it looks complex, write a function...
So the only way to create an object in PowerShell v2 with ordered properties is like this, right?
$Kalle = New-Object PSObject
$Kalle
| Add-Member -MemberType NoteProperty -Name First -Value "Kalle"
$Kalle
| Add-Member -MemberType NoteProperty -Name Last -Value "Svensson"
$Kalle
| Add-Member -MemberType NoteProperty -Name Phone -Value "555-55 55 55"$Kalle
First Last Phone
----- ---- -----
Kalle Svensson 555-55 55 55
So lets make it a an advanced function.
function New-CustomObject
{
param (
[array]$PropertyArray
)
$Object = New-Object PSObject
foreach ($Property in $PropertyArray){
$Object | Add-Member -MemberType 'NoteProperty' -Name $Property -Value $null
}
return $Object
}
Then putting the new function to use
$Kalle = New-CustomObject -PropertyArray "First","Last","Phone"
$Kalle.First = "Kalle"
$Kalle.Last = "Svensson"
$Kalle.Phone = "555 - 55 55 55"
$Kalle
First Last Phone
----- ---- -----
Kalle Svensson 555-55 55 55
And I'm done
Thursday, March 3, 2016
Finally, objects is making sence
I've been struggling with one last part of MS PowerShell for a while now, namely the internal data structures of PowerShell objects (and all .Net objects for that matter).
They are neat, but how do I define custom outputs in an easy way to read in my script code?
You've all read about Add-Member -type and New-Object System.Object.
They do work, but they are a pig to write.
Now, you might say "But why don't simply use hash tables?".
Well, they can't be ordered in PowerShell v2. You'll need PowerShell v3 to build it, i.e.
[ordered]@{First = "Sven"; Last = "Karlsson"}
and then there's the matter of hash tables only containing two values (key and value) which makes the construct confusing :/
Say I want to output a phone list as an object in PowerShell.
$propertyhashSven = @{}
$propertyhashSven.first = "Sven"
$propertyhashSven.last = "Karlsson"
$propertyhashSven.phone = "040-11 12 13"
> $propertyhashSven
Name Value
---- -----
last Karlsson
phone 040-11 12 13
first Sven
> $sven = New-Object PSObject -Property $propertyhashSven
> $sven
last phone first
---- ----- -----
Karlsson 040-11 12 13 Sven
The properties is not ordered at ALL :/
But how about this...
First thing is to define the object. The easiest way I found is to first create my own data type in C#.
add-type @"
public struct contact {
public string First;
public string Last;
public string Phone;
}
"@
Then, simply create the objects using that data type.
> $sven = New-Object contact
> $kalle = New-Object contact
And then populate it with some properties
> $sven.First = "Sven"
> $sven.Last = "Karlsson"
> $sven.Phone = "040-11 12 13"
> $kalle.first = "Kalle"
> $kalle.last = "Svensson"
> $kalle.phone = "08-555 555"
And then finally wrapping it up in a phone book as an array.
> $phonebook = @($sven,$kalle)
And there you go :)
> $phonebook
First Last Phone
----- ---- -----
Sven Karlsson 040-11 12 13
Kalle Svensson 08-555 555
Want to sort it by first name? No problems.
> $phonebook | Sort-Object First
First Last Phone
----- ---- -----
Kalle Svensson 08-555 555
Sven Karlsson 040-11 12 13
And adding more entries is just a matter of expanding the array...
> $sture = New-Object contact
> $sture.first = "Sture"
> $phonebook = $phonebook + $sture
> $phonebook
First Last Phone
----- ---- -----
Sven Karlsson 040-11 12 13
Kalle Svensson 08-555 555
Sture
And hopefully, it won't break anything ;)
They are neat, but how do I define custom outputs in an easy way to read in my script code?
You've all read about Add-Member -type and New-Object System.Object.
They do work, but they are a pig to write.
Now, you might say "But why don't simply use hash tables?".
Well, they can't be ordered in PowerShell v2. You'll need PowerShell v3 to build it, i.e.
[ordered]@{First = "Sven"; Last = "Karlsson"}
and then there's the matter of hash tables only containing two values (key and value) which makes the construct confusing :/
Say I want to output a phone list as an object in PowerShell.
$propertyhashSven = @{}
$propertyhashSven.first = "Sven"
$propertyhashSven.last = "Karlsson"
$propertyhashSven.phone = "040-11 12 13"
> $propertyhashSven
Name Value
---- -----
last Karlsson
phone 040-11 12 13
first Sven
> $sven = New-Object PSObject -Property $propertyhashSven
> $sven
last phone first
---- ----- -----
Karlsson 040-11 12 13 Sven
The properties is not ordered at ALL :/
But how about this...
First thing is to define the object. The easiest way I found is to first create my own data type in C#.
add-type @"
public struct contact {
public string First;
public string Last;
public string Phone;
}
"@
Then, simply create the objects using that data type.
> $sven = New-Object contact
> $kalle = New-Object contact
And then populate it with some properties
> $sven.First = "Sven"
> $sven.Last = "Karlsson"
> $sven.Phone = "040-11 12 13"
> $kalle.first = "Kalle"
> $kalle.last = "Svensson"
> $kalle.phone = "08-555 555"
And then finally wrapping it up in a phone book as an array.
> $phonebook = @($sven,$kalle)
And there you go :)
> $phonebook
First Last Phone
----- ---- -----
Sven Karlsson 040-11 12 13
Kalle Svensson 08-555 555
Want to sort it by first name? No problems.
> $phonebook | Sort-Object First
First Last Phone
----- ---- -----
Kalle Svensson 08-555 555
Sven Karlsson 040-11 12 13
And adding more entries is just a matter of expanding the array...
> $sture = New-Object contact
> $sture.first = "Sture"
> $phonebook = $phonebook + $sture
> $phonebook
First Last Phone
----- ---- -----
Sven Karlsson 040-11 12 13
Kalle Svensson 08-555 555
Sture
And hopefully, it won't break anything ;)
Subscribe to:
Posts (Atom)