Please feel free to provide feedback or file bugs here.

Empty pipeline input has single $null item on slow ring build

I noticed this a few fast ring builds ago and now see it on the slow ring build #14295. For functions that declare at least one parameter and are marked [CmdletBinding()], $input.count is 1 even when no input is sent either on the pipeline or via param. The one element is $null. So if you had code that checks to see if input is from the pipeline using something like if($input.count) and expect 0 to mean no pipeline input is present, that breaks. Here is an example function:

function my-test {
[CmdletBinding()]
param(
[String]$blah
)

write-host $input.count
}

Calling my-test returns 1 on the slow ring build #14295 and 0 on RTM and psv4 too.

2 votes
Sign in
(thinking…)
Password icon
Signed in as (Sign out)

We’ll send you updates on this idea

Matt Wrock shared this idea  ·   ·  Flag idea as inappropriate…  ·  Admin →

3 comments

Sign in
(thinking…)
Password icon
Signed in as (Sign out)
Submitting...
  • Dave Wyatt commented  ·   ·  Flag as inappropriate

    If it helps, while investigating this behavior, I did notice another difference. Try running this code on different PS Versions:

    function Test-Input
    {
    [CmdletBinding()]
    param ( )

    process
    {
    $input.GetType().FullName
    }
    }

    Test-Input

    You'll find that in PSv2, $input was an enumerator (which is what the documentation states it should be.) In more recent versions, for some reason $input is an ArrayList object rather than an enumerator. (And even in versions of PowerShell where @($input).Count returns 0, the ArrayList itself still contains a single Null element.)

    I haven't tested it on v3 or v4 to figure out when that change took place, but it may be related as well.

  • Matt Wrock commented  ·   ·  Flag as inappropriate

    Looking more at this I realize I need to clarify my example since that actually will result in 1 on both versions. This modified example:
    function my-test {
    [CmdletBinding()]
    param(
    [String]$blah
    )
    $test=@($input)
    write-host $test.count
    }
    will write 1 on psv4/5RTM and 1 on new builds. So $input has to be forced to an array. I believe I do that because I found it to work universally on psv2,3,4.

Feedback and Knowledge Base