Веб-службы WCF, возвращающие строку ошибки / исключения

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

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

Например, вот мой красивый код C #, который запрашивает мойNorthwind базы данных, и возвращает списокCustomer имена.

Или скорее,это сделало бы, но я намеренно воткнул туда исключение.

public List<string> GetAllCustomerNames()
{
    //  Get a list of unique Customer names.
    //
    try 
    {
        throw new Exception("Oh heck, something went wrong !");

        NorthwindDataContext dc = new NorthwindDataContext();
        var results = (from cust in dc.Customers select cust.CompanyName).Distinct().OrderBy(s => s).ToList();

        return results;
    }           
    catch (Exception ex)
    {
        OutgoingWebResponseContext response = WebOperationContext.Current.OutgoingResponse;
        response.StatusCode = System.Net.HttpStatusCode.InternalServerError;
        response.StatusDescription = ex.Message;
        return null;
    }
}

В моем контроллере AngularJS я могу вызвать этот веб-сервис ...

$http.get('http://localhost:15021/Service1.svc/getAllCustomerNames')
    .then(function (data) {
        //  We successfully loaded the list of Customer names.
        $scope.ListOfCustomerNames = data.GetAllCustomerNamesResult;

    }, function (errorResponse) {

        //  The WCF Web Service returned an error

        var HTTPErrorNumber = errorResponse.status;
        var HTTPErrorStatusText = errorResponse.statusText;

        alert("An error occurred whilst fetching Customer Names\r\nHTTP status code: " + HTTPErrorNumber + "\r\nError: " + HTTPErrorStatusText);

    });

... и если возникает это исключение, я вижу полное сообщение об исключении ...

Замечательно.

Для всех читателей, которые хотели бы знать простой, общий способ возврата и отображения исключений из ваших веб-служб WCF, есть ваше решение!

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

Но .. если возникает исключение при подключении к базе данных (например, когда истекает время, у меня неверное имя базы данных в строке подключения и т. Д.), То следующая строка кодаделает бросить исключение ...

NorthwindDataContext dc = new NorthwindDataContext();

... мойcatch кодделает включите (я поставил точку останова для проверки), и мы установили для StatusDescription сообщение об исключении.

Но ответ, который отправляется обратно, не содержит ни моего номера статуса HTTP, ни текста.

Мой контроллер Angular просто получает HTTP-код состояния 0 без StatusMessage.

И если я нажму F12 в Chrome, вы увидите, что на самом деле это говорит веб-сервисне удалосьвместо возврата кода состояния 403, и сообщения нет.

Итак, мой вопрос просто, есть ли способ предотвратить этот сбой?

Очевидно, гораздо приятнее возвращать описание того, что пошло не так, а не просто «Веб-служба с треском провалилась ... но мы не можем сказать вам, почему».

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

Обновление, много часов спустя ..

Я нашел причину и решение.

Готовы ли вы к этому?

Проблема заключалась в том, что когдаDataContext линия выкинула исключение ...

NorthwindDataContext dc = new NorthwindDataContext();

... сообщение об исключении имелолиния подачи в этом.

Cannot open database "Northwind" requested by the login. 
The login failed.Login failed for user 'MikesWrongUserName'.This session has been assigned a tracing ID of '1f0513d1-9ce1-47ef-9d44-1f4546eb0b73'.  Provide this tracing ID to customer support when you need assistance.

Этот перевод строки был причиной проблемы. Если вы попытаетесь вернуть это вStatusDescription поле, это заставляет весь веб-сервис сообщаться как «сбой».

Таким образом, решение состоит в том, чтобы просто удалить все переводы строк, прежде чем вы вернете сообщение об исключении.

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

public List<string> GetAllCustomerNames()
{
    //  Get a list of unique Company Names.
    //
    try
    {
        NorthwindDataContext dc = new NorthwindDataContext();
        var results = (from cust in dc.Customers select cust.CompanyName).Distinct().OrderBy(s => s).ToList();

        return results;
    }
    catch (Exception ex)
    {
        OutgoingWebResponseContext response = WebOperationContext.Current.OutgoingResponse;
        response.StatusCode = System.Net.HttpStatusCode.InternalServerError;

        //  If a database Exception occurs, it might have a line-feed in it, 
        //  which will cause the web service to completely fail  (no Status
        //  Code or Status Message will get returned.)
        response.StatusDescription = ex.Message.Replace("\r\n", "");
        return null;
    }
}

Спасибо за все ваши предложения!

Ответы на вопрос(0)

Ваш ответ на вопрос