2

EWS Managed API를 사용하여 CRM과 Exchange Server를 동기화합니다. EWS Mangage API 1.1을 사용하는 한 모든 것이 완벽하게 작동했습니다. 이제 Api 2.0 (Dll-version : 15.0.516.14)으로 업데이트했고 다른 폴더에서 동일한 폴더에 바인딩하고 이유를 이해하지 못하는 경우 ArgumentException이 발생합니다.ArgumentException on async Folder.Bind

private void TestAsyncFolderGet() 
    { 
     try 
     { 
      ExchangeService service = this.GetService(); 

      Parallel.For(0, 20, (i) => 
       { 
        Folder fo = Folder.Bind(service, WellKnownFolderName.Inbox); 
       }); 

     } 
     catch (Exception ex) 
     { 
      this.State = "Failed: " + ex.Message; 
     } 
    } 

    private ExchangeService GetService() 
    { 
     ExchangeService result = new ExchangeService(ExchangeVersion.Exchange2010); 

     result.AutodiscoverUrl("[email protected]"); 

     return result; 
    } 

내 실제 시나리오는 변경 비동기를 pullsubscription를 사용하여 처리 변경된 항목을 받고 그 메신저입니다 :

다음은 예외를 발생시키는에 SampleCode입니다. 이 작업을 수행하는 동안 일부 정보를 얻기 위해 부모 폴더에 바인딩됩니다.

예외를 피할 수있는 사람이 있습니까?

스택 추적 및 예외 정보를 정기적으로 :

System.ArgumentException은 : 동일한 키 가진 항목이 이미 추가되었습니다. Microsoft.Exchange.WebServices.Data.ExchangeService.FindFolders에서

System.Collections.Generic.Dictionary 2.Insert(TKey key, TValue value, Boolean add) at Microsoft.Exchange.WebServices.Data.ExchangeServiceBase.SaveHttpResponseHeaders(WebHeaderCollection headers) at Microsoft.Exchange.WebServices.Data.SimpleServiceRequestBase.ReadResponse(IEwsHttpWebResponse response) at Microsoft.Exchange.WebServices.Data.ExchangeService.InternalFindFolders(IEnumerable 1 parentFolderIds, SearchFilter searchFilter, FolderView보기 ServiceErrorHandling errorHandlingMode) 에서

(FolderId parentFolderId, FolderView보기)

+1

BTW : 불행히도 이것은 Exchange Webservices의'FindItems' 메소드에도 적용됩니다. –

답변

5

I Microsoft에 지원 센터를 만들었으며이 대답을 얻었습니다. ...

저는 Messaging Developer Support 팀에서이 사례에 대한 소유권을 얻었습니다. 포럼에서 설명 했으므로이 문제를 살펴 보았습니다. 샘플 코드를 기반으로하면 ExchangeService가 공용 정적 멤버 (http://msdn.microsoft.com/en-us/library/microsoft.exchange.webservices.data.exchangeservice(v=exchg.80).aspx 참조)를 제외하고 스레드로부터 안전하다는 보장이 없다는 간단한 대답이 있습니다.

이 문제를 방지하는 데 사용할 수있는 다양한 방법이 있습니다. 각 스레드마다 ExchangeService를 사용할 수는 있지만, 한 번에 많은 스레드가 실행되는 경우 권장하지 않을 수 있습니다 (각 서비스 인스턴스가 서버에서 새 세션을 초래할 수 있음). 폴더 개체에 대한 캐시를 구현할 수 있으므로 다른 스레드가 동일한 개체를 요청하면 캐시 개체는 이미 요청 된 경우이를 반환 할 수 있습니다. 이렇게하면 서버에 대한 요청이 줄어들어 성능이 향상됩니다.

EWS는 웹 응용 프로그램이므로주의 깊게 멀티 스레딩을 사용하고 작업자 스레드 수를 최소화해야합니다. 각 작업자 스레드가 Exchange 서버에 대한 요청을 생성하는 경우 Exchange의 응답을 기다리면서 하나의 작업자 스레드를 사용하는 것에 비해 성능 측면에서 많은 이득을 얻지 못할 수 있습니다.

그래서 제 경우의 솔루션은 "SafeExecuter"라는 클래스를 생성하여 사용자 당 Exchange에 대한 호출 만 동시에 이루어 지도록합니다. 또한 스로틀 링 폴리시가 초과되지 않도록주의해야합니다.