Безопасна ли среда WCF ClientBase?

Я использовал ClientBase для использования WCF для подключения к службе. Затем я вызываю метод на канале для связи с сервисом.

base.Channel.CalculateSomething();

Является ли этот поток потоков безопасным или я должен блокировать его при запуске нескольких потоков?

Спасибо

Ответ 1

Последующие комментарии к ответам здесь также меня не совсем поняли, поэтому я сделал еще несколько копаний. Вот несколько убедительных доказательств того, что ClientBase<T> является потокобезопасным - этот пост в блоге обсуждает, как заставить службу WCF правильно работать в присутствии одного клиентского прокси-сервера несколькими потоками одновременно (смелый акцент делается на оригинале):

... Однако существует сценарий, в котором установка ConcurrencyMode to Multiple в службе PerCall может увеличить пропускную способность вашей службы, если применяются следующие условия:

  • Клиент является многопоточным и выполняет вызовы вашей службы из нескольких потоков с использованием того же прокси-сервера.

  • Связывание между клиентом и службой привязка, имеющая сеанс (например, netTcpBinding, wsHttpBinding с надежным сеансом, netNamedPipeBinding и т.д.).

Кроме того, доказательства в этом сообщении, похоже, противоречат дополнительному замечанию Брайана о том, что WCF выполняет сериализацию любых многопоточных запросов. Сообщение показывает несколько запросов от одного клиента, работающего одновременно - , если ConcurrencyMode.Multiple и InstanceContextMode.PerCall.

Ниже приведено дополнительное обсуждение относительно последствий этого подхода, а также некоторых альтернатив.

Ответ 2

Да, это поточно-безопасный. Однако вы должны знать, что WCF автоматически сериализует выполнение CalculateSomething, когда он вызывается из более чем одного потока, используя тот же экземпляр ClientBase. Поэтому, если вы ожидали, что CalculateSomething будет выполняться одновременно, вам придется переосмыслить свой дизайн. Посмотрите этот ответ для одного подхода к созданию асинхронного API для метода CalculateSomething.

Ответ 3

Да, вызов метода на канале является потокобезопасным (с точки зрения клиента - перспектива обслуживания зависит от реализации сервиса). Вы можете вызвать этот метод из нескольких потоков параллельно. Даже автогенерирующий прокси предложит вам создавать методы для асинхронных вызовов.

Ответ 4

Кому это может быть интересно. Клиентская база 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:08
Задание 2: 15:47:10

Задание 1:15:47:18
Имя: Объект один "Привет"

Задание 2: 15:47:20
Имя: Объект один "Привет"