WebDAV Issues After Upgrade to Exchange 2003

Discussion in 'ASP .Net' started by George Durzi, Nov 6, 2004.

  1. George Durzi

    George Durzi Guest

    We recently upgraded to Exchange2K3/W2K3 from Exchange2K/W2K, and some of my
    c# code that I used to access users' contacts using WebDAV has stopped
    working. I'm getting a 401 unauthorized error. Hopefully, I can explain this
    adequately.

    Prior to the upgrade the following code was working properly.
    FYI: The site was running in the context of the domain administrator, and
    was also using the Administrator account to create a CredentialCache to
    access Exchange

    This function accepts my URI:
    http://myMailServer/exchange/userLogin/contacts/?Cmd=contents

    #region FetchContactsXml
    private string FetchContactsXml(string sSourceURL)
    {
    StringBuilder sbPayload = new StringBuilder();
    sbPayload.Append("<?xml version=\"1.0\"?>");
    sbPayload.Append("<a:searchrequest xmlns:a=\"DAV:\">");
    sbPayload.Append("<sql> SELECT \"urn:schemas:contacts:fileas\" ");
    sbPayload.Append(", \"urn:schemas:contacts:givenName\" ");
    sbPayload.Append(", \"urn:schemas:contacts:sn\" ");
    sbPayload.Append(", \"urn:schemas:contacts:eek:\" ");
    sbPayload.Append("FROM Scope('SHALLOW TRAVERSAL OF \"\"') ");
    sbPayload.Append("Where \"DAV:isfolder\" = false AND \"DAV:contentclass\"
    ");
    sbPayload.Append("= 'urn:content-classes:person'");
    sbPayload.Append(" ORDER BY \"urn:schemas:contacts:fileas\" ASC");
    sbPayload.Append("</>");
    sbPayload.Append("</>");

    // Array to hold Xml Payload
    byte[] arPayload = null;

    try
    {
    // Get Payload and Encode it to utf-8
    arPayload = Encoding.UTF8.GetBytes((string)sbPayload.ToString());

    // Create HTTP Web Request & Set Properties
    HttpWebRequest oWebRequest =
    (System.Net.HttpWebRequest)HttpWebRequest.Create(sSourceURL);
    oWebRequest.Method = "SEARCH";
    oWebRequest.ContentType = "text/xml";
    oWebRequest.ContentLength = arPayload.Length;

    // Inject the Search Payload into the RequestStream
    Stream oRequestStream = oWebRequest.GetRequestStream();
    oRequestStream.Write(arPayload, 0, arPayload.Length);
    oRequestStream.Close();

    // Set Credentials to Access Exchange Store
    oWebRequest.Credentials = CreateCredentialCache(sSourceURL);

    // Create the Web Response Object
    System.Net.WebResponse oWebResponse = (System.Net.WebResponse)
    oWebRequest.GetResponse();
    // Get the Xml Response Stream
    Stream oStream = oWebResponse.GetResponseStream();
    // utf-8 handle it
    Encoding oEncoding = System.Text.Encoding.GetEncoding("utf-8");
    StreamReader oStreamReader = new StreamReader(oStream, oEncoding);
    // Get the WebDAV Xml into a string
    string sXmlData = oStreamReader.ReadToEnd();

    // Clean Up
    oStreamReader.Close();
    oStream.Close();
    oWebResponse.Close();

    // Return the Xml string
    return sXmlData;
    }
    catch (Exception oException)
    {
    ExceptionManager.Publish(oException);
    throw(oException);
    }
    }
    #endregion

    #region CreateCredentialCache
    private CredentialCache CreateCredentialCache(string sSourceURL)
    {
    try
    {
    CredentialCache oCredentialCache = new CredentialCache();
    oCredentialCache.Add(
    new System.Uri(sSourceURL),
    "NTLM",
    new NetworkCredential(
    ConfigurationSettings.AppSettings["ExchangeAdminAccount"].ToString(),
    @ConfigurationSettings.AppSettings["ExchangeAdminAccountPwd"].ToString(),
    ConfigurationSettings.AppSettings["DomainName"].ToString()));

    return oCredentialCache;
    }
    catch (Exception oException)
    {
    ExceptionManager.Publish(oException);
    throw(oException);
    }
    }
    #endregion

    As I said, all of this worked perfectly before the upgrade. Now apparently
    Exchange 2003 doesn't allow the Administrator account to have permissions on
    all other account by default - which is a good thinkg since I shouldn't have
    been using that anyway. So our exchange admin created an account for me to
    use with the necessary permissions.

    I verified that the account he created can access a user's contacts folder
    by browsing to http://myMailServer/exchange/userLogin/contacts/?Cmd=contents
    and logging in as DOMAIN\account, password. I was able to open any user's
    contacts folder that I wanted to.


    Ok, so after the upgrade, the code breaks at the following spot:
    Stream oRequestStream = oWebRequest.GetRequestStream();

    I noticed that this is before I even attached the CredentialCache, so I
    tried moving that to above that point in code, but no change.

    The exact exception is:

    The remote server returned an error: (401) Unauthorized.


    When building the CredentialCache in the CreateCredentialCache function, I
    am using that new account I noted that our exchange admin created.

    Any help is appreciated.
    George Durzi, Nov 6, 2004
    #1
    1. Advertising

  2. And you're not running forms-based authentication or frontend/backend OWA or
    anything like that? See if the Exchange Explorer can access your folders
    since that's a WebDAV client as well.

    Tom

    --
    Looking for a good book on programming Exchange, Outlook, ADSI and
    SharePoint? Check out http://www.microsoft.com/MSPress/books/5517.asp



    "George Durzi" <> wrote in message
    news:...
    > We recently upgraded to Exchange2K3/W2K3 from Exchange2K/W2K, and some of
    > my c# code that I used to access users' contacts using WebDAV has stopped
    > working. I'm getting a 401 unauthorized error. Hopefully, I can explain
    > this adequately.
    >
    > Prior to the upgrade the following code was working properly.
    > FYI: The site was running in the context of the domain administrator, and
    > was also using the Administrator account to create a CredentialCache to
    > access Exchange
    >
    > This function accepts my URI:
    > http://myMailServer/exchange/userLogin/contacts/?Cmd=contents
    >
    > #region FetchContactsXml
    > private string FetchContactsXml(string sSourceURL)
    > {
    > StringBuilder sbPayload = new StringBuilder();
    > sbPayload.Append("<?xml version=\"1.0\"?>");
    > sbPayload.Append("<a:searchrequest xmlns:a=\"DAV:\">");
    > sbPayload.Append("<sql> SELECT \"urn:schemas:contacts:fileas\" ");
    > sbPayload.Append(", \"urn:schemas:contacts:givenName\" ");
    > sbPayload.Append(", \"urn:schemas:contacts:sn\" ");
    > sbPayload.Append(", \"urn:schemas:contacts:eek:\" ");
    > sbPayload.Append("FROM Scope('SHALLOW TRAVERSAL OF \"\"') ");
    > sbPayload.Append("Where \"DAV:isfolder\" = false AND
    > \"DAV:contentclass\" ");
    > sbPayload.Append("= 'urn:content-classes:person'");
    > sbPayload.Append(" ORDER BY \"urn:schemas:contacts:fileas\" ASC");
    > sbPayload.Append("</>");
    > sbPayload.Append("</>");
    >
    > // Array to hold Xml Payload
    > byte[] arPayload = null;
    >
    > try
    > {
    > // Get Payload and Encode it to utf-8
    > arPayload = Encoding.UTF8.GetBytes((string)sbPayload.ToString());
    >
    > // Create HTTP Web Request & Set Properties
    > HttpWebRequest oWebRequest =
    > (System.Net.HttpWebRequest)HttpWebRequest.Create(sSourceURL);
    > oWebRequest.Method = "SEARCH";
    > oWebRequest.ContentType = "text/xml";
    > oWebRequest.ContentLength = arPayload.Length;
    >
    > // Inject the Search Payload into the RequestStream
    > Stream oRequestStream = oWebRequest.GetRequestStream();
    > oRequestStream.Write(arPayload, 0, arPayload.Length);
    > oRequestStream.Close();
    >
    > // Set Credentials to Access Exchange Store
    > oWebRequest.Credentials = CreateCredentialCache(sSourceURL);
    >
    > // Create the Web Response Object
    > System.Net.WebResponse oWebResponse = (System.Net.WebResponse)
    > oWebRequest.GetResponse();
    > // Get the Xml Response Stream
    > Stream oStream = oWebResponse.GetResponseStream();
    > // utf-8 handle it
    > Encoding oEncoding = System.Text.Encoding.GetEncoding("utf-8");
    > StreamReader oStreamReader = new StreamReader(oStream, oEncoding);
    > // Get the WebDAV Xml into a string
    > string sXmlData = oStreamReader.ReadToEnd();
    >
    > // Clean Up
    > oStreamReader.Close();
    > oStream.Close();
    > oWebResponse.Close();
    >
    > // Return the Xml string
    > return sXmlData;
    > }
    > catch (Exception oException)
    > {
    > ExceptionManager.Publish(oException);
    > throw(oException);
    > }
    > }
    > #endregion
    >
    > #region CreateCredentialCache
    > private CredentialCache CreateCredentialCache(string sSourceURL)
    > {
    > try
    > {
    > CredentialCache oCredentialCache = new CredentialCache();
    > oCredentialCache.Add(
    > new System.Uri(sSourceURL),
    > "NTLM",
    > new NetworkCredential(
    > ConfigurationSettings.AppSettings["ExchangeAdminAccount"].ToString(),
    >
    > @ConfigurationSettings.AppSettings["ExchangeAdminAccountPwd"].ToString(),
    > ConfigurationSettings.AppSettings["DomainName"].ToString()));
    >
    > return oCredentialCache;
    > }
    > catch (Exception oException)
    > {
    > ExceptionManager.Publish(oException);
    > throw(oException);
    > }
    > }
    > #endregion
    >
    > As I said, all of this worked perfectly before the upgrade. Now apparently
    > Exchange 2003 doesn't allow the Administrator account to have permissions
    > on all other account by default - which is a good thinkg since I shouldn't
    > have been using that anyway. So our exchange admin created an account for
    > me to use with the necessary permissions.
    >
    > I verified that the account he created can access a user's contacts folder
    > by browsing to
    > http://myMailServer/exchange/userLogin/contacts/?Cmd=contents and logging
    > in as DOMAIN\account, password. I was able to open any user's contacts
    > folder that I wanted to.
    >
    >
    > Ok, so after the upgrade, the code breaks at the following spot:
    > Stream oRequestStream = oWebRequest.GetRequestStream();
    >
    > I noticed that this is before I even attached the CredentialCache, so I
    > tried moving that to above that point in code, but no change.
    >
    > The exact exception is:
    >
    > The remote server returned an error: (401) Unauthorized.
    >
    >
    > When building the CredentialCache in the CreateCredentialCache function, I
    > am using that new account I noted that our exchange admin created.
    >
    > Any help is appreciated.
    >
    >
    Tom Rizzo [MSFT], Nov 13, 2004
    #2
    1. Advertising

  3. George Durzi

    George Durzi Guest

    Tom,
    Sorry, I'm not too experienced with administering Exchange. Is the Exchange
    Explorer when you actually browse in IE to
    http:\\exchserver\exchange\login\Inbox, etc..?

    If so, yes it works

    "Tom Rizzo [MSFT]" <> wrote in message
    news:...
    > And you're not running forms-based authentication or frontend/backend OWA
    > or anything like that? See if the Exchange Explorer can access your
    > folders since that's a WebDAV client as well.
    >
    > Tom
    >
    > --
    > Looking for a good book on programming Exchange, Outlook, ADSI and
    > SharePoint? Check out http://www.microsoft.com/MSPress/books/5517.asp
    >
    >
    >
    > "George Durzi" <> wrote in message
    > news:...
    >> We recently upgraded to Exchange2K3/W2K3 from Exchange2K/W2K, and some of
    >> my c# code that I used to access users' contacts using WebDAV has stopped
    >> working. I'm getting a 401 unauthorized error. Hopefully, I can explain
    >> this adequately.
    >>
    >> Prior to the upgrade the following code was working properly.
    >> FYI: The site was running in the context of the domain administrator, and
    >> was also using the Administrator account to create a CredentialCache to
    >> access Exchange
    >>
    >> This function accepts my URI:
    >> http://myMailServer/exchange/userLogin/contacts/?Cmd=contents
    >>
    >> #region FetchContactsXml
    >> private string FetchContactsXml(string sSourceURL)
    >> {
    >> StringBuilder sbPayload = new StringBuilder();
    >> sbPayload.Append("<?xml version=\"1.0\"?>");
    >> sbPayload.Append("<a:searchrequest xmlns:a=\"DAV:\">");
    >> sbPayload.Append("<sql> SELECT \"urn:schemas:contacts:fileas\" ");
    >> sbPayload.Append(", \"urn:schemas:contacts:givenName\" ");
    >> sbPayload.Append(", \"urn:schemas:contacts:sn\" ");
    >> sbPayload.Append(", \"urn:schemas:contacts:eek:\" ");
    >> sbPayload.Append("FROM Scope('SHALLOW TRAVERSAL OF \"\"') ");
    >> sbPayload.Append("Where \"DAV:isfolder\" = false AND
    >> \"DAV:contentclass\" ");
    >> sbPayload.Append("= 'urn:content-classes:person'");
    >> sbPayload.Append(" ORDER BY \"urn:schemas:contacts:fileas\" ASC");
    >> sbPayload.Append("</>");
    >> sbPayload.Append("</>");
    >>
    >> // Array to hold Xml Payload
    >> byte[] arPayload = null;
    >>
    >> try
    >> {
    >> // Get Payload and Encode it to utf-8
    >> arPayload = Encoding.UTF8.GetBytes((string)sbPayload.ToString());
    >>
    >> // Create HTTP Web Request & Set Properties
    >> HttpWebRequest oWebRequest =
    >> (System.Net.HttpWebRequest)HttpWebRequest.Create(sSourceURL);
    >> oWebRequest.Method = "SEARCH";
    >> oWebRequest.ContentType = "text/xml";
    >> oWebRequest.ContentLength = arPayload.Length;
    >>
    >> // Inject the Search Payload into the RequestStream
    >> Stream oRequestStream = oWebRequest.GetRequestStream();
    >> oRequestStream.Write(arPayload, 0, arPayload.Length);
    >> oRequestStream.Close();
    >>
    >> // Set Credentials to Access Exchange Store
    >> oWebRequest.Credentials = CreateCredentialCache(sSourceURL);
    >>
    >> // Create the Web Response Object
    >> System.Net.WebResponse oWebResponse = (System.Net.WebResponse)
    >> oWebRequest.GetResponse();
    >> // Get the Xml Response Stream
    >> Stream oStream = oWebResponse.GetResponseStream();
    >> // utf-8 handle it
    >> Encoding oEncoding = System.Text.Encoding.GetEncoding("utf-8");
    >> StreamReader oStreamReader = new StreamReader(oStream, oEncoding);
    >> // Get the WebDAV Xml into a string
    >> string sXmlData = oStreamReader.ReadToEnd();
    >>
    >> // Clean Up
    >> oStreamReader.Close();
    >> oStream.Close();
    >> oWebResponse.Close();
    >>
    >> // Return the Xml string
    >> return sXmlData;
    >> }
    >> catch (Exception oException)
    >> {
    >> ExceptionManager.Publish(oException);
    >> throw(oException);
    >> }
    >> }
    >> #endregion
    >>
    >> #region CreateCredentialCache
    >> private CredentialCache CreateCredentialCache(string sSourceURL)
    >> {
    >> try
    >> {
    >> CredentialCache oCredentialCache = new CredentialCache();
    >> oCredentialCache.Add(
    >> new System.Uri(sSourceURL),
    >> "NTLM",
    >> new NetworkCredential(
    >> ConfigurationSettings.AppSettings["ExchangeAdminAccount"].ToString(),
    >>
    >> @ConfigurationSettings.AppSettings["ExchangeAdminAccountPwd"].ToString(),
    >> ConfigurationSettings.AppSettings["DomainName"].ToString()));
    >>
    >> return oCredentialCache;
    >> }
    >> catch (Exception oException)
    >> {
    >> ExceptionManager.Publish(oException);
    >> throw(oException);
    >> }
    >> }
    >> #endregion
    >>
    >> As I said, all of this worked perfectly before the upgrade. Now
    >> apparently Exchange 2003 doesn't allow the Administrator account to have
    >> permissions on all other account by default - which is a good thinkg
    >> since I shouldn't have been using that anyway. So our exchange admin
    >> created an account for me to use with the necessary permissions.
    >>
    >> I verified that the account he created can access a user's contacts
    >> folder by browsing to
    >> http://myMailServer/exchange/userLogin/contacts/?Cmd=contents and logging
    >> in as DOMAIN\account, password. I was able to open any user's contacts
    >> folder that I wanted to.
    >>
    >>
    >> Ok, so after the upgrade, the code breaks at the following spot:
    >> Stream oRequestStream = oWebRequest.GetRequestStream();
    >>
    >> I noticed that this is before I even attached the CredentialCache, so I
    >> tried moving that to above that point in code, but no change.
    >>
    >> The exact exception is:
    >>
    >> The remote server returned an error: (401) Unauthorized.
    >>
    >>
    >> When building the CredentialCache in the CreateCredentialCache function,
    >> I am using that new account I noted that our exchange admin created.
    >>
    >> Any help is appreciated.
    >>
    >>

    >
    >
    George Durzi, Nov 15, 2004
    #3
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. =?Utf-8?B?bWFyaWEucw==?=

    Exchange WebDAV - PUT Request - 501 not implemented

    =?Utf-8?B?bWFyaWEucw==?=, Aug 31, 2005, in forum: ASP .Net
    Replies:
    3
    Views:
    6,835
    =?Utf-8?B?bWFyaWEucw==?=
    Sep 1, 2005
  2. KovaiRam
    Replies:
    1
    Views:
    1,264
    KovaiRam
    Feb 1, 2005
  3. Bernhard Weitlaner
    Replies:
    11
    Views:
    13,869
    NemanjaB
    Dec 15, 2010
  4. funnycoder
    Replies:
    0
    Views:
    437
    funnycoder
    Jul 25, 2006
  5. Michael Dichtl

    WebDAV: Connect Ruby to a WebDAV Server

    Michael Dichtl, Jul 9, 2007, in forum: Ruby
    Replies:
    7
    Views:
    878
    Rob Biedenharn
    Jul 9, 2007
Loading...

Share This Page