假设我们有行动:
[HttpGet]
public Task<IActionResult> Foo(DateTime date)
{
var utc = date.ToUniversalTime();
}
默认情况下,MVC框架似乎将UTC DateTime转换为Local(中间件中的某个位置)。如何关闭此行为并摆脱其他转换?
UPD:
Chrome开发者console(网络选项卡)显示我这样的查询参数:
date:2017-12-01T00:00:00.000Z
但在控制器中我看到:
{01/12/2017 03:00:00}
答案 0 :(得分:1)
DateTime
。这就是DateTimeOffset
存在的原因。默认情况下,DateTime.Kind
为DateTimeKind.Unspecified
。换句话说,在发布后,它取决于你,以确定它应被解释为什么。问题是你真的只能假设DateTimeKind.Utc
,因为这是唯一可以正确解释为DateTime
的东西。发布用户的本地时间会使您陷入困境,因为DateTimeKind.Local
实际上意味着服务器的本地时间,这通常不会与客户端相同[&1;第
但是,即使在HTML5中,使用时区发布完整日期时间实际上也是不可能的。虽然存在datetime
和datetime-local
等输入类型,但它们并未在任何主要浏览器中实现。如果您想发布带有时间和时区的日期,那么您实际上需要在视图模型上使用三个属性:
public DateTime Date { get; set; }
public TimeSpan Time { get; set; }
public string TimeZone { get; set; }
TimeZone
属性假设您使用由TimeZoneInfo.GetSystemTimeZones()
的值组成的下拉列表。如果您想使用不同的设置,则需要某种方式来映射/从这些值映射,因为您必须使用C#来获取偏移量。但是,您可以简单地允许用户发布偏移量,但这对用户不太友好,对某些用户来说可能很难。特别是,他们不仅需要了解概念&#34;偏离UTC&#34;意味着,但也考虑到夏令时的当前状态,并根据实际日期调整该偏移。
无论如何,在{{1}的情况下,每个属性都可以轻松映射到输入类型:date
/ time
和select
/ time
取决于您是使用下拉列表还是手动偏移条目。它们也可以通过模型绑定器轻松映射回您的视图模型。然后,您只需要根据该信息创建TimeZone
,这就是您实际在实体类中保留的信息。
DateTimeOffset