Question:
I have this simple script:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 |
param([string[]]$to="markk", $subject=$null, $body=$null, $from="name", $suffix="@example.com", $server="dev-builder") function NormalizeAddress([string]$address) { if ($address -notmatch "@") { $address = $address + $suffix } $address } if (! $subject) { $subject = [DateTime]::Now } $from = NormalizeAddress $from $to = $to | % { NormalizeAddress $_ } Send-MailMessage -To $to -Subject $subject -From $from -Body $body -SmtpServer $server |
It is written that way so that one could run it without any arguments, in which case a test message would be sent to the author (me).
Currently the script fails, because passing $null
in the -Body
argument is not allowed:
1 2 3 4 5 6 |
Send-MailMessage : Impossible de valider l'argument sur le paramètre « Body ». L'argument est null ou vide. Indiquez un argument qui n'est pas null ou vide et réessayez. Au niveau de C:\Work\hg\utils\SendEmail.ps1 : 19 Caractère : 61 + Send-MailMessage -To $to -Subject $subject -From $from -Body <<<< $body -SmtpServer $server + CategoryInfo : InvalidData: (:) [Send-MailMessage], ParameterBindingValidationException + FullyQualifiedErrorId : ParameterArgumentValidationError,Microsoft.PowerShell.Commands.SendMailMessage |
I have three possible solutions:
- Two
Send-MailMessage
command statements:
1 2 3 4 5 6 7 8 9 |
if ($body) { Send-MailMessage -To $to -Subject $subject -From $from -Body $body -SmtpServer $server } else { Send-MailMessage -To $to -Subject $subject -From $from -SmtpServer $server } |
- Using
Invoke-Expression
:
1 2 3 4 5 6 7 8 |
$expr = "Send-MailMessage -To `"$to`" -Subject `"$subject`" -From `"$from`" -SmtpServer `"$server`"" if ($body) { $expr = "$expr -Body `"$body`"" } Invoke-Expression $expr |
- Simulating an empty body with a single space character:
1 2 3 4 5 6 |
if (! $body) { $body = " " } Send-MailMessage -To $to -Subject $subject -From $from -Body $body -SmtpServer $server |
All of these solutions look bad to me, because they all have this smell of being just hacks. I must be missing something really basic here, so my question is how can I pass the empty body without having to resort to these hacks?
Thanks.
Answer:
You can use a “splat” variable to pass parameters indirectly:
1 2 3 4 5 6 7 |
$extraParams = @{} if (-not [String]::IsNullOrEmpty($body)) { $extraParams['Body'] = $body } Send-MailMessage -To $to -Subject $subject -From $from -SmtpServer $server @extraParams |
Note use of @
to pass hash table of parameter-name parameter-value pairs (you can of course pass all the parameters this way, eg. in the initialisation of $extraParams
).