SMTP sink on win2003

  • Thread starter Thread starter Guest
  • Start date Start date
G

Guest

Hi,
I have a sink class which is registered on the server correctly. I know this
because in my class I put in some ex handling that writes to the event log
and I do get entries. Wat I want to do is get my class to see the content of
the message. Once I get this far I will be able to handle the rest. The COM
exception I am getting in event viewer is:
ExchangeSinks: Unable to cast COM object of type
'Microsoft.Exchange.Transport.EventInterop.MailMsgClass' to class type
'Microsoft.Exchange.Transport.EventWrappers.Message'. Instances of types that
represent COM components cannot be cast to types that do not represent COM
components; however they can be cast to interfaces as long as the underlying
COM component supports QueryInterface calls for the IID of the interface.

Class Code is:

Imports System

Imports System.Diagnostics

Imports System.Runtime.InteropServices

Imports Microsoft.Exchange.Transport.EventInterop

Imports Microsoft.Exchange.Transport.EventWrappers

Namespace SampleManagedSink



<Guid("xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx")> Public Class
ExchSinkClass

Implements IMailTransportSubmission, IEventIsCacheable

Public Sub IsCacheable() _

Implements IEventIsCacheable.IsCacheable

End Sub

Public Sub OnMessageSubmission(ByVal pIMailMsg As
Microsoft.Exchange.Transport.EventInterop.MailMsg, ByVal pINotify As
Microsoft.Exchange.Transport.EventInterop.IMailTransportNotify, ByVal
pvNotifyContext As System.IntPtr) _

Implements IMailTransportSubmission.OnMessageSubmission

Try

Dim buffer As Byte() = CopyContentToStream(pIMailMsg)

Dim oFileStream As System.IO.FileStream

Dim nw As DateTime = Now

oFileStream = New System.IO.FileStream("C:\Logs\" &
nw.ToShortTimeString & " email.txt", System.IO.FileMode.OpenOrCreate)

oFileStream.Write(buffer, 0, buffer.Length - 1)

oFileStream.Close()

Catch cex As COMException

Dim sSource As String = "Exchange Sink Library"

Dim sLog As String = "Application"

Dim sEvent As String = cex.Source & ": " & cex.Message

If (Not EventLog.SourceExists(sSource)) Then
EventLog.CreateEventSource(sSource, sLog)

EventLog.WriteEntry(sSource, sEvent)

Catch ex As Exception

Dim sSource As String = "Exchange Sink Library"

Dim sLog As String = "Application"

Dim sEvent As String = ex.Source & ": " & ex.Message

If (Not EventLog.SourceExists(sSource)) Then
EventLog.CreateEventSource(sSource, sLog)

EventLog.WriteEntry(sSource, sEvent)

End Try

End Sub



Function CopyContentToStream(ByVal msg As Message)

Dim buffer As Byte()

Dim Offset As Integer = 0

Try

Const BYTES_TO_READ As Integer = 2048

buffer = msg.ReadContent(Offset, BYTES_TO_READ)

Catch cex As COMException

Dim sSource As String = "Exchange Sink Library"

Dim sLog As String = "Application"

Dim sEvent As String = "In Function, " & cex.Source & ": " &
cex.Message

If (Not EventLog.SourceExists(sSource)) Then
EventLog.CreateEventSource(sSource, sLog)

EventLog.WriteEntry(sSource, sEvent)

Catch ex As Exception

Dim sSource As String = "Exchange Sink Library"

Dim sLog As String = "Application"

Dim sEvent As String = "In Function, " & ex.Source & ": " &
ex.Message

If (Not EventLog.SourceExists(sSource)) Then
EventLog.CreateEventSource(sSource, sLog)

EventLog.WriteEntry(sSource, sEvent)

End Try

If buffer.Length > 0 Then

Return buffer

Else

Return Nothing

End If

End Function

End Class

End Namespace


if I edit this code to simply create an entry in event log every time the
sink class is run, it does and I get no errors.

I don't know how to pass the same interface to my function. Please help.
 
Windows Server 2003 R2 Standard POP3/SMTP server role. No Exchange.
Right now I have a relay setup to another domain but I also have a POP3
account setup on the server. The end result of my project can involve the
SMTP relay or the SMTP storing the message locally, it doesn't matter to me
but from what I have gathered so far, this sink should fire on either one.
There is a SCO UNIX box on the local subnet (the only other system there)
that sends out alerts (email) to this server. The emails I will recieve need
to be processed and sent to other accounts based on the message content and
date/time received, which is why my class needs access to the message
content. Once my class can see the content, I can handle the message
processing code. No budget for 3rd party utilities so I must do this myself.
It is evident that I am passing a
Microsoft.Exchange.Transport.EventInterop.MailMsg object to my
copycontenttostream function and the function is treating as an object from
the Transport.EventWrappers namespace instead (ByVal msg As Message).
When I change the function parameter to byval msg as
Microsoft.Exchange.Transport.EventInterop.MailMsg the function now requires
more parameters be passed that I dont understand how to get, such as pINotify
pvNotifyContext, etc... If you can explain to me how I can provide all of the
required parameters (I will always want the whole text of the message), then
I can change my function to expect the correct interface and I won't get the
"cannot cast" COM exception and maybe my class will run as expected. .NET
documentation on this particular issue is non-existant and I have searched
google for 2 days straight.
Thanks
 
Hello,

Here is a sample of SMTP sink in .NET code, you may first take a look to
see if this can help:

How to write an OnArrival-type SMTP event sink in managed code by using
Visual Studio .NET 2003
http://support.microsoft.com/kb/894286

Hope this help,

Sincerely,

Luke Zhang

Microsoft Online Community Support
==================================================
Get notification to my posts through email? Please refer to
http://msdn.microsoft.com/subscriptions/managednewsgroups/default.aspx#notif
ications.

Note: The MSDN Managed Newsgroup support offering is for non-urgent issues
where an initial response from the community or a Microsoft Support
Engineer within 1 business day is acceptable. Please note that each follow
up response may take approximately 2 business days as the support
professional working with you may need further investigation to reach the
most efficient resolution. The offering is not appropriate for situations
that require urgent, real-time or phone-based interactions or complex
project analysis and dump analysis issues. Issues of this nature are best
handled working with a dedicated Microsoft Support Engineer by contacting
Microsoft Customer Support Services (CSS) at
http://msdn.microsoft.com/subscriptions/support/default.aspx.
==================================================

This posting is provided "AS IS" with no warranties, and confers no rights.
 
Hi Luke,
I know it has been a while..
This is one of the first documents I found before I posted this question and
does not tell me the answer I needed, which was regarding where to get the
values for the required parameters. Lack of response forced me to use
CDOSYS.dll instead.
Thanks
 
Hey Luke,
I just reread my post, I should have said circumstances forced me to use
dcdosys.dll, not lack of response. Sorry about that.
 
To all who need more information on writing managed event sinks (for IIS SMTP or Exchange), please take a look at my blog.
http://blog.rednael.com/

There is a very in depth article on How to write a custom authentication sink (using the AUTH command). It addresses various problems that are solved when writing event sinks.

For example, how do you read input lines after the AUTH command is processed.
And how do you use the property bags within a session.
And more...

Also, there is a list of registry settings for IIS SMTP (as well as Exchange 2000/2003), with which you can influence the behavior of the SMTP server.

Enjoy...
 
Back
Top