2011-01-07 5 views
26

WCF를 사용하여 서비스에 연결하기 위해 ClientBase를 구현했습니다. 그런 다음 채널에서 서비스와 통신 할 수있는 메소드를 호출합니다.WCF ClientBase 스레드가 안전합니까?

base.Channel.CalculateSomething(); 

이 호출 스레드는 안전합니까? 아니면 다중 스레드를 실행할 때 잠그지 않아야합니까? 채널의 메소드를 호출

감사

답변

3

예는 스레드로부터 안전하다 (클라이언트의 관점에서 - 서비스 관점은 서비스 구현에 따라 다름). 병렬로 여러 스레드에서이 메서드를 호출 할 수 있습니다. 자동 생성 프록시조차도 비동기 호출을위한 메소드를 생성 할 수 있습니다.

+1

는 무엇인가 스레드로부터 안전하다고 말하는 당신의 증거 또는 이유? 나는 [MSDN의 ClientBase 클래스] (http://msdn.microsoft.com/en-us/library/ms576141%28v=vs.110%29.aspx)가 끝났기 때문에 요청하고있다. thread-safe. – ChrisW

+0

@ChrisW : 아마도 'ClientBase'의 속성에 액세스하는 것은 스레드로부터 안전하지 않지만 서비스에 대한 호출은 (또는 문서에서 버그 일 수 있습니다. 우선 클라이언트 기반없이 전화를 걸 수 있습니다. 단 하나의 채널 만 있으면됩니다. 나는 어떤 증거도 가지고 있지 않다. 원격 서비스를 호출하면 전역 공유 데이터를 저장할 필요가 없다고 생각합니다. 그렇지 않으면 WCF의 전체 클라이언트 측이 잘못 설계 될 것입니다. –

+0

내부 '채널'은 스레드로부터 안전합니까? 나는 채널이 몇몇 메모리 버퍼와 네트워크 소켓을 소유하고 있다고 상상한다. 동시 사용자 (예 : 요청 순서 지정)를 지원하도록 명시 적으로 설계되지 않은 한 두 사람이 동시에 메모리와 소켓에 쓰려고하면 심각한 결과를 초래할 수 있습니다. – ChrisW

10

예, 그것은 스레드 안전합니다. 그러나 동일한 ClientBase 인스턴스를 사용하는 둘 이상의 스레드에서 호출 될 때 WCF가 CalculateSomething의 실행을 자동으로 직렬화한다는 것을 알아야합니다. 따라서 CalculateSomething이 동시에 실행되기를 원한다면 디자인을 재고해야합니다. CalculateSomething 메서드에 대한 비동기 API를 만드는 한 가지 방법은 this answer을 참조하십시오. 답변에

+2

당신이 의미하는 바를 설명해 주시겠습니까? "그러나 동일한 ClientBase 인스턴스를 사용하는 둘 이상의 스레드에서 호출 될 때 WCF가 CalculateSomething의 실행을 자동으로 직렬화한다는 것을 알아야합니다." 감사! – Erick

+4

WCF는 순차적 인 방식으로 호출을 수행하고 동시에 호출하지는 않는다는 것을 의미합니다 (프로그래밍 방식의 관점에서 볼 때). –

+1

스레드로부터 안전하다고 말하는 증거 나 이유는 무엇입니까? 그리고 CalculateSomething이 자동으로 serialize됨을 어떻게 알 수 있습니까? 즉, 클라이언트 측 ClientBase 인스턴스 또는 서버/구현 측에서 serialize됩니까? 나는 [MSDN의 ClientBase 클래스] (http://msdn.microsoft.com/en-us/library/ms576141%28v=vs.110%29.aspx)가 끝났기 때문에 요청하고있다. thread-safe. – ChrisW

14

추시 의견은 여기뿐만 아니라 저를 확신했다, 그래서 나는 좀 더 파고했다. ClientBase<T>이 스레드로부터 안전하다는 확실한 증거가 있습니다. this blog post이있는 상태에서 WCF 서비스를 올바르게 수행하는 방법에 대해 설명합니다. (이중 강조는 원본에 있음) :

... 그러나, 다음과 같은 조건이 적용되는 경우 서비스 처리량을 증가시킬 수 PerCall 서비스에 다중를 들면, ConcurrencyMode를 설정하는 시나리오가 :

  1. 클라이언트는 멀티 스레드 및 귀하의 서비스에 복수의 스레드 에서 같은 프록시을 사용하여 전화를 걸고 있습니다.

  2. 하면 다음은 클라이언트와 서비스 간의 바인딩 것은 세션 가지고있는 바인딩 (예 netTcpBinding, 신뢰성있는 wsHttpBinding 세션, netNamedPipeBinding 등/w).

또한,이 게시물의 증거는 WCF 어떤 멀티 스레드 요청을 직렬화 브라이언의 추가 발언을 반박 것으로 보인다.ConcurrencyMode.MultipleInstanceContextMode.PerCall를 사용하는 경우 - 게시물은 동시에 를 실행하는 하나의 클라이언트에서 여러 요청을 보여줍니다.

이 방법의 성능에 미치는 영향뿐만 아니라 몇 가지 대안에 대한 몇 가지 추가 논의 here 있습니다. 누구에게 관심이 있습니다

+1

_ 채널에 의해 생성 된 채널과 클라이언트는 스레드로부터 안전하지만, 둘 이상의 메시지를 동시에 전선에 쓰는 것을 지원하지 않을 수 있습니다 ._ 출처 : [MS docs] (https://docs.microsoft.com). –

0

. WCF 클라이언트 기반은 적어도이 구성에서 스레드로부터 안전 할 수 있습니다. 다른 구성을 시도하지 않았습니다.

[ServiceContract(SessionMode = SessionMode.Required, CallbackContract = typeof(IWcfCallbacksContract), Namespace = "http://wcf.applicatin.srv/namespace")] 
public interface IWcfContract 
{ 
    [OperationContract] 
    CompositeReturnObject GetServerObject(); 
} 

서비스 :

public CompositeReturnObject GetServerObject() 
{ 
    CompositeReturnObject ret = new CompositeReturnObject("Hello"); 
    Thread.Sleep(10000); // Simulating long call 
    return ret; 
} 

클라이언트 :

private void GetData_Click(object sender, RoutedEventArgs e) 
{ 
    Console.WriteLine("Task 1 start: " + DateTime.Now.ToString("HH:mm:ss")); 

    Task.Factory.StartNew(() => { 
     var res = _proxy.GetServerObject(); 
     Console.WriteLine("Task 1 finish: " + DateTime.Now.ToString("HH:mm:s")); 
     Console.WriteLine(res.ToString()); 
     return; 
    } 
    ); 

    Thread.Sleep(2000); 

    Console.WriteLine("Task 2 start: " + DateTime.Now.ToString("HH:mm:ss")); 

    Task.Factory.StartNew(() => { 
     var res = _proxy.GetServerObject(); 
     Console.WriteLine("Task 2 finish: " + DateTime.Now.ToString("HH:mm:s")); 
     Console.WriteLine(res.ToString()); 
     return; 
    } 
    ); 
} 

그리고 결과 :

작업 1 시작 : 15시 47분 8초
작업이 시작 : 15 : 47 : 10

작업 1 마무리 : 15시 47분 18초
이름 : 개체는 하나 "안녕하세요"

작업이 마무리 : 15시 47분 20초
이름 : "안녕하세요"한 개체는

+0

이것은 호출이 직렬화되지 않았 음을 나타냅니다. com/ko-ko/dotnet/framework/wcf/feature-details/middle-tier-client-applications? view = netframework- 클라이언트가 스레드로부터 안전하다는 것을 증명할 수는 없습니다. 우연의 일치 일 수 있습니다. –

관련 문제