Reputation: 47375
Thank goodness for R#7. Without their new "go to decompiled sources" feature, I would be at a loss for how to describe this issue.
I have had a certain SmtpMailSender implementation class for a while now. Here are a couple of things it does:
1.) It does not send network mail in development mode. The development web.config looks like this:
<smtp deliveryMethod="SpecifiedPickupDirectory">
<specifiedPickupDirectory pickupDirectoryLocation="App_Data/mail" />
</smtp>
<!--<smtp deliveryMethod="Network">
<network host="smtp.roadrunner.com" />
</smtp>-->
The mail sending class sniffs the SmtpClient.DeliverMethod
property, and configures the real runtime path of the SmtpClient.PickupDirectoryLocation
(to something like "C:\path\to\project\App_Data\mail"
).
2.) It wraps all of the sending code into a using statement and a try block:
...
try
{
using (var smtpClient = new SmtpClient())
{
// detect pickup directory
// do other encapsulated behaviors
smtpClient.Send(message);
}
}
catch (Exception ex)
{
_exceptionLogger.LogException(ex);
if (++retryCount > 2) throw;
Thread.Sleep(3000);
Send(message, retryCount); // recursive to same method
}
This has all been working great on my main workstation since last year. I downloaded the project onto my laptop though, and kept seeing that every SmtpClient.Send(MailMessage)
was causing the following exception:
InvalidOperationException: "The SMTP host was not specified."
at System.Net.Mail.SmtpClient.CheckHostAndPort()
at System.Net.Mail.SmtpClient.get_ServicePoint()
at System.Net.Mail.SmtpClient.Dispose(Boolean disposing)
at System.Net.Mail.SmtpClient.Dispose()
at My.ImplementationOf.SmtpMailSender.Send(MailMessage message, Int32 retryCount)
The exception was being thrown from SmtpClient.CheckHostAndPort
, which throws either when the SmtpClient.Host
property is null or zero length according to the R# decompilation on my laptop. I went back to my workstation and found that even though the smtpClient.Host
property was null, this exception was not being thrown.
Then I used R#'s little decompile feature for System.Net.Mail.SmtpClient
on the workstation and found that there are 2 different implementations of this class! Very strange, because the reference to System.dll is pointing at C:\Windows\Microsoft.NET\Framework\v4.0.30319\System.dll
on both machines! Basically they are the same, with one important difference:
protected virtual void Dispose(bool disposing)
{
// the workstation decompilation shows this:
if (this.transport != null && this.servicePoint != null)
this.transport.CloseIdleConnections(this.servicePoint);
// but the laptop decompilation shows this:
if (transport != null)
transport.CloseIdleConnections(ServicePoint);
}
HOW CAN THERE BE TWO DIFFERENT IMPLEMENTATIONS OF THIS?
Updates
Both machines are showing Windows 7 Professional Service Pack 1. I ran Windows Update on both and both are telling me the computer is up to date. The only difference I can think of is that the laptop's Windows 7 has not yet been activated, I just installed it 3 days ago. I wonder, could activation of the OS change the framework's System.dll?
I then took these steps:
Upvotes: 3
Views: 1916
Reputation: 1234
Probably because one machine has .NET 4.5 and the other does not. Have you installed VS2012 onto your main workstation?
This bug was fixed in .NET 4.5:
And installing .NET 4.5 overwrites new DLLs on top of your existing .NET 4.0 dlls:
http://www.west-wind.com/weblog/posts/2012/Mar/13/NET-45-is-an-inplace-replacement-for-NET-40
Upvotes: 1
Reputation: 1501926
IIRC, service packs to the framework don't bump the assembly versions. I could be wrong, but the first thing I'd check is the service pack level of each machine.
Of course, there are hotfixes which wouldn't show as clearly as service packs...
Upvotes: 0