Hi
I have a utility class, called MailHandler, that I wrote to read and operate
on emails on an Exchange server using WebDAV. The WebDAV SQL statements are
sent using an HttpWebRequest object.
This worked fine in a .NET 1.1 project. I have copied the same Mailhandler
class into a .NET 2.0 project. This, too, worked fine when I initially
tested it, running as a Windows Forms app on my machine (running under my
network account). However, when I installed the app running as a Windows
service under the local system account, I got a Proxy Authentication Required
error (status 407). The .NET 1.1 project was also running as a Windows
service on the same machine, running under the same account. It was also
connecting to the same mailbox on the same Exchange server.
I've run an Ethereal trace on the outputs from the two projects. The .NET
1.1 project is communicating directly with the Exchange server. The .NET 2.0
project is communicating with the proxy server rather than the Exchange
server.
Obviously there has been some change in the HttpWebRequest class between
..NET 1.1 and .NET 2.0 that would cause the .NET 2.0 version to use the proxy
server where the .NET 1.1 version doesn't. Does anyone know what has
changed, and how I could bypass the proxy server in .NET 2.0?
Here is the relevant code from the MailHandler class. It returns an XML
document containing a list of all the emails in a specified folder in a
specified mailbox (I've left out everything after the HttpWebResponse is
returned):
public XmlDocument GetFolderEmails(string sFolder)
{
// Where _mailboxURI = "http://" + sMailServer + "/exchange/" + sMailbox.
// sMailServer is of the form <ExchangeServerName>@<CompanyName>.co.nz.
// sMailbox is the name of the mailbox, eg InwardsJobs.
// sFolder is the name of a mail folder within the mailbox, eg Inbox.
string sFolderURI = _mailboxURI;
string sQuery;
string sErrMsg;
HttpWebRequest Request;
HttpWebResponse Response = null;
byte[] bytes = null;
Stream RequestStream = null;
Stream ResponseStream = null;
int iStatusCode = 0;
XmlDocument ResponseXMLDoc = null;
try
{
sFolder = sFolder.Replace(" ", "%20");
if (!sFolderURI.EndsWith("/"))
{
sFolderURI += "/";
}
sFolderURI += sFolder;
sQuery = "<?xml version=\"1.0\"?><D:searchrequest xmlns:D = \"DAV:\" >"
+ "<D:sql>SELECT "
+ "\"urn:schemas:mailheader:message-id\", "
+ "\"urn:schemas:httpmail:subject\", "
+ "\"urn:schemas:httpmail:fromemail\", "
+ "\"urn:schemas:httpmail:fromname\", "
+ "\"urn:schemas:httpmail:date\", "
+ "\"urn:schemas:httpmail:datereceived\", "
+ "\"urn:schemas:httpmail:textdescription\" "
+ "FROM \"" + sFolderURI + "\" "
+ "WHERE \"DAV:ishidden\" = false "
+ "AND \"DAV:isfolder\" = false"
+ "</D:sql></D:searchrequest>";
Request = (HttpWebRequest)HttpWebRequest.Create(sFolderURI);
Request.Credentials = _mailCredentials;
Request.Method = "SEARCH";
// Write the SQL query to the request stream.
bytes = Encoding.UTF8.GetBytes(sQuery);
Request.ContentLength = bytes.Length;
RequestStream = Request.GetRequestStream();
RequestStream.Write(bytes, 0, bytes.Length);
RequestStream.Close();
Request.ContentType = "text/xml";
Response = (HttpWebResponse)Request.GetResponse();
iStatusCode = (int)Response.StatusCode;
<More code here to deal with returned XML document>
catch (Exception xcp)
{
<Exception handling code here>
}
finally
{
if (Response != null)
{
Response.Close();
}
}
return ResponseXMLDoc;
}
_mailCredentials is a CredentialCache object that is set as follows:
_mailCredentials = new CredentialCache();
_mailCredentials.Add( new System.Uri(_mailboxURI),
"NTLM",
new System.Net.NetworkCredential(sUser, sPwd, sDomain)
);
where sUser, sPwd and sDomain are username, password and domain required to
log into the mailbox, and _mailboxURI is the same as in the code above.
Cheers
Si