执行此操作的简单方法如下:
- 实现一个具有 DateTime 属性的类,您将在其中反序列化 DateTime 值,例如
DateTimeWrapper
- 将路由参数定义为此类,而不是
DateTime
- 创建一个类型转换器,它可以通过继承
TypeConverter 将url 段字符串转换为DateTimeWrapper 类。你可以叫它DateTimeWrapperConverter
- 用类似
[TypeConverter(typeof(DateTimeWrapperConverter))] 的属性装饰你的DateTimeWrapper 类
完成此操作后,当您收到请求时,DateTimeWrapper 类的任何路由参数都将由您的转换器处理。然后,您只需阅读由您的自定义转换器创建的DateTimeWrapper 的DateTime 属性。
这样可以避免修改DateTime 值的一般行为。
这是一个示例实现,但缺少解析本身:
[TypeConverter(typeof(DateTimeWrapperConverter))]
public class DateTimeWrapper
{
public DateTime Value { get; set; }
}
public class DateTimeWrapperConverter : TypeConverter
{
public override bool CanConvertFrom(
ITypeDescriptorContext context, Type sourceType)
{
if (sourceType == typeof (string))
{
return true;
}
return base.CanConvertFrom(context, sourceType);
}
public override object ConvertFrom(
ITypeDescriptorContext context, CultureInfo culture, object value)
{
if (value is string)
{
DateTimeWrapper wrapper = new DateTimeWrapper
{
Value = new DateTime() // parse the url segment !!
};
return wrapper;
}
return base.ConvertFrom(context, culture, value);
}
}
你可以用这样的控制器来测试:
public class TestController : ApiController
{
// GET api/<controller>/5
public string Get(DateTimeWrapper id)
{
return id.Value.ToString(CultureInfo.InvariantCulture);
}
}
由于id 是DateTimeWrapper 类型,它使用自定义转换器进行转换。
如果您愿意,您可以更改 DateTimeWrapper,使其隐式转换为 DateTime,这样您就无需阅读 Value 属性。将此添加到 DateTimeWrapper 类:
public static implicit operator DateTime(DateTimeWrapper wrapper)
{
return wrapper.Value;
}
在此之后,您可以在需要 DateTime 时使用此类的对象。
注意:在这种情况下,更改 JSON.NET 序列化程序不会有任何作用。它仅用于反序列化 HTTP 请求的负载,但对路由参数没有任何作用。