Я пытаюсь принудительно использовать IsoDateTimeConverter для определенного свойства.
Я регистрирую маршруты и Переговорный контент:
public class RouteMapper : IServiceRouteMapper
{
public void RegisterRoutes(IMapRoute mapRouteManager)
{
mapRouteManager.MapHttpRoute("SbApi", "default", "{controller}/{action}", new[] { "SbApi.Controllers" });
GlobalConfiguration.Configuration.Services.Replace(typeof(System.Net.Http.Formatting.IContentNegotiator), new JsonContentNegotiator());
}
}
public class JsonContentNegotiator : IContentNegotiator
{
public ContentNegotiationResult Negotiate(Type type, HttpRequestMessage request, IEnumerable<MediaTypeFormatter> formatters)
{
var formatter = new JsonMediaTypeFormatter();
formatter.UseDataContractJsonSerializer = false;
var isoDateConverter = formatter.SerializerSettings.Converters
.OfType<IsoDateTimeConverter>()
.FirstOrDefault();
if(isoDateConverter!=null){
formatter.SerializerSettings.Converters.Remove(isoDateConverter);
}
formatter.SerializerSettings.Converters.Add(new IsoDateTimeConverter() { DateTimeFormat = "dd-MM-yyyy" }); // custom date format, to see if the converter is used
var result = new ContentNegotiationResult(formatter, new MediaTypeHeaderValue("application/json"));
return result;
}
}
Атрибут, используемый для свойства:
[JsonConverter(typeof(IsoDateTimeConverter))]
public System.DateTime EndDate { get; set; }
Выходной сигнал сериализатора:
"EndDate":"2016-01-01T00:00:00"
Как я могу использовать IsoDateTimeConverter?
Редактировать:
Я использовал пользовательский IContentNetogiator для принудительного использования JSON над XML.
Я использовал пользовательский формат даты и времени, чтобы увидеть, действительно ли используется преобразование.
Я действительно нуждаюсь в формате ISO (с полным часовым поясом), но по какой-то причине я не могу обеспечить его исполнение. Я попытался настроить его в CustomDate, но безрезультатно.
public CustomDatetimeConverter()
{
base.DateTimeFormat = "yyyy'-'MM'-'dd'T'HH':'mm':'ss.FFFFFFFK"; // none of these work..
base.DateTimeFormat = "o";
base.Culture = System.Globalization.CultureInfo.InvariantCulture;
base.DateTimeStyles = System.Globalization.DateTimeStyles.AssumeLocal;
}
Редактировать 2: Во всяком случае, я получил его работу, вроде. Поскольку ничего не работало, и мне не нужна миллисекунда часть времени, я закончил использовать следующий формат: "yyyy" - "MM" - "dd'T'HH": 'mm': 'ss.000000zzz ". "Zzz" используется вместо "K", который по какой-то причине не работает.
Есть несколько способов решить эту проблему. Также не IContentNegotiator
замена IContentNegotiator
. Первый (и самый простой) способ заключается в создании подкласса IsoDateTimeConverter
с вашим пользовательским форматом даты:
class CustomDateTimeConverter : IsoDateTimeConverter
{
public CustomDateTimeConverter()
{
base.DateTimeFormat = "dd-MM-yyyy";
}
}
Затем измените [JsonConverter]
в свойстве EndDate
:
[JsonConverter(typeof(CustomDateTimeConverter))]
public System.DateTime EndDate { get; set; }
Другой способ сделать то же самое - создать пользовательский IContractResolver
который будет программно использовать IsoDateTimeConverter
для вашего целевого свойства. Ниже приведен код, который вам нужен для распознавателя. Замените Your_Class
именем класса, содержащего свойство EndDate
.
class CustomResolver : DefaultContractResolver
{
protected override IList<JsonProperty> CreateProperties(Type type,
Newtonsoft.Json.MemberSerialization memberSerialization)
{
IList<JsonProperty> props = base.CreateProperties(type, memberSerialization);
if (type == typeof(Your_Class))
{
JsonProperty prop =
props.Where(p => p.PropertyName == "EndDate")
.FirstOrDefault();
if (prop != null)
{
prop.Converter =
new IsoDateTimeConverter { DateTimeFormat = "dd-MM-yyyy" };
}
}
return props;
}
}
Чтобы установить этот преобразователь в свой проект, добавьте следующую строку в метод Register
вашего класса WebApiConfig
:
config.Formatters.JsonFormatter.SerializerSettings.ContractResolver =
new CustomResolver();