Envía correos electrónicos fácilmente con el cmdlet Send-MailMessage de PowerShell

Para el cmdlet de PowerShell del día, estamos cubriendo el cmdlet Send-MailMessage. Este cmdlet de PowerShell tiene un propósito y solo un propósito; enviar correos electrónicos de muchas maneras diferentes.

Dado que hay tantas formas en que el cmdlet Send-MailMessage puede enviar mensajes de correo electrónico, sumerjámonos y comencemos a cubrir todos los ejemplos comunes que puedas encontrar. En este artículo, vamos a abordar muchos ejemplos, desde los más simples hasta algunos escenarios que no le deseo a nadie.

Este post será un excelente recurso para marcar en caso de que te encuentres en situaciones donde necesitas enviar correos electrónicos con PowerShell y olvides la sintaxis.

El servidor SMTP

Todo correo electrónico debe pasar por un servidor SMTP en algún lugar, a través de un servidor y un puerto. Para especificar el servidor SMTP a utilizar, usa un parámetro llamado SMTPServer que te permite especificar el servidor SMTP para establecer una conexión y retransmitir el correo. Sin embargo, no es obligatorio.

Si no especificas un valor para el parámetro SMTPServer, se utilizará el valor almacenado en la variable de preferencia $PSEmailServer. Puedes asignarle un valor a esta variable de la misma manera que lo harías con cualquier otra variable.

Assigning a value to the $PSEmailServer preference variable
PS51> $PSEmailServer = 'smtp.server.local'

Sin embargo, esta variable no persiste a lo largo de las sesiones de PowerShell. Esto significa que debes definirla cada vez que se abre una nueva sesión de PowerShell. Por esta razón, recomendaría o bien utilizarla definiéndola antes de tu referencia a Send-MailMessage o simplemente no definirla en absoluto. En su lugar, personalmente sugeriría proporcionar el valor del parámetro SMTPServer. De esta manera, no tienes que gestionar una variable externa que podría cambiar inesperadamente.

PS51> Send-MailMessage -SmtpServer 'smtp.server.local'

Port

Por defecto, el valor con el que el cmdlet intentará enviar un correo electrónico a través del servidor SMTP es el puerto 25. Este es un SMTP sin cifrar. Sin embargo, hoy en día, es más común enviar correos electrónicos cifrados utilizando SSL/TLS (abordaremos estos escenarios más adelante).

Si necesitas cambiar el puerto desde 25, puedes utilizar el parámetro Port.

PS51> Send-MailMessage -SmtpServer 'smtp.server.local' -Port 587

Destinatarios y Remitentes

Para enviar un correo electrónico a diferentes destinatarios mediante métodos como los campos To, Cc y Bcc, el cmdlet tiene varios parámetros para acomodar esto.

Los parámetros To, Cc y Bcc en el cmdlet Send-MailMessage

El cmdlet tiene tres parámetros, cada uno admitiendo múltiples destinatarios separados por una coma llamados To, Cc y Bcc.

Puedes especificar direcciones individuales como se muestra a continuación.

Sending email to one recipient via To, Cc and Bcc
PS51> Send-MailMessage -To joe@gmail.com -Cc bob@gmail.com -Bcc susie@hotmail.com -Subject 'this is a subject'

O puedes especificar múltiples destinatarios para cada valor de parámetro.

Sending email to multiple recipients via To, Cc and Bcc
PS51> Send-MailMessage -To joe@gmail.com, tony@mycompany.local -Cc bob@gmail.com, rick@othercompany.com -Bcc susie@hotmail.com,secret@fooorg.org -Subject 'this is a subject'

El parámetro From

Cuando envíes un correo electrónico, también puedes especificar el parámetro From, que establecerá el encabezado de respuesta en el correo electrónico. Este parámetro solo permite una dirección. Si un destinatario elige responder al correo electrónico, esta será la dirección de correo electrónico a la que volverá la respuesta.

Sending email from an address
PS51> Send-MailMessage -From me@company.org -To joe@gmail.com -Subject 'this is a subject'

De forma predeterminada, al usar una dirección de correo electrónico, simplemente se mostrará la dirección de correo electrónico en el campo FROM del destinatario. Sin embargo, si deseas especificar un nombre o algún tipo de etiqueta como Service Account Mailbox, también puedes especificar un nombre y un correo electrónico como:

Adam Bertram <adbertram@gmail.com>

Observa que se utilizó el parámetro Subject. Este parámetro siempre es obligatorio. Verás que se utiliza este parámetro en todos los ejemplos.

Cuerpo

El parámetro Body te permite especificar qué contendrá el cuerpo del correo electrónico. En su forma más simple, puedes especificar cualquier texto que desees y el cmdlet lo enviará como texto sin formato.

PS51> Send-MailMessage -From me@company.org -To joe@gmail.com -Subject 'this is a subject' -Body 'this is the body'

Envío de correos electrónicos con cuerpo HTML

También puedes enviar un cuerpo de correo electrónico mediante HTML en lugar de texto sin formato. Para hacerlo, utiliza el mismo parámetro Body que usarías con texto sin formato, pero utiliza HTML para la cadena y utiliza el parámetro de interruptor BodyAsHtml.

Sending an HTML table in an email
$body = @' <table style="width:100%"> <tr> <th>Firstname</th> <th>Lastname</th> <th>Age</th> </tr> <tr> <td>Jill</td> <td>Smith</td> <td>50</td> </tr> <tr> <td>Eve</td> <td>Jackson</td> <td>94</td> </tr> </table> '@ PS51> Send-MailMessage -From me@company.org -To joe@gmail.com -Subject 'this is a subject' -Body $body -BodyAsHtml

Observa en el ejemplo anterior, encerré la cadena de cuerpo en @' y '@. Esto se llama un cadena aquí. Esto te permite definir cadenas largas típicamente vistas en cuerpos de correo electrónico que contienen saltos de línea. Las cadenas aquí conservan el formato de las cadenas y es una excelente manera de definir el cuerpo del correo electrónico, especialmente si está en HTML.

Codificación

Si tienes caracteres especiales en el asunto o cuerpo de tu correo electrónico, puedes usar el parámetro Codificación. Este parámetro te permite codificar el asunto y el cuerpo del correo electrónico mediante el tipo de codificación especificado antes de enviarlo.

Tienes algunas opciones aquí:

  • ASCII (predeterminado)
  • UTF8
  • UTF7
  • UTF32
  • Unicode
  • BigEndianUnicode
  • Por defecto
  • OEM
PS51> Send-MailMessage -From me@company.org -To joe@gmail.com -Subject 'this is a subject' -Body 'this is the body' -Encoding UTF8

Archivos adjuntos

El cmdlet también puede adjuntar uno o más archivos. Para hacerlo, puedes usar el parámetro ArchivosAdjuntos y proporcionar la ruta del archivo(s) que deseas adjuntar.

Attaching the C:\file.doc to an email
PS51> Send-MailMessage -From me@company.org -To joe@gmail.com -Subject 'this is a subject' -Body 'this is the body' -Attachments 'C:\file.doc'

También puedes especificar varios archivos adjuntos mediante una colección separándolos con una coma.

Attaching the C:\file.doc and D:\report.xlsx file to an email
PS51> Send-MailMessage -From me@company.org -To joe@gmail.com -Subject 'this is a subject' -Body 'this is the body' -Attachments 'C:\file.doc','D:\report.xlsx'

El parámetro ArchivosAdjuntos también te permite enviar archivos mediante cmdlets como Get-Item y Get-ChildItem al cmdlet Send-MailMessage también.

PS51> Get-ChildItem -Path 'C:\MyFiles' | Send-MailMessage -From me@company.org -To joe@gmail.com -Subject 'this is a subject' -Body 'this is the body'

Correo electrónico seguro y autenticado

Por defecto, el cmdlet envía correos electrónicos a través de comunicación SMTP no cifrada por el puerto 25. Sin embargo, también admite el envío de correos electrónicos cifrados a través de SSL/TLS con un nombre de usuario y contraseña.

Si intentas retransmitir correos electrónicos a través de un servidor SMTP que requiere autenticación, el comando fallará con un mensaje de error como el siguiente.

Error message when attempting to send unencrypted email.
The SMTP server requires a secure connection or the client was not authenticated. The server response was: 5.7.0 Must issue a STARTTLS command first.

Para remediar esto, primero debes especificar el puerto (típicamente 587 para TLS) y el parámetro UseSsl. Esto indica al cmdlet que intente conectarse al puerto 587 en el servidor SMTP y cifrar el mensaje completo. Típicamente (¿siempre?) también deberás especificar el nombre de usuario/contraseña para autenticarte en el servidor SMTP mediante el parámetro Credential.

PS51> $credential = Get-Credential
PS51> Send-MailMessage -From me@company.org -To joe@gmail.com -Subject 'this is a subject' -Body 'this is the body' -UseSsl -Port 587 -Credential $credential

En el ejemplo, estoy obteniendo un objeto de credencial (PSCredential) usando el cmdlet Get-Credential. Esto a veces presenta un problema porque es interactivo, lo que significa que detiene el script para solicitar un nombre de usuario y una contraseña. Para evitar esto, podrías crear un objeto PSCredential al vuelo.

A common email example is to use Gmail. Using the knowledge you’ve gained above, you can now easily send email through Gmail using the smtp.gmail.com SMTP server as shown below.

$gmailCred = Get-Credential

$sendMailParams = @{
    From = '[email protected]' ## Debe ser gmail.com
    To = '[email protected]'
    Subject = 'some subject'
    Body = 'some body'
    SMTPServer = 'smtp.gmail.com'
    SMTPPort = 587
    UseSsl = $true
    Credential = $gmailCred
}

Send-MailMessage @sendMailParams

Asignación de Prioridad de Correo Electrónico

Aunque es una característica del correo electrónico que personalmente desearía que desapareciera, puedes asignar niveles de prioridad a los correos electrónicos que envías mediante el parámetro Priority. Esta prioridad luego es interpretada de diversas maneras por el cliente de correo electrónico.

High priority message in Outlook

Send-mailmessage te permite asignar un correo electrónico con tres prioridades diferentes.

  • Normal (predeterminado)
  • Alta
  • Baja
Assigning a high-priority email
PS51> Send-MailMessage -From me@company.org -To joe@gmail.com -Subject 'this is a subject' -Body 'this is the body' -Priority High

Pero por favor, por el amor de Dios, ¡no pienses que todos tus correos electrónicos son de alta prioridad!

Notificaciones de entrega

Finalmente, puedes especificar notificaciones de entrega para correos electrónicos. Las notificaciones de entrega son lo que comúnmente se conoce como recibos de lectura en algunos clientes de correo electrónico. Las notificaciones de entrega te permiten ser notificado si/cuando el correo electrónico es recibido por el destinatario. Sin embargo, el destinatario aún debe permitirlo.

Tienes cuatro opciones al solicitar notificaciones de entrega.

  • Ninguna (por defecto)
  • EnÉxito (cuando la entrega del correo es exitosa)
  • EnFallo (notificar si la entrega no tiene éxito)
  • Retraso (cuando el correo se retrasa a través de un servidor SMTP)

Puedes especificar una opción de notificación de entrega utilizando el parámetro DeliveryNotificationOptions.

Requesting a notification on delivery
PS51> Send-MailMessage -From me@company.org -To joe@gmail.com -Subject 'this is a subject' -Body 'this is the body' -DeliveryNotificationsOptions 'OnSuccess'

También puedes solicitar múltiples notificaciones de entrega a la vez separándolas con una coma.

Requesting a notification for all types
PS51> Send-MailMessage -From me@company.org -To joe@gmail.com -Subject 'this is a subject' -Body 'this is the body' -DeliveryNotificationsOptions 'OnSuccess','OnFailure','Delay'

Resumen

En esta publicación, aprendiste todo sobre el cmdlet Send-mailmessage y lo que puede hacer. Cubrimos este cmdlet extensamente utilizando todos los parámetros que tiene junto con ejemplos. Espero que esta publicación pueda servir como referencia para ti cuando uses el cmdlet Send-mailmessage.

Lectura Adicional

Asegúrate de revisar algunos otros posts relacionados!

Source:
https://adamtheautomator.com/send-mailmessage/