Newtonsoft.Json中的時間格式詳解.


Newtonsoft.json是一款不錯的序列化反序列化第三方組件,具體如何使用屬於基礎知識,此處不再講解.看以下代碼:

public class OutgameEntity
{
    public string orderid{get;set;}
    public DateTime? payTime { get; set; }
}

很簡單的一個實體類

假如此時有一個url:http://www.xxx.xx/do.svc/xxx?data=,我們如果要把OutgameEntity實體類的值傳過去,就需要反序列化對象為string字符串.

public static string JsonSerialize(T o)
{
   string str = JsonConvert.SerializeObject(o, Newtonsoft.Json.Formatting.Indented, new JsonSerializerSettings
   {
        NullValueHandling = NullValueHandling.Ignore
   });
   return str;
}
 
new WebClient().DownloadString(url,JsonSerialize(OutgameEntity));
 
此段代碼看似沒有任何問題.不過當你接收時,你會發現一點點問題.
"payTime":"\/Date(13884569650000800)\/".
如果這個參數值沒有任何意義,那么我們可以忽略這個問題.但是作為程序員,特別是和別的公司進行對接的接口會出現這樣的參數值,會給同行造成此人是菜鳥的心理.所以我們應該想辦法解決這個不大不小的問題.
如何解決呢?
 
請看以下這個接口:
using Newtonsoft.Json.Schema;
using System;

namespace Newtonsoft.Json
{
    public abstract class JsonConverter
    {
        protected JsonConverter();

        public virtual bool CanRead { get; }
        public virtual bool CanWrite { get; }

        public abstract bool CanConvert(Type objectType);
        public virtual JsonSchema GetSchema();
        public abstract object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer);
        public abstract void WriteJson(JsonWriter writer, object value, JsonSerializer serializer);
    }
}
using Newtonsoft.Json;
using System;

namespace Newtonsoft.Json.Converters
{
    public abstract class DateTimeConverterBase : JsonConverter
    {
        protected DateTimeConverterBase();

        public override bool CanConvert(Type objectType);
    }
}

已經有了DatetimeConverterBse這個父類,那么要實現這個功能就比較好辦.

我們去重寫實現JsonConverter中的ReadJson和WriteJson方法,如下:

public class UnixDateTimeConverter : DateTimeConverterBase
{
    public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
    {
        if (reader.TokenType != JsonToken.Integer)
        {
            throw new Exception(String.Format("日期格式錯誤,got {0}.", reader.TokenType));
        }
        var ticks = (long)reader.Value;
        var date = new DateTime(1970, 1, 1);
        date = date.AddSeconds(ticks);
        return date;
    }
    public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer)
    {
        long ticks;
        if (value is DateTime)
        {
            var epoc = new DateTime(1970, 1, 1);
            var delta = ((DateTime)value) - epoc;
            if (delta.TotalSeconds < 0)
            {
                throw new ArgumentOutOfRangeException("時間格式錯誤.1");
            }
            ticks = (long)delta.TotalSeconds;
        }
        else
        {
            throw new Exception("時間格式錯誤.2");
        }
        writer.WriteValue(ticks);
    }
}

請注意JsonConverter類中有一個方法叫CanConvert(Type t),那由此我們是否可以用這樣的方式來實現呢?如代碼所示:

public class ModelEntity
{
    public string value { get; set; }

    [JsonConverter(typeof(UnixDateTimeConverter))]
    public DateTime createtime { get; set; }
}
 
OK,debug走起,
private void button1_Click(object sender, EventArgs e)
{
    var model = new ModelEntity();
    model.birthdate = DateTime.Now;
    model.value = "Find a Way";
    var str = Common.SerializerHelper<ModelEntity>.JsonSerialize(model);
 }

image

那我修改實體,如下:

image

再去反序列化呢?

image

時間戳,高大尚,媽媽再也不用擔心我寫代碼.


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM