0

有时我需要向客户发送一封简单的电子邮件,其中包含我们存储在对象中的数据。但是,对象的日期时间存储为长吗?Unix 时间戳。显然,这种格式对于普通人来说是不可读的,必须转换为客户可以理解的格式。我无法将时间戳的类型从 long 更改为 DateTime,因为它会在许多地方破坏代码。到目前为止,我可以想出一种使用 JSON 序列化器的自定义转换器的解决方案。但是,我不想破坏反序列化过程的逻辑。我很想省略在 Converter 中实现 Read 功能,但如果我这样做,我会得到错误。我想要做的是只返回读者的价值?我认为?

有人能说这段代码是否不会破坏 JsonSerializer 的反序列化过程吗?否则会非常糟糕。

或者也许有更好的解决方案可以在 JSON 文件中将长数字换成漂亮的日期?

编辑:有点像预期的那样,代码炸毁了应用程序,但不是因为错误的读取函数,而是因为在序列化对象之前尝试反序列化时它崩溃了。它期待很长时间,但约会看起来很漂亮。我的解决方法是使用选项 WriteIndented 来决定我是否想要长?要序列化的时间戳或作为一个漂亮的日期。

using System;
using System.Text.Json;
using System.Text.Json.Serialization;

public class EpochToDateJSONSerializeConverter : JsonConverter<long?>
    {
        public override long? Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options)
        {
            if(reader.TryGetInt64(out long currentValue))
            {
                return currentValue;
            }
            return null;
        }

        public override void Write(Utf8JsonWriter writer, long? value, JsonSerializerOptions options)
        {
            if (options.WriteIndented)
            {
                if (value.HasValue)
                {
                    long unixTimeStamp = value.Value;
                    DateTime dtDateTime = new DateTime(1970, 1, 1, 0, 0, 0, 0, DateTimeKind.Utc);
                    dtDateTime = dtDateTime.AddMilliseconds(unixTimeStamp).ToLocalTime();
                    writer.WriteStringValue(dtDateTime.ToString());
                }
                else
                {
                    writer.WriteStringValue("null");
                }
            }
            else
            {
                if (value == null) writer.WriteStringValue("null");
                else writer.WriteNumberValue(value.Value);
            }
        }
    }

我一直在一个简单的汽车类上测试转换器。重要的是只选长了?属性更改为漂亮的日期和其他保持不变。

public class Car
    {
        public string Name { get; set; }
        public long? Kilometrage { get; set; }
        [JsonConverter(typeof(EpochToDateJSONSerializeConverter))]
        public long? ProductionDate { get; set; }
    }

在主要:

    Car car = new Car() { Name = "MyCar", Kilometrage = 69, ProductionDate = 1589277616910};
    Console.WriteLine(JsonSerializer.Serialize(car));
4

1 回答 1

0

如果你不介意 aDateTimeOffset而不是 a DateTime,总有DateTimeOffset.FromUnixTimeSeconds它的逆.ToUnixTimeSeconds

于 2020-06-10T14:41:36.703 回答