locked
How to send digitally sign S/MIME messages with Powershell cmdlet Send-MailMessage? RRS feed

  • Question

  • Hello,

    using AD Windows PKI I assigned a certificate EKU (1.3.6.1.5.5.7.3.4) to sign emails and get this with autoenrollment also to my CERT Store PS CERT:\CurrentUser\UserDS\ or the certificate could found via MMC / certificates in the store structur under "Active Directory User Object".
    Signed messages (red icon) to send as S/MIME message using Outlook 2010 is not a problem.

    Using PowerShell cmdlet Send-MailMessage to be sent company notification for a new passwordpolicy some days before pwd expired?! I use the cmdlet already successfully to filling HTML bodies with variables and send to individuals accounts.

    Reduced simplified PS code:

    #
    $SMTPBodyHtmlTemplate = Get-Content "C:\PS\Template\HTMLBody.html" | Out-String
    #
    Function SendEmailNotification # /* SEND E-MAIL Notification to User */#
    {
    #
    [string] $SMTPServer = "mail.domain.local"
    #
    $CurrentUser = "$env:username"
    [string]$SMTPFrom = (Get-ADUser $CurrentUser -properties mail).mail
    #
    [string[]] $SMTPTo = $($Obj.EmailAddress)
    #
    [string]$SMTPSubject = "Notification!"
    #
    [String]$SMTPBodyHtml = $SMTPBodyHtmlTemplate.Replace("UserDisplayname","$($UserDisplayname)")
    #
    Send-MailMessage -From $SMTPFrom -To $SMTPTo -Subject $SMTPSubject -BodyAsHtml $SMTPBodyHtml -dno OnFailure -SmtpServer $SMTPServer -encoding ([System.Text.Encoding]::UTF8) -ErrorAction Continue
    #
    }
    #

    How can I use the PSDrive own CERT and using PowerShell cmdlet Send-MailMessage to send a signed message, without development experience?

    Thanks in advance for cooperation.


    Manfred Schüler

    Tuesday, March 17, 2015 1:59 PM

Answers

  • Hi,

    could create with an other colleague a DLL file (with this informations) for successfully sending sign messages from PS-Script. 

    Function SendEmailNotification # /* SEND SIGN E-MAIL */#
    {
    $SMTPBodyHtmlTemplate = Get-Content "C:\PS\Template\HTML.html" | Out-String
    [System.Reflection.Assembly]::LoadFile("C:\PS\Assembly\Cpi.Net.SecureMail.dll") | Out-Null
    [string]$strSmtpServer  = "smtp.domain.local"
    [string]$strSmtpPort    = "25"
    [string]$strFrom        = (Get-ADUser $CurrentUser -properties mail).mail
    [string]$strFromAlias   = (Get-ADUser $CurrentUser -properties DisplayName).DisplayName
    [string]$strTo          = $UserEmailAddress
    [string]$strToAlias     = $UserEmailDisplayName
    [String]$strSubject = "Subject as you like"
    [string]$strBody        = $SMTPBodyHtmlTemplate.Replace("UserDisplayname","$($UserDisplayname)")
    $objMail = New-Object Cpi.Net.SecureMail.SecureMailMessage
    $objFrom = New-Object Cpi.Net.SecureMail.SecureMailAddress($strFrom,$strFromAlias,$objCert,$objCert)
    $objTo   = New-Object Cpi.Net.SecureMail.SecureMailAddress($strTo,$strToAlias)
    $objMail.From = $objFrom
    $objMail.to.Add($objTo)
    $objMail.Subject = $strSubject
    $objMail.Body = $strBody
    $objMail.IsBodyHtml = $TRUE
    $objMail.IsSigned = $TRUE
    $objMail.IsEncrypted = $FALSE
    $objSMTPClient = New-Object System.Net.Mail.SmtpClient($strSmtpServer,$strSmtpPort)
    $objSMTPClient.Credentials = [System.Net.CredentialCache]::DefaultNetworkCredentials
    $objSMTPClient.send($objMail)
    }
    Maybe Microsoft can implement this in future versions of the cmdlets Send-MailMessage ;-)


    Manfred Schüler

    • Marked as answer by MSchueler Wednesday, April 8, 2015 7:03 AM
    Wednesday, April 8, 2015 6:36 AM

All replies

  • Hi Manfred Schüler

    have a look on following which may help you.

    http://dloder.blogspot.in/2013/08/sending-encrypted-smime-messages-with.html

    http://securitymusings.com/article/1967/tutorial-sending-smime-e-mail-from-net-code

    http://www.codeproject.com/Articles/41727/An-S-MIME-Library-for-Sending-Signed-and-Encrypted

    http://www.rebex.net/secure-mail.net/features/s-mime.aspx


    Thanks , Prakash ,Please Note: My Posts are provided “AS IS” without warranty of any kind, either expressed or implied.


    • Edited by p.th Friday, March 27, 2015 4:12 AM
    Friday, March 27, 2015 4:09 AM
  • Hi,

    could create with an other colleague a DLL file (with this informations) for successfully sending sign messages from PS-Script. 

    Function SendEmailNotification # /* SEND SIGN E-MAIL */#
    {
    $SMTPBodyHtmlTemplate = Get-Content "C:\PS\Template\HTML.html" | Out-String
    [System.Reflection.Assembly]::LoadFile("C:\PS\Assembly\Cpi.Net.SecureMail.dll") | Out-Null
    [string]$strSmtpServer  = "smtp.domain.local"
    [string]$strSmtpPort    = "25"
    [string]$strFrom        = (Get-ADUser $CurrentUser -properties mail).mail
    [string]$strFromAlias   = (Get-ADUser $CurrentUser -properties DisplayName).DisplayName
    [string]$strTo          = $UserEmailAddress
    [string]$strToAlias     = $UserEmailDisplayName
    [String]$strSubject = "Subject as you like"
    [string]$strBody        = $SMTPBodyHtmlTemplate.Replace("UserDisplayname","$($UserDisplayname)")
    $objMail = New-Object Cpi.Net.SecureMail.SecureMailMessage
    $objFrom = New-Object Cpi.Net.SecureMail.SecureMailAddress($strFrom,$strFromAlias,$objCert,$objCert)
    $objTo   = New-Object Cpi.Net.SecureMail.SecureMailAddress($strTo,$strToAlias)
    $objMail.From = $objFrom
    $objMail.to.Add($objTo)
    $objMail.Subject = $strSubject
    $objMail.Body = $strBody
    $objMail.IsBodyHtml = $TRUE
    $objMail.IsSigned = $TRUE
    $objMail.IsEncrypted = $FALSE
    $objSMTPClient = New-Object System.Net.Mail.SmtpClient($strSmtpServer,$strSmtpPort)
    $objSMTPClient.Credentials = [System.Net.CredentialCache]::DefaultNetworkCredentials
    $objSMTPClient.send($objMail)
    }
    Maybe Microsoft can implement this in future versions of the cmdlets Send-MailMessage ;-)


    Manfred Schüler

    • Marked as answer by MSchueler Wednesday, April 8, 2015 7:03 AM
    Wednesday, April 8, 2015 6:36 AM