EvotecIT / Mailozaurr

Mailozaurr is a PowerShell module that aims to provide SMTP, POP3, IMAP and probably some other ways to interact with Email. Underneath it uses MimeKit and MailKit libraries written by Jeffrey Stedfast.
MIT License
154 stars 15 forks source link

Feature Request: Signed mail #8

Open jschpp opened 5 years ago

jschpp commented 5 years ago

Hi there.

I love this collection of utilities and replaced some of my own tools with it. Would it be possible to add S/MIME signed mails to the Send-Email function?

Also on this topic: The System.Net.Mail.SmtpClient API is obsolete. Microsoft recommends using https://github.com/jstedfast/MimeKit

PrzemyslawKlys commented 5 years ago

Hi,

I know it's a bit obsolete however it's the only way that works and allows you to define EmailReplyTo. Send-MailMessage doesn't allow you to do that.

Does MimeKit allow you to do that?

I was thinking to move Send-Email to Emailimo, and as soon as most of my modules move to Emailimo (if I will be able to migrate them) scrap some Email functions out.

jschpp commented 5 years ago

Yeah. Send-MailMessage can't do signing either.

MimeKit can do pretty much everything. I've looked for ReplyTo specifically and there seems to be options for that. The documentation seems very comprehensive http://www.mimekit.net/docs/html/Creating-Messages.htm It looks like you could cast System.Net.Mail.MailMessage to MimeKit.MimeMessage as well.

You would need to pack MimeKit with Emailimo though.

jschpp commented 5 years ago

Also. After looking over System.Net.Mail.SmtpClient it looks like signing mails is non trivial... So if you don't want to migrate to MimeKit right now I can understand if this takes a while

PrzemyslawKlys commented 5 years ago

Well, I did take a look and it's not trivial. Most likely would require a separate module to cover all topics related to MimeKit. But let's keep this open. Maybe when I'll get time, or I'll be bored I'll take a look and implement something. If not signing then maybe migrate to mimekit to be 'supported'.

jschpp commented 5 years ago

I've found an Implementation of MailKit which handles closely to Send-MailMessage PSMailKit

As of now it's not on the gallery. I've opened an issue https://github.com/dbaileyut/PSMailKit/issues/7 to this end.

PrzemyslawKlys commented 4 years ago

I've done my own implementation of MailKit in https://github.com/EvotecIT/Mailozaurr

It doesn't yet have signing but I'm one step closer :-)

jschpp commented 4 years ago

I've done my own implementation of MailKit in https://github.com/EvotecIT/Mailozaurr

It doesn't yet have signing but I'm one step closer :-)

It looks quite good. I'm going to have a closer look next week :-)

DaveyRance commented 3 years ago

I am liking the Mailozaurr module so far but would like to +1 for the Signed mail. (Things like password expiry notifications would be great to be sent signed)

PrzemyslawKlys commented 3 years ago

I agree. It would be cool. Resources:

No promises - but when I'll get some free time I'll take a look.

jschpp commented 2 years ago

I had a few looks at SMIME functionality. The main problem as I see it is that we (the module) need to curate a database for certificate management.

Per default this would be a SQLite DB.

Shall we simply use SQLite or should there be a class which can be inherited from for Users/Admins to write their own implementation of SMIMEContext? Also there seems to be a WindowsDefaultContext which seems to access the windows certificate store. How should that one be provided?

The actual signing implementation itself is not that much work as soon as you have a context.

Here is an example with the windows default context:

index 5ed86b8..775f6db 100644
--- a/Public/Send-EmailMessage.ps1
+++ b/Public/Send-EmailMessage.ps1
@@ -530,6 +530,10 @@
     }
     $Message.Body = $BodyBuilder.ToMessageBody()

+    $ctx = $ctx = [MimeKit.Cryptography.WindowsSecureMimeContext]::new([System.Security.Cryptography.X509Certificates.StoreLocation]::CurrentUser)
+    $Signer = $Message.From.Mailboxes[0].Clone()
+    $Message.Body = [MimeKit.Cryptography.MultipartSigned]::Create($ctx, $Signer, [MimeKit.Cryptography.DigestAlgorithm]::Sha256, $Message.Body)
+
     ### SMTP Part Below
     $SmtpClient = [MySmtpClient]::new()
     if ($SkipCertificateRevocation) {

A few notes here

PrzemyslawKlys commented 2 years ago

As you can see I also tried the SMIME in the Testing-Certs branch but a bit failed attempt.

https://github.com/EvotecIT/Mailozaurr/blob/884faf3093166e50fff51c50285d7b8935c2557e/Public/Send-EmailMessage.ps1#L542

I saw windosecuremimecontext, but what about linux/macos. I am not sure what is the best approach. I would like it to be as portable as possible.

jschpp commented 2 years ago

I saw windosecuremimecontext, but what about linux/macos. I am not sure what is the best approach. I would like it to be as portable as possible.

In that case I'd say you should bundle System.Data.SQLite for Windows Systems and it should be possible to use that in concert with Mono.Data.Sqlite on Non Windows Systems.

The question then is where you want to store the SQLite DB per default.

Maybe I'll take a look at writing a Context this weekend

PrzemyslawKlys commented 2 years ago

Once you have something ready and working the path can be then decided. Let's work out the working solution.

I guess we should have something hardcoded if parameter is not provided, but also allow people to define location where the db is located, or maybe explicitly prompt for it - since it can be hard to define on macos/linux/winows to make sure all 3 locations are supported

PrzemyslawKlys commented 2 years ago

Proposed path

[Environment]::GetFolderPath([Environment+SpecialFolder]::LocalApplicationData)
[Environment]::GetFolderPath([Environment+SpecialFolder]::CommonApplicationData)

On windows:

image

On linux: image

PrzemyslawKlys commented 2 years ago

@jschpp any luck with creating this? I believe this would be greatly beneficial. Seeing as Integrated Auth will soon be a thing, I think we mostly miss Signing