When you’re learning PowerShell one of the first things you will notice is that you don’t have to use the full parameter name. This is because of something called parameter disambiguation.
When it works
For instance, instead of saying Get-ChildItem -Recurse, you can say Get-ChildItem -R. Get-ChildItem only has one (non-dynamic) parameter that started with the letter ‘R’.. Since only one parameter matches, PowerShell figures you must mean that one. As a side note, dynamic parameters like -ReadOnly are created at run-time and are treated a bit differently.
Here’s the error message. Notice that it included a couple of other parameters as possibilities:
When it doesn’t work
This doesn’t always work, though. An easy example is with Get-Service. You can’t say Get-Service -In because you haven’t specified enough of the parameter name for PowerShell to work out what parameter you meant. With Get-Service, both -Include and -InputObject start with -In, so PowerShell can’t tell which of these you meant.
Trying it ourselves
Let’s write a quick function to make sure we understand what’s going on.
function test-param{ Param($da,$de) $true }
Calling this function with test-param -d gives us the same kind of error as before:
Interestingly (this is the surprise) if we make this an advanced function (and we should almost always do that), something strange happens.
function test-param{ [CmdletBinding()] Param($da,$de) $true }
Remember that one of the benefits of having an advanced function is that it now supports common parameters (like -debug).
When we call it with test-param -de, however, we don’t get an ambiguous parameter message! It’s asking for a value for -de!
So, even though we got a couple of common parameters in the error message for Get-Service -In, the -Debug common parameter isn’t considered in the disambiguation for this function.
Not earth-shattering, but something to take note of.
If I’m missing something (and it’s entirely possible), let me know in the comments.
-Mike
P.S. Remember that it is a best practice to spell out parameter names fully when writing a script. Abbreviating (and aliases) are considered fair game for the command-line, though.
Pingback: PowerShell Parameter Disambiguation and a Surprise - How to Code .NET