Wednesday, January 17, 2007

PowerShell CmdLet Parameters 101 (Part II)

In the first chapter I established the relationship between two of the available "Attributes" for CmdLet properties.  The two I chose were chosen because they are immediately usable and I can very quickly demonstrate their usefulness.

The next two useful "Attributes" I am going to explore are [Alias] and [HelpMessage].  Neither of these are obvious in usage nor in demonstration.

Let's explore [Alias] first.  The Alias attribute looks like this.

[Alias( alias1,alias2,...)]

By itself on a property it is declared thusly:

[Alias( alias1,alias2,...)] Public Property MyProperty

When combined with "Parameter" it looks like this:

[Alias( alias1, alias2)] _

[Parameter()] _

Public Property MyProperty

What does "Alias" do?

The Alias attribute allows us to give alternate names to the same property. 

Suppose we want to pass an object in the pipeline that contains a user name property called "Fullname".  Our CmdLet doesn't accept "Fullname" but does look for "Name". 

Couldn't we just add another property? 

Well we could but we can more easily just add an "Alias" - "Fullname".  This would allow the exact same code to execute and allow the same property to bind to objects that express "Name" or "Fullname".

There is an actual example of this in the Windows PowerShell Programmer's Guide code sample for CmdLet building that uses the Get-Process CmdLet to demonstrate the use of an Alias.  Get-Proc defines the property "ProcesssID" with the  Alias "ID" as a shorthand for ProcessID. ( see Adding Aliases, Wildcard Expansion, and Help to Cmdlet Parameters )

If I modify my test CmdLet "Name" property like this:

<[Alias](foobar)> _

<Parameter( _

           Position:=0, _

          ValueFromPipelineByPropertyName:=True)> _

Public Property Name

I can do this:

                                                                                                                                                                                                                                      
PS>test-cmdlet -foobar SomeFooBar                                                                                       
                                                                                                                        
Name                 Stopping CommandRuntime                          
----                 -------- --------------                          
SomeFooBar           False Test-Cmdlet                             
                                                                                                                        

Now "-foobar" can set the Name property from the command line or from the pipeline.  Notice that the property is still "Name" so all code references to this will continue to be the same.  All internal references within the CmdLet will reference "Name" and external references from outside the CmdLet code can reference either "Name" or "foobar".

So the "Alias" attribute is pretty easy to describe.  What about the "HelpMessage" value of the Parameter attribute?  How does it look?  What does it do?

The "HelpMessage" value looks like this:

HelpMessage:="some useful message"

It is added into the list of values following the "Parameter" declaration.

<[Alias](foobar)> _

<Parameter( _

          HelpMessage:="some useful message" ,  _

           Position:=0, _

          ValueFromPipelineByPropertyName:=True)> _

Public Property Name

Help message adds useful runtime information that can be displayed with the Get-Command utility CmdLet. 

                                                                                                                        
PS>get-bufferhtml 15 >d:\buffer.txt                                                                                     
PS>((gcm test-cmdlet).Parametersets[0].parameters)[0]                                                                   
                                                                                                                        
                                                                                                                        
Name                            : Name                                                                                  
ParameterType                   : System.String                                                                         
IsMandatory                     : False                                                                                 
IsDynamic                       : False                                                                                 
Position                        : 0                                                                                     
ValueFromPipeline               : False                                                                                 
ValueFromPipelineByPropertyName : True                                                                                  
ValueFromRemainingArguments     : False                                                                                 
HelpMessage                     : Some useful message.                                                                  
Aliases                         : {TheName, foobar}                                                                     
Attributes                      : {System.Management.Automation.AliasAttribute, __AllParameterSets}                     
                                                                                                                                                                                                                                                                                                                                                                                                                             

Notice that this message show up in the properties of a property.  Notice also that all of the aliases are listed here too.

The command I used to explore this gets the members of the default CmdLet "PropertySet" and gets the first property in the set which is out "Name" property.  All of these items listed are the standard  attributes of a PowerShell property object.  Notice that the "ValueFromPipelineByPropertyName" parameter value is listed and set to true.  The "Position" is set to zero.

"Get-Command" is how we read these values incase we need to know how a command works.  The "HelpMessage" should contain useful hints on how to use the property. It's kind of a mini  help system built into the CmdLet that can let us quickly assess the how a property is to be used.

Next I will try and unwind PropertySets.

 Here is the complete and latest code.

Imports System.Management.Automation

<Cmdlet(VerbsDiagnostic.Test, "Cmdlet", SupportsShouldProcess:=True)> _
Public Class Test_Cmdlet
    Inherits Cmdlet

    Private _Name As String
    '<Parameter(Position:=0, Mandatory:=False)> _
    <Parameter( _
         HelpMessage:="Some useful message.", _
         Position:=0, _
         ValueFromPipelineByPropertyName:=True)> _
    <[Alias]("TheName", "foobar")> _
    Public Property Name() As String
        Get
            Return _Name
        End Get
        Set(ByVal value As String)
            _Name = value
        End Set
    End Property

    Protected Overrides Sub ProcessRecord()
        Try
            WriteObject(Me)
        Catch ex As Exception

        End Try
    End Sub

End Class

Technorati tags: ,
del.icio.us tags: ,

No comments:

Post a Comment