如何使用Dapper.net从Postgres读取DateTimeOffset?

时间:2014-03-03 13:22:19

标签: postgresql dapper datetimeoffset

拥有这个Postgres表

CREATE TABLE "TimeRange"
(
  "Id" bigint NOT NULL,
  "Start" timestamp with time zone NOT NULL,
  "End" timestamp with time zone NOT NULL,
  CONSTRAINT "TimeRange_pkey" PRIMARY KEY ("Id")
)

填写

INSERT INTO "TimeRange"("Id", "Start", "End")
VALUES (1, '2014-03-03 05:55:00+01', '2014-03-03 05:55:00+01');

拥有这个C#POCO

public class TimeRange
{
    public long Id { get; set; }
    public DateTimeOffset Start { get; set; }
    public DateTimeOffset End { get; set; }
}

选择数据..

myOpenedNpgsqlConnection.Query<TimeRange>("SELECT * FROM \"TimeRange\"");

..导致DataException:“解析第1列时出错(Start = 03.03.2014 05:55:00 - DateTime)”

我知道错误消息中缺少时区信息。在PgAdmin中运行相同的sql语句将返回包含时区信息的结果。

是否有任何(干净的)方式通过dapper将Postgres“timestamp with timezone”读入DateTimeOffset?

编辑:

我发现将POCO修改为跟随似乎有效。但说真的,没有更好的方法吗?

public class TimeRange
{
    public long Id { get; set; }
    private DateTime Start { get; set; }
    private DateTime End { get; set; }

    public DateTimeOffset StartOffset { get { return this.Start; } set { this.Start = value.UtcDateTime; } }
    public DateTimeOffset EndOffset { get { return this.Start; } set { this.Start = value.UtcDateTime; } }
}

1 个答案:

答案 0 :(得分:0)

似乎PostgreSQL仅在内部存储UTC时间戳。 也许有帮助,如果你在SQL查询中转换时区信息,PostgreSQL会在客户端会话中使用TZ。

CREATE TABLE TimeRange
(
  Id bigint NOT NULL,
  start_at timestamp with time zone NOT NULL,
  end_at timestamp with time zone NOT NULL,
  CONSTRAINT TimeRange_pkey PRIMARY KEY (Id)
);

INSERT INTO TimeRange (Id, start_at, end_at)
VALUES (1, '2014-03-03 05:55:00+01', '2014-03-03 05:55:00+01');


SELECT 
  id, 
  start_at::TIMESTAMP WITH TIME ZONE as start, 
  end_at::TIMESTAMP WITH TIME ZONE as end 
FROM TimeRange;