liveBook · Manning

Comment-based help

As explained in Learn PowerShell Scripting in a Month of Lunches, Second Edition: Write and organize scripts and tools

Comment-based help is a documentation convention in which specially formatted source-code comments provide help content for a PowerShell command or script.

Comment-based help turns specially formatted comments inside a PowerShell script or function into help content. It is the quickest way to make an automation tool understandable without maintaining a separate help file. section 14.0

Build useful help by documenting the command’s purpose, behavior, inputs, and usage:

  • Place a block comment where PowerShell searches for help comments, commonly at the beginning of a script or function. section 14.0 section 14.7
  • Use uppercase keywords such as .SYNOPSIS, .DESCRIPTION, .PARAMETER, and .EXAMPLE to organize the help. section 14.7
  • Add .INPUTS, .OUTPUTS, .NOTES, and separate .LINK entries when users need types, extra information, or related topics. section 14.3
  • Use editor snippets to create a repeatable template, and add whitespace when it improves readability; extra blank lines do not change generated help. section 14.6.3

Documenting a service-management function

A function such as Set-TMServiceLogon can describe its purpose with .SYNOPSIS, explain CIM and WMI behavior in .DESCRIPTION, and document ServiceName, ComputerName, NewPassword, and NewUser under .PARAMETER. The help can also state remote permission requirements and explain how computer names and IP addresses behave. section 14.6.3

Listing 14.3 Our solution
function Set-TMServiceLogon {
<#
.SYNOPSIS
Sets service login name and password.
.DESCRIPTION
This command uses either CIM (default) or WMI to
set the service password, and optionally the logon
user name, for a service, which can be running on
one or more remote machines. You must run this command
as a user who has permission to perform this task,
remotely, on the computers involved.
.PARAMETER ServiceName
The name of the service. Query the Win32_Service class
to verify that you know the correct name.
.PARAMETER ComputerName
One or more computer names. Using IP addresses will
fail with CIM; they will work with WMI. CIM is always
attempted first. 
.PARAMETER NewPassword
A plain-text string of the new password.
.PARAMETER NewUser
Optional; the new logon user name, in DOMAIN\USER
format.
.PARAMETER ErrorLogFilePath
If provided, this is a path and filename of a text
file where failed computer names will be logged.
#>
    [CmdletBinding()]
    Param(
        [Parameter(Mandatory=$True,
                   ValueFromPipelineByPropertyName=$True)]
        [string]$ServiceName,
        [Parameter(Mandatory=$True,
                   ValueFromPipeline=$True,
                   ValueFromPipelineByPropertyName=$True)]
        [string[]]$ComputerName,
        [Parameter(ValueFromPipelineByPropertyName=$True)]
        [string]$NewPassword,
        [Parameter(ValueFromPipelineByPropertyName=$True)]
        [string]$NewUser,
        [string]$ErrorLogFilePath
    )
BEGIN{}
PROCESS{
    ForEach ($computer in $ComputerName) {
        Write-Verbose "Connect to $computer on WS-MAN"
        $option = New-CimSessionOption -Protocol Wsman
        $session = New-CimSession -SessionOption $option `
                                  -ComputerName $Computer
        If ($PSBoundParameters.ContainsKey('NewUser')) {
            $args = @{'StartName'=$NewUser
                      'StartPassword'=$NewPassword}
        } Else {
            $args = @{'StartPassword'=$NewPassword}
            Write-Warning "Not setting a new user name"
        }
        Write-Verbose "Setting $servicename on $computer"
        $params = @{'CimSession'=$session
                    'MethodName'='Change'
                    'Query'="SELECT * FROM Win32_Service " +
                            "WHERE Name = '$ServiceName'"
                    'Arguments'=$args}
        $ret = Invoke-CimMethod @params
        switch ($ret.ReturnValue) {
            0  { $status = "Success" }
            22 { $status = "Invalid Account" }
            Default { $status = "Failed: $($ret.ReturnValue)" }
        }
        $props = @{'ComputerName'=$computer
                   'Status'=$status}
        $obj = New-Object -TypeName PSObject -Property $props
        Write-Output $obj
        Write-Verbose "Closing connection to $computer"
        $session | Remove-CimSession
    } #foreach
} #PROCESS
END{} 
} #function

Inspect a complete comment-based help listing for a function that changes service login credentials across remote machines. section 14.6.3

Comment-based help is convenient but limited: it stays close to the code and does not provide the separation, localization, or Update-Help workflow available through external MAML help. PlatyPS offers a Markdown-based path for generating MAML when documentation needs grow. section 14.5

How Learn PowerShell Scripting in a Month of Lunches, Second Edition: Write and organize scripts and tools covers it

How deep it goes
Explains comment placement, formatting, standard sections, advanced keywords, whitespace, and external-help trade-offs without detailing PowerShell’s complete help parser.
Examples
Uses Get-MachineInfo and Set-TMServiceLogon examples with parameter documentation, remote-service behavior, input types, notes, and links.
What it assumes
Assumes PowerShell scripting familiarity while teaching help keywords, placement, formatting, and documentation structure directly.
What you can do after
Build it from scratch by adding readable, structured help comments to a PowerShell function or script.
How it connects
Connects PowerShell help, external help files, MAML, Markdown, PlatyPS, and Update-Help.

Also explained in

Compare how 2 books explain comment-based help →

Related concepts

This explainer was generated by Manning's knowledge graph from the text of Learn PowerShell Scripting in a Month of Lunches, Second Edition: Write and organize scripts and tools. The section links point to the parts of the book it draws on.