none
Help - Best way to temporarily store outbound emails and release them later on command via custom transport agent RRS feed

  • Question

  • Hi,

    I have thought of two possible solutions to a problem we are having and am interested in getting some expert opinions on both.

    Problem: we have a custom exchange transport agent which analyses outbound emails as they pass through the exchange.  If certain conditions are met, then it needs to temporarily store this email whilst it sends an automated email to the sender asking for permission to release / delete.  When the sender replies yes / no, it then must either delete the email or release it for sending again.

    Solution 1 (current): we use a SQL database and write the email to this, storing a unique ID as key and the email parts with it (including attachments).  When the user response comes in, we use the email key to located the correct email and either delete it or rebuild the email and put in pickup folder to be sent

    Solution 2: we could use a new exchange mailbox and redirect the email to it for holding.  When user sends the response we then access the mailbox and resend the email, hopefully since the email was redirected it would be sent as the original.

    Questions:

    - I'm not 100% sure of our current implementation of storing/restoring the email in the SQL database (I didn't implement it), but from a technical / feasibility PoV, should this be okay and is it possible to always restore the email correctly without losing any info?

    - If we went with mailbox approach, is it possible to redirect email from transport agent?  Is it also possible to access mailbox and resend email from it via our transport agent code?

    Any other ideas on how we could implement this would be greatly appreciated :-).

    Thanks!

    Tom

    Monday, August 3, 2015 6:47 PM

All replies

  • Another method you can use is just write the Email to disk on the Hub server where the agent is running and then use the replay directory when you want to send it https://technet.microsoft.com/en-us/library/bb124230%28v=exchg.150%29.aspx . In this way everything is self contained on the MTA and you have no high availability type issues with using SQL server or such.

    Cheers
    Glen

    Tuesday, August 4, 2015 4:21 AM
  • Hi Ken,

    Thanks for your response.  One other criteria I forgot to mention is that this needs to work in multi-exchange environments where an email might pass through a different exchange or a couple of exchanges before finally being sent out, and the user email response confirming to send or not may not pass through the exact same exchange where the email is being held.

    Our solution needs to allow all the transport agents on the same forest to access where the messages are being stored, and for there to be some sort of failover or backup process if this location isn't accessible. With a SQL database we could distribute it so that there are alternative versions that are accessible if the primary one fails to connect, and I believe that with a mailbox there are also some MS protections / backups.

    When you say to write the email to disk, is this just to a folder the we create somewhere and will this be accessible from other Hub servers? (is the multi hub server thing I mentioned even a problem?)

    Also, is it easy / quick to locate an email by ID from this folder on disk and then move it to the replay directory / pickup directory?

    Thanks,

    Tom

    Tuesday, August 4, 2015 9:47 AM
  • >>Thanks for your response.  One other criteria I forgot to mention is that this needs to work in multi-exchange environments where an email might pass through a different exchange or a couple of exchanges before finally being sent out, and the user email response confirming to send or not may not pass through the exact same exchange where the email is being held.

    That sounds like you should be using moderation instead that functionality is already built into exchange https://technet.microsoft.com/en-us/library/dd298007(v=exchg.150).aspx

    >>When you say to write the email to disk, is this just to a folder the we create somewhere and will this be accessible from other Hub servers? (is the multi hub server thing I mentioned even a problem?) Also, is it easy / quick to locate an email by ID from this folder on disk and then move it to the replay directory / pickup directory?

    If you went down this route all your doing in the Transport agent is writing the message to disk all the other intelligence your asking about you need to create (eg write another agent or service to managed it)

    Using the replay directory https://technet.microsoft.com/en-us/library/bb124230(v=exchg.150).aspx is pretty straight forward the Envelope recipients should be entered as X-Receiver so you can still cater for BCC etc .

    Cheers
    Glen

    Tuesday, August 4, 2015 11:35 PM
  • Thank Glen.

    Unfortunately the inbuilt moderation doesn't do everything that we need it to, so we are having to build a custom hold / release system for exchange.  What is the difference when using the pickup vs replay directory?  I think we are currently using just the pickup directory to recollect the message after we have built it again from the SQL database where it is temporarily stored...

    Also, is a transport agent able to access a mailbox and release emails from there, since if so we could use that mailbox approach I mentioned earlier rather than storing in a SQL db?

    When I mentioned multiple exchanges, I am assuming all of them will have access to a specific mailbox, since each server with Hub transport role installed with our transport agent will need to access it to release the emails?

    Thanks again for your patience here with all these questions!

    Tom

    Wednesday, August 5, 2015 12:10 PM
  • >> What is the difference when using the pickup vs replay directory?

    Pickup is meant to be used to submit new email while replay is designed to be used to resubmit messages that where removed from the Transport pipeline by things like a Quarantine process etc. Or technically the Pick up directory uses the P2 header and the replay directory uses the P1 headers (via the X-headers) see http://blogs.technet.com/b/eopfieldnotes/archive/2014/09/26/p2-headers-now-respected-for-end-user-safe-and-blocked-senders-lists.aspx. Take for example a message that has been send to two email addresses fred@internal and Bob@external you stop the message but only after the message has already been delivered to Bob@external. If you used the pickup directory to resubmit the message then Bob@external would get another copy of the message because his address in is P2 headers. If you used the replay directory and because you saved of the envelope recipients (which are the P1 recipients) of the message originally so you knew the message has already been delivered to bob@external when you resubmitted the message to the replay directory with only 1 X-Receiver header for fred@internal only fred would get the message.

    >>Also, is a transport agent able to access a mailbox and release emails from there, since if so we could use that mailbox approach I mentioned earlier rather than storing in a SQL db?

    A transport agent is part of the Message Transfer Process (eg the Message your processing is in the Transport Pipeline so Mailboxes have no context) you shouldn't be accessing a Mailbox within a Transport Agent. If you want to trigger an event when a Message arrives in a Mailbox look at EWS Notifications https://msdn.microsoft.com/en-us/library/office/dn458791(v=exchg.150).aspx . You can redirect a Message within a Transport Agent to a Mailbox if you don't want to store it in SQL. You'll then need to search and find the message in that Mailbox later using the InternetMessageId using EWS.

    For reliability sake you should keep your Transport Agent code as simple a possible for what you want to do you in the Transport Agent I would write the envelope headers (P1 Recps) to your own custom property in the message then redirect it to a Mailbox and just store Internet MessageId in your database. Then at the time you want to send the message another process can access that Mailbox use EWS and resend the message to the P1 recps you stored in the custom property in that way your still catering for BCC rcps).

    Cheers
    Glen

    Thursday, August 6, 2015 5:34 AM