function - Powershell implicitly converting arrays preventing use with Select -Property in v2 -


i struggling powershell implicitly modifying structure of data in powershell 2 exclusively. same logic works fine in powershell 4.

i've created helper function given field, alias and/or block expression can feed second function builds name/expression array can passed select -property request. worked fine in powershell 4 i'm working in mixed environment , when tried use on powershell 2 server script failed returning datatype conversion error.

cannot convert system.management.automation.psobject 1 of following types {system.string, system.management.automation.scriptblock}. + categoryinfo          : invalidargument: (:) [select-object], notsupportedexception + fullyqualifiederrorid : dictionarykeyunknowntype,microsoft.powershell.commands.selectobjectco    mmand + pscomputername        : #### 

i have rebuild array in calling function because explicit conversion array raises same exception.

if ($psversiontable["psversion"].major -eq 2) {     #write-host "rebuilding setting"     $origprops = [system.array](get-selectpropertyarray2 $propstoselect)     $props = @()     ($i =0 ; $i -lt $origprops.count ; $i++)     {         #write-host $i         $props += @{n=([system.array]$origprops)[$i]["n"];e=(([system.array]$origprops)[$i]["e"])}     } } 

the following insufficient:

[system.array](get-selectpropertyarray2 $propstoselect) 

when gettype() @ initialization, addition array , return statements type system.object, system.array

however in calling function becomes system.hashtable

here example of using function:

$propstoselect = @("name","path","pspath") # get-selectpropertyarrayset takes field return, alias , optional code block (to override default) $propstoselect += get-selectpropertyarrayset "." "asp_appallowclientdebug" {                     (get-webconfigurationproperty -filter /system.webserver/asp -name appallowclientdebug -pspath $pspath).value } $propstoselect += get-selectpropertyarrayset "." "asp_appallowdebugging" {                     (get-webconfigurationproperty -filter /system.webserver/asp -name appallowdebugging -pspath $pspath).value }  $props = (get-selectpropertyarray2 $propstoselect) # following line 1 fails $config = get-item $pspath | select -property $props 

the following line 1 fails unless rebuild array shown above.

$config = get-item $pspath | select -property $props 

when write out types, following results:

ps c:\scripts\ps\bits> $p = get-selectpropertyarray2 $set init:  ispublic isserial name                                     basetype -------- -------- ----                                     -------- true     true     object[]                                 system.array   inc alias:  ispublic isserial name                                     basetype -------- -------- ----                                     -------- true     true     object[]                                 system.array   return:  ispublic isserial name                                     basetype -------- -------- ----                                     -------- true     true     object[]                                 system.array   ps c:\scripts\ps\bits> $p.gettype()  ispublic isserial name                                     basetype -------- -------- ----                                     -------- true     true     hashtable                                system.object 

as can see last 1 quite different, if use on select statement fail exception shown previously.

here functions code:

<#     .synopsis     generates psobject field/alias/expression set use get-selectpropertyarray2 function.     .description     generates psobject field/alias/expression set use get-selectpropertyarray2 function.      alias property optional      .example     get-selectpropertyarrayset "name"      .example      get-selectpropertyarrayset "accessflags" "access flags"      .example      get-selectpropertyarrayset "accessflags" "access flags"      .example     $propstoselect = @(                         (get-selectpropertyarrayset "name"),                         (get-selectpropertyarrayset "accessflags" "access flags"),                         (get-selectpropertyarrayset "authanonymous" "auth anonymous")                         )      get-selectpropertyarray2  $propstoselect      .parameter field     [string] name of field select     .parameter alias     [string] alias name of field select     .parameter expression     [scriptblock] script block use capturing data, allows custom field definitions outside standard aliasing.  #> function get-selectpropertyarrayset  {     [cmdletbinding()]     param(         [parameter(mandatory=$true)]         [alias("f")]            [string]$field,         [parameter(mandatory=$false)]         [alias("a")]            [string]$alias,         [parameter(mandatory=$false)]         [alias("e")]            [scriptblock]$expression     )     #write-host "building property set $field, $alias"# $expression"     new-object psobject -property @{field=$field; alias=$alias; expression=$expression} } 

and second function (the lines write out data types included commented out):

<#     .synopsis     generates array of script blocks can passed select statement. aliasing field name.     .description     generates array of script blocks can passed select statement. aliasing field name.      input psobject field , alias property      example:     field:    alias:            -----------  ------------     name         name     myfield      myfield alias      helper function get-selectpropertyarrayset can used create psobject.      .example     $propstoselect = @(                         (get-selectpropertyarrayset "name"),                         (get-selectpropertyarrayset "accessflags" "access flags"),                         (get-selectpropertyarrayset "authanonymous" "auth anonymous")                         )     $propstoselect | get-selectpropertyarray2      .example     $propstoselect = @(                         (get-selectpropertyarrayset "name"),                         (get-selectpropertyarrayset "accessflags" "access flags"),                         (get-selectpropertyarrayset "authanonymous" "auth anonymous")                         )      get-selectpropertyarray2  $propstoselect     .example     $propstoselect = @(                         (new-object psobject -property @{field="name"}),                         (new-object psobject -property @{field="accessflags"; alias="access flags"}),                         (new-object psobject -property @{field="authanonymous"; alias="auth anonymous"})                         )      get-selectpropertyarray2  $propstoselect         .parameter propertiestoselect     [psobject] array containing field/alias pair use  #> function get-selectpropertyarray2 {     [cmdletbinding()]     param(         [parameter(mandatory=$true,valuefrompipeline=$true)]         [alias("prop")]            [psobject]$propertiestoselect     )     begin {         #initialize property-array select-object         $proparray = @()         #write-host "init"         #write-host init:          #$proparray.gettype() | out-host      }     process {          #create script block each field in input array/pipeline         #write-host "start"         #$propertiestoselect | select field,alias         foreach ($propertyset in $propertiestoselect)         {             $sb = $null             if ($propertyset.gettype().name -eq "string")             {                 #write-host string found                 $fieldname = $propertyset                 $fieldalias = $null             }             else             {                 #write-host object found                 $fieldname = $propertyset.field                 $fieldalias = $propertyset.alias                   #use provided expression if present , valid type                 if ($propertyset.expression)                 {                     #write-host "expression found"                     #$propertyset.expression.gettype().name                     switch ($propertyset.expression.gettype().name)                     {                         "scriptblock"                         {                             #write-host "expression [scriptblock]"                             $sb = $propertyset.expression                         }                         "string"                         {                             #write-host "expression [string], converting [scriptblock]"                              $sb = [scriptblock]::create($propertyset.expression)                         }                     }                 }             }                if (! ($sb)) { <#write-host "no sb, using default";#> $sb = [scriptblock]::create("`$_.`"$fieldname`"") }              #"mapping field: {0} --> {1}" -f $fieldname,$fieldalias |write-host             if ($fieldalias)             {                 #write-host inc alias:                  #$proparray.gettype() | out-host                 $proparray += @{n=[string]$fieldalias;e=($sb)}             }             else #singleton - no alias             {                 #write-host inc field:                  #$proparray.gettype()  |out-host                 $proparray += @{n=[string]$fieldname;e=($sb)}             }         }          # return script block array         #write-host "end"         #write-host "<--$propertiestoselect"       }     end {         #write-host "return:"         #write-host return:          #$proparray.gettype() |out-host            return $proparray     }  } 

there 2 differences in v2 vs v4 related issue:

  1. objects returned return statement, wrapped psobject in v2:

    [type]::gettypearray(@(&{return "name"}))[0].fullname 

    return system.management.automation.psobject in v2 , system.string in v4.

  2. select-object cmdlet in v2 can not handle wrapped objects property parameter:

    select-object (,[psobject]"name") 

    error in v2, ok in v4.

ps:
can ask 1 thing? benefits have this:

$propstoselect = @(     get-selectpropertyarrayset "name"     get-selectpropertyarrayset "accessflags" "access flags"     get-selectpropertyarrayset "authanonymous" "auth anonymous" ) $props = get-selectpropertyarray2 $propstoselect 

or this:

$propstoselect = @(     new-object psobject -property @{field="name"}     new-object psobject -property @{field="accessflags"; alias="access flags"}     new-object psobject -property @{field="authanonymous"; alias="auth anonymous"} ) $props = get-selectpropertyarray2 $propstoselect 

over this:

$props = @(     "name"     @{expression="accessflags"; name="access flags"}     @{expression="authanonymous"; name="auth anonymous"} ) 

?


Comments

Popular posts from this blog

css - SVG using textPath a symbol not rendering in Firefox -

Java 8 + Maven Javadoc plugin: Error fetching URL -

node.js - How to abort query on demand using Neo4j drivers -