Alexander
Alexander

Reputation: 20224

Finding the Public Folder for a certain mail address

In one public folder mailbox, I have two mail-enabled folders.

Now when selecting all the Active Directory entries for GAL, there are some entries:

So, naturally I would call EWS autodiscover for these email addresses. This works fine for all users, but not for public folders - it says it can't find a mailbox for that email address. So I got from Active Directory the email address of the mailbox and connected to that.

But how can I now traverse to the corresponding folder? I tried:

FolderView view = new FolderView(1);
view.Traversal = FolderTraversal.Shallow;
var folders = ews.FindFolders(
        WellKnownFolderName.Root, 
        new SearchFilter.IsEqualTo(
            FolderSchema.DisplayName, // <- how can I search by the folder's email address?
            displayName
        ), view);

This throws the following, really useful error message:

Internal Server Error. The operation failed.

For sake of completeness, the following EWS XML is created:

<Trace Tag="EwsRequest" Tid="121" Time="2016-03-23 13:31:41Z" Version="15.00.0913.015">
  <?xml version="1.0" encoding="utf-8"?>
  <soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:m="http://schemas.microsoft.com/exchange/services/2006/messages" xmlns:t="http://schemas.microsoft.com/exchange/services/2006/types" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
    <soap:Header>
      <t:RequestServerVersion Version="Exchange2013" />
      <t:ExchangeImpersonation>
        <t:ConnectingSID>
          <t:SmtpAddress>[email protected]</t:SmtpAddress>
        </t:ConnectingSID>
      </t:ExchangeImpersonation>
    </soap:Header>
    <soap:Body>
      <m:FindFolder Traversal="Shallow">
        <m:FolderShape>
          <t:BaseShape>AllProperties</t:BaseShape>
        </m:FolderShape>
        <m:IndexedPageFolderView MaxEntriesReturned="1" Offset="0" BasePoint="Beginning" />
        <m:Restriction>
          <t:IsEqualTo>
            <t:FieldURI FieldURI="folder:DisplayName" />
            <t:FieldURIOrConstant>
              <t:Constant Value="Test Public Folder Mailbox" />
            </t:FieldURIOrConstant>
          </t:IsEqualTo>
        </m:Restriction>
        <m:ParentFolderIds>
          <t:DistinguishedFolderId Id="root" />
        </m:ParentFolderIds>
      </m:FindFolder>
    </soap:Body>
  </soap:Envelope>
</Trace>

and the following response by the server:

<Trace Tag="EwsResponse" Tid="121" Time="2016-03-23 13:31:41Z" Version="15.00.0913.015">
  <?xml version="1.0" encoding="utf-8"?>
  <s:Envelope xmlns:s="http://schemas.xmlsoap.org/soap/envelope/">
    <s:Body>
      <s:Fault>
        <faultcode xmlns:a="http://schemas.microsoft.com/exchange/services/2006/types">a:ErrorInternalServerError</faultcode>
        <faultstring xml:lang="de-DE">Interner Serverfehler. Fehler bei diesem Vorgang.</faultstring>
        <detail>
          <e:ResponseCode xmlns:e="http://schemas.microsoft.com/exchange/services/2006/errors">ErrorInternalServerError</e:ResponseCode>
          <e:Message xmlns:e="http://schemas.microsoft.com/exchange/services/2006/errors">Interner Serverfehler. Fehler bei diesem Vorgang.</e:Message>
        </detail>
      </s:Fault>
    </s:Body>
  </s:Envelope>
</Trace>

What could cause that issue or where can I find additional information as to why this issue occurs?

Upvotes: 0

Views: 1241

Answers (2)

Alexander
Alexander

Reputation: 20224

For those who are searching, some C# Code to bind to a certain public folder:

AlternatePublicFolderId hexId = new AlternatePublicFolderId(IdFormat.HexEntryId, directoryEntry.msExchPublicFolderEntryId);
AlternatePublicFolderId ewsId = service.ConvertId(hexId, IdFormat.EwsId) as AlternatePublicFolderId;
calendar = CalendarFolder.Bind(service, new FolderId(ewsId.FolderId));

Upvotes: 0

Glen Scales
Glen Scales

Reputation: 22032

A few things are wrong here first you can't use EWS or any of the Mailbox Access API's to open the Public Folder Mailboxes directly you should access the Public Folders via the correct API endpoint eg DistinguishedFolderIdNameType.publicfoldersroot also your trying to impersonate the Public Folder Mailbox eg

    <t:ConnectingSID>
      <t:SmtpAddress>[email protected]</t:SmtpAddress>
    </t:ConnectingSID>

You can't do this you can only impersonate a Valid user, in the case of accessing the Public Folder Tree you should use a user that has rights to the Public Folder you wish to access. The only thing you should be doing with the PublicFolder Mailbox SMTP is to set routing headers to ensure your request are routed correctly see https://msdn.microsoft.com/en-us/library/office/dn818490(v=exchg.150).aspx

To find a Public folder connect as a user and the search the Public Folder tree and all it's children, you can't use a Deep traversal with the Public Folder Tree so you will need to make separate Shallow traversal requests for each Child folder level. I have EWS Power shell library that does this and bunch of things like enumerate MailEnabled folders etc which maybe useful https://github.com/gscales/Powershell-Scripts/blob/master/PublicFolderMod.ps1

If you have Exchange 2013 you can use the Exchange management Shell Get-MailPublicFolder cmdlet to get the HexEntryId of the Folder then use ConvertId to convert it to a EWSid and bind to the folder directly.

Cheers Glen

Upvotes: 1

Related Questions