Почему веб-служба WCF, размещенная в IIS, случайно перестает отвечать? - PullRequest
1 голос
/ 09 октября 2009

Это моя первая попытка использовать WCF, поэтому в этом подходе может быть что-то принципиально неправильное - если да, я с удовольствием переключусь на другую модель. На первый взгляд, я подумал, что ответ на этот вопрос сработает, но мой сценарий выглядит иначе.

У меня есть веб-сайт ASP.NET MVC, где контроллеры получают доступ к клиентскому классу WCF через промежуточный репозиторий. Хранилище - это просто оболочка для клиента WCF, которая создает его один раз и устанавливает правильный адрес конечной точки.

public class WcfRepository : IRepository
{
    private MyWCFServiceClient client;

    public WcfRepository()
    {
        client = new MyWCFServiceClient();
    }

    public bool MyMethod1()
    {
         return client.MyMethod1();
    }

    ... etc       
}

Я могу получить доступ к разным страницам на сайте, пока не произойдет, казалось бы, случайная точка, когда служба WCF начнет отсчет времени. Неважно, какой метод я вызываю - это время ожидания для разных. Я также не вижу никаких исключений на компьютере IIS, на котором размещена служба WCF; журнал событий там пуст. Простой метод, такой как GetCustomerByName(), который работал двумя минутами раньше, больше не будет, поэтому я думаю, что это больше связано с коммуникацией WCF, а не с самой службой.

Если я попытаюсь использовать тестовый клиент WCF после наступления одного из этих таймаутов, он также не будет выполнен. Но если я подожду некоторое время (и выберу «запустить новый прокси»), все снова будет работать.

Я очень запутался - должен ли я создавать новый экземпляр клиента WCF каждый раз, когда я хочу использовать его в своем хранилище? Есть ли другой способ, которым я должен использовать клиент? Перенос каждого вызова в Open()/Close() также не работает, так как первый вызов Close() переводит объект в состояние удаления.

1 Ответ

2 голосов
/ 09 октября 2009

Когда вы закончите с вашим клиентом WCF, вы должны явно закрыть его, потому что в противном случае он будет сохранять «соединение» открытым для сервиса, и существует (настраиваемое) ограничение на количество одновременных соединений, которые вы можете иметь.

Хотя это ограничение можно изменить, правильное решение - создать новый клиент WCF, вызвать один или несколько методов и закрыть его снова, когда вы закончите. Это считается наилучшей практикой, и следует аккуратно избегать проблем, с которыми вы сталкиваетесь в настоящее время.

Это означает, что ваша реализация должна идти примерно так:

public class WcfRepository : IRepository
{
    public bool MyMethod1()
    {
         var client = new MyWCFServiceClient();
         try
         {
             return client.MyMethod1();
         }
         finally
         {
             try
             {
                 client.Close();
             }
             catch(CommunicationException)
             {
                 // handle exception here
             }
             catch(TimeoutException)
             {
                 // handle exception here
             }

         }
    }

    ... etc       
}

Обратите внимание на неприятную конструкцию try / finally, которая необходима, потому что Close может бросить. Подробнее об этом здесь .

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...