Подтвердить что ты не робот

Как установить Json.Net в качестве сериализатора по умолчанию для службы WCF REST

Можно ли переопределить поведение WCF DataContractSerializer по умолчанию, когда Serialize/DeSerialize сущности и вместо этого использовать JSON.NET?

У меня есть следующий контракт на обслуживание объекта City. По соображениям дизайна объект City имеет IsReference = true, поэтому по умолчанию DataContractSerializer вызывает ошибки.

Для методов "GET" я могу справиться с ситуацией с JsonConvert.DeserializeObject, но с методами "PUT, POST, DELETE" DataContractSerializer имеет приоритет и терпит неудачу, поскольку объекты IsReference не могут быть сериализованы.

Я нашел эту Post, чтобы реализовать IOperationBehavior и предоставить собственный Serializer, но я не знаю, как интегрировать Json.NET с этим. и я считаю, что для этого должен быть более прямой подход.

Id ценит любую помощь или рекомендации относительно этого сценария или советы другим подходам.

[ServiceContract]
[AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)
[ServiceBehavior(InstanceContextMode = InstanceContextMode.PerCall)]
public class CityService
{
    [Description("Get all Cities")]  
    [WebGet(UriTemplate = "")]
    public Message Cities()
    {

    }

    [Description("Allows the details of a single City to be updated.")]
    [WebInvoke(UriTemplate = "{code}", Method = "PUT")]
    public Message UpdateCity(string code, City city)
    {
    }
}

Большое спасибо

Хоссама

4b9b3361

Ответ 1

Использование расширенных кодеров и сериализаторов (см. http://msdn.microsoft.com/en-us/library/ms733092.aspx) или другие методы расширения WCF, такие как использование DataContractSerializerOperationBehavior, очень интересно, но для вашей особой проблемы есть более простые способы решения.

Если вы уже используете тип Message, чтобы возвращать результаты, используйте WCF4, вы можете сделать что-то вроде следующего:

public Message UpdateCity(string code, City city)
{
    MyResponseDataClass message = CreateMyResponse();
    // use JSON.NET to serialize the response data
    string myResponseBody = JsonConvert.Serialize(message);
    return WebOperationContext.Current.CreateTextResponse (myResponseBody,
                "application/json; charset=utf-8",
                Encoding.UTF8);
}

В случае ошибок (например, HttpStatusCode.Unauthorized или HttpStatusCode.Conflict) или в других ситуациях, когда вам нужно установить код состояния HTTP (например, HttpStatusCode.Created), вы можете продолжать использовать WebOperationContext.Current.OutgoingResponse.StatusCode.

В качестве альтернативы вы также можете вернуть Stream (см. http://blogs.msdn.com/b/carlosfigueira/archive/2008/04/17/wcf-raw-programming-model-web.aspx и http://msdn.microsoft.com/en-us/library/ms732038.aspx) вместо Message, чтобы возвращать любые данные без дополнительной обработки по умолчанию с помощью сериализатора Microsoft JSON. В случае WCF4 вы можете использовать CreateStreamResponse (см. http://msdn.microsoft.com/en-us/library/dd782273.aspx) вместо CreateTextResponse. Не забудьте установить позицию потока в 0 после записи в потоке, если вы будете использовать эту технику для получения ответа.

Ответ 2

Есть ли какая-то причина, по которой вы хотите использовать библиотеку Json.NET. Если вы хотите вернуть JSON, почему бы просто не использовать свойство ResponseFormat из атрибутов WebGet и WebInvoke?

[WebGet(UriTemplate = "", ResponseFormat = WebMessageFormat.Json)]

Это должно быть в большинстве случаев. Какую версию WCF вы используете? Любая причина, по которой вы возвращаете тип сообщения, а не фактический тип?