Build Your Own PowerShell Cmdlet: Part 7 of 9

Summary: Microsoft Windows PowerShell MVP, Sean Kearney, continues a series of guest blogs detailing building your own cmdlet.

Microsoft Scripting Guy, Ed Wilson, is here. Guest blogger and Windows PowerShell MVP, Sean Kearney, has written a series about building cmdlets. For more about Sean, see his previous guest blog posts.

Note This is Part 7 of a nine-part series about building your own Windows PowerShell cmdlet. Read the entire series as it unfolds.

Here’s Sean…

Begin, Process, and End blocks

So far, we haven’t discussed three sections for your cmdlet. They are Begin, Process, and End.

  • The Begin block runs only once for each instance of the cmdlet. An example of script that you could place here might be the definition of static variables that will never change.

  • The Process block can be more dynamic in nature. It will run for each record in the pipeline. If you ran Import-CSV for some data and piped it to your cmdlet, for every row that existed within the CSV, this block of script would execute.

  • The End block also runs only once for each instance of the cmdlet. It is meant for any clean-up that may need to be performed, for example, closing open files that were created by the cmdlet.

We’ll modify our current advanced function to more correctly reflect processing the cmdlet.

Because we are going to be piping in data, and we are no longer dealing with a single element by default, we must adjust the parameters to reflect this. Whenever we pass data through the Process block, it is received as a single-element object array. To your script, this is actually a very minor change—simply alter each passed parameter in the Process block with a [0] to reflect this.

In our current cmdlet, we would look for references to the $Folder, $Preface, and $Extension variables. Most of the actual processing of our cmdlet will happen in the Process block, and this is where you need to ensure that you affect those changes on the variables.

Our current cmdlet modified to have its structure broken into appropriate script blocks, with variables reflecting input from the pipeline, will look like this.

function global:ADD-LOGFILE{

 

[CmdletBinding(

DefaultParameterSetName=”Folder”,

SupportsShouldProcess=$True,

ConfirmImpact=’High’

)]

 

PARAM(

 

[parameter(Mandatory=$True,

ValueFromPipeline=$True,

Position=0,

HelpMessage=’Folder to Store Logfiles in’)]

[STRING[]]$Folder=”C:PowerShell”,

 

[parameter(ValueFromPipeline=$True,

Position=1,

HelpMessage=’TEXT to prepend all logfiles with’)]

[STRING[]]$Preface=”Logfile”,

 

[parameter(ValueFromPipeline=$True,

Position=1,

ValueFromPipelineByPropertyName=$True,

HelpMessage=’File Extension for Logfiles’)]

[STRING[]]$Extension=”.log”

)

 

Begin {}

Process {

 

WRITE-DEBUG “`$Folder: $Folder[0]”

WRITE-DEBUG “`$Preface: $Preface[0]”

WRITE-DEBUG “`$Extension: $Extension[0]”

 

# GET the Current Date for our Logfile

 

$Today=GET-DATE

WRITE-DEBUG “`$Today: $Today”

# Extract the Date removing the “/”

 

$Date=$Today.toshortdatestring().Replace(“/”,””)

WRITE-DEBUG “`$Date: $Date”

 

# Extract the Time removing the “:”

 

$Time=$Today.tostring(“HH:mm:ss”).Replace(“:”,”“)

WRITE-DEBUG “`$Time: $Time”

 

# Build our Filename

 

$Logfilename=$Folder[0]+””+$Preface[0]+”-“+$Date+”-“+$Time+$Extension[0]

WRITE-DEBUG “`$Logfilename: $Logfilename”

 

# Test and ensure file does not already exist

 

IF (TEST-PATH -path $Logfilename)

 

{ WRITE-ERROR –message “Error: $Logfilename exists.” –category ‘WriteError’

 

# If file exists, return a status of Boolean $False for Unsuccessful

 

RETURN $Logfilename,$FALSE }

 

ELSE

 

{

 

# Create logfile

 

NEW-ITEM –Type File -path $Logfilename -Force | OUT-NULL

WRITE-DEBUG “$Logfilename successfully created”

 

# Return the Full path and filename if successful

 

RETURN $Logfilename,$TRUE

}

End {}

}

}

~Sean

Thank you, Sean. You are a marathoner, and you are really going the distance on this series. Guest Blogger Week will continue tomorrow when Sean will bring us Part 8.

I invite you to follow me on Twitter and Facebook. If you have any questions, send email to me at scripter@microsoft.com, or post your questions on the Official Scripting Guys Forum. See you tomorrow. Until then, peace.

Ed Wilson, Microsoft Scripting Guy