2011-12-28 44 views
11

Có ai có Deserializer làm việc không? tôi đang nhận được biểu thức JSON hoàn chỉnh trong phương pháp "deserialize" thay vì phần tử ??Gson Deserializer cho java.util.Date

public static void main(String[] args) { 
    GsonBuilder gb = new GsonBuilder(); 
    gb.registerTypeAdapter(DummyObject.class, new JsonSerializer<Date>() { 
     public JsonElement serialize(Date src, Type typeOfSrc, JsonSerializationContext context) { 
      System.out.println("serialize..."); 
      return new JsonPrimitive(DateUtil.toString(src)); 
     } 
    }); 
    gb.registerTypeAdapter(DummyObject.class, new JsonDeserializer<Date>() { 
     DateFormat format = DateFormat.getInstance(); 

     public Date deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context) throws JsonParseException { 
      if (!(json instanceof JsonPrimitive)) { 
       throw new JsonParseException("The date should be a string value"); 
      } 

      try { 
       return format.parse(json.getAsString()); 
      } catch (ParseException e) { 
       throw new JsonParseException(e); 
      } 
     } 
    }); 

    String jsonExp = "{\"createdDate\":\"2011-12-27T15:21:16\"}"; 
    Gson g = gb.create(); 
    DummyObject tf = g.fromJson(jsonExp, DummyObject.class); 

} 

Trả lời

40
Gson gson = new GsonBuilder() 
.setDateFormat("yyyy-MM-dd'T'HH:mm:ssz") 
.create(); 
+2

chữ 'z' nhỏ ở cuối có thể là vấn đề đối với chuỗi ngày tháng được định dạng ISO vì múi giờ có thể là Z hoặc số 00: 00 không thể được xử lý đúng cách bởi SimpleDateFormat – Lucas

+0

Rất muốn biết cách định cấu hình Spring để thực hiện việc này. – user1944491

+0

câu trả lời hoàn hảo ..... đã bỏ phiếu cho 1 – sonida

-2

Với mã trong câu hỏi ban đầu, sử dụng Gson 1.7.1 hoặc Gson 2.0, tất cả tôi nhận được là "ngoại lệ trong chủ đề 'chính' com.google.gson.JsonParseException: Ngày phải là một chuỗi giá trị". Đây là những gì tôi mong đợi mã như được viết để làm.

Tôi đoán bạn có thể muốn đăng ký bộ điều hợp loại cho java.util.Date và không cho DummyObject. (Điều này dẫn đến một lỗi khác, nhưng tôi nghĩ nó gần với những gì bạn đang cố gắng đạt được. Tất nhiên, tôi đoán một chút về ý định của câu hỏi/mã.)

Hoặc có thể bạn muốn thay đổi logic deserialization theo các dòng sau, hiểu rằng bạn chỉ muốn deserialize phần ngày của JSON thành một java.util.Date.

gb.registerTypeAdapter(DummyObject.class, new JsonDeserializer<Date>() 
{ 
    DateFormat format = DateFormat.getInstance(); 

    public Date deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context) 
     throws JsonParseException 
    { 
    try 
    { 
     return format.parse(((JsonObject)json).get("createdDate").getAsString()); 
    } 
    catch (ParseException e) 
    { 
     throw new JsonParseException(e); 
    } 
    } 
}); 

Bạn vẫn cần giải quyết lỗi phân tích cú pháp ngày cụ thể hơn.

+0

Nếu JSON Biểu hiện chứa các trường khác ánh xạ để cho phép nói "DummyObject" và một trong các trường được biểu diễn dưới dạng ngày.? – gpa

0

Ở đây bạn đi, tùy chỉnh Gson builder mà xử lý hầu hết các ngày mẫu sử dụng JodaTime (có thể loại trừ nó nếu không muốn sử dụng nó, nó chỉ mở rộng khả năng)

public class MyGsonBuilder { 

    public static <T> List<T> toList(String json, Class<T> clazz) { 
     if (null == json) { 
      return null; 
     } 
     Gson gson = build(); 
     return gson.fromJson(json, new TypeToken<T>() { 
     }.getType()); 
    } 

    private static boolean enableLog = false; 


    private static void log(String log) { 
     if (enableLog) Log.d("DEBUG_GSON_TIME", log); 
    } 

    static List<SimpleDateFormat> knownPatterns = new ArrayList<>(Arrays.asList(
      new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ssZ"), 
      new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSSZ"), 
      new SimpleDateFormat("yyyy-MM-dd' 'HH:mm:ss"), 
      new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss'Z'"), 
      new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss") 
    )); 

    static JsonSerializer<Date> ser = new JsonSerializer<Date>() { 
     @Override 
     public JsonElement serialize(Date src, Type typeOfSrc, JsonSerializationContext context) { 
      return new GsonBuilder().create().toJsonTree(buildIso8601Format().format(src)); 
     } 
    }; 


    static JsonDeserializer<Date> deser = new JsonDeserializer<Date>() { 

     @Override 
     public Date deserialize(JsonElement json, Type typeOfT, 
           JsonDeserializationContext context) throws JsonParseException { 
      Date date = null; 

      try { 
       // Take a try 
       String dateString = json.getAsJsonPrimitive().getAsString(); 
       log("deserialize date string = " + dateString); 
       date = buildOddFormat().parse(dateString); 
       log(" pattern (yyyy-MM-dd HH:mm:ss) = SUCCESS " + dateString + " = " + date.toString()); 
      } catch (Throwable t) { 
       // Loop on 
       log(" pattern (yyyy-MM-dd HH:mm:ss) = error = " + t.getMessage()); 
      } 

      if (date == null) { 
       try { 
        // Take a try 
        String dateString = json.getAsJsonPrimitive().getAsString(); 
        date = buildOldFormat().parse(dateString); 
        log(" pattern (MMM dd, yyyy HH:mm:ss) = SUCCESS " + dateString + " = " + date.toString()); 
       } catch (Throwable t) { 
        // Loop on 
        log(" pattern (MMM dd, yyyy HH:mm:ss) = error = " + t.getMessage()); 
       } 

      } 
      if (date == null) { 
       try { 
        // Take a try 
        String dateString = json.getAsJsonPrimitive().getAsString(); 
        date = buildVeryOldFormat().parse(dateString); 
        log(" pattern (MMM d, yyyy HH:mm:ss) = SUCCESS " + dateString + " = " + date.toString()); 
       } catch (Throwable t) { 
        // Loop on 
        log(" pattern (MMM d, yyyy HH:mm:ss) = error = " + t.getMessage()); 
       } 

      } 
      if (date == null) 

       for (SimpleDateFormat pattern : knownPatterns) { 
        try { 
         // Take a try 
         if (!pattern.toPattern().contains("Z")) 
          pattern.setTimeZone(TimeZone.getTimeZone("UTC")); 
         String dateString = json.getAsJsonPrimitive().getAsString(); 
         if (!pattern.toPattern().contains("Z")) 
          pattern.setTimeZone(TimeZone.getTimeZone("UTC")); 
         date = new Date(pattern.parse(dateString).getTime()); 
         log(" pattern (" + pattern.toPattern() + ") = SUCCESS " + dateString + " = " + date.toString()); 
         break; 
        } catch (Throwable t) { 
         // Loop on 
         log(" pattern (" + pattern.toPattern() + ") = error = " + t.getMessage()); 
        } 
       } 

//   } 
      if (date == null) { 
       try { 
        date = new Date(json.getAsJsonPrimitive().getAsLong()); 
        log(" Joda = SUCCESS " + json.getAsJsonPrimitive().getAsString() + " = " + date.toString()); 
       } catch (Throwable t) { 
        log(" pattern (Long) = error = " + t.getMessage()); 
       } 
      } 
      if (date == null) { 
       try { 
        date = DateFormat.getInstance().parse(json.getAsJsonPrimitive().getAsString()); 
        log(" Joda = SUCCESS " + json.getAsJsonPrimitive().getAsString() + " = " + date.toString()); 
       } catch (Throwable t) { 
        log(" pattern (DateFormat.getInstance().parse()) = error = " + t.getMessage()); 
       } 
      } 
      if (date == null) { 
       DateTimeFormatter fmt = ISODateTimeFormat.dateTime(); 
       try { 
        String dateString = json.getAsJsonPrimitive().getAsString(); 
        date = fmt.parseDateTime(dateString).toDate(); 
        log(" Joda = SUCCESS " + dateString + " = " + date.toString()); 
       } catch (Throwable t) { 
        // Loop on 
        log(" Joda error = " + t.getMessage()); 
        Crashlytics.logException(new Throwable("NON PARSABLE DATE!!! = " + json.toString())); 
       } 
      } 

      if (date == null) 
       date = new Date(); 

      return date; 
     } 
    }; 

    private static DateFormat buildIso8601Format() { 
     DateFormat iso8601Format = new SimpleDateFormat(
       "yyyy-MM-dd'T'HH:mm:ss.SSSZ"); 
     return iso8601Format; 
    } 

    private static DateFormat buildOddFormat() { 
     DateFormat iso8601Format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); 
     iso8601Format.setTimeZone(TimeZone.getTimeZone("UTC")); 
     return iso8601Format; 
    } 

    private static DateFormat buildOldFormat() { 
     DateFormat iso8601Format = new SimpleDateFormat("MMM dd, yyyy HH:mm:ss"); 
     iso8601Format.setTimeZone(TimeZone.getTimeZone("UTC")); 
     return iso8601Format; 
    } 

    private static DateFormat buildVeryOldFormat() { 
     DateFormat iso8601Format = new SimpleDateFormat("MMM d, yyyy HH:mm:ss"); 
     iso8601Format.setTimeZone(TimeZone.getTimeZone("UTC")); 
     return iso8601Format; 
    } 

    static public Gson build() { 
     Gson gson = new GsonBuilder() 
       //.setDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSSZ") 
       .registerTypeAdapter(Date.class, deser) 
       .registerTypeAdapter(Date.class, ser) 
       .excludeFieldsWithoutExposeAnnotation() 
       .create(); 
     return gson; 
    } 
} 
Các vấn đề liên quan