androidjsonfirebasefirebase-realtime-databaseinstantiationexception

firebase: InstantiationException: Can't instantiate abstract class java.util.TimeZone


I try to parse a List of EventPojo-classes from a firebase DB like this:

GenericTypeIndicator<HashMap<String, EventPojo>> tEvents = new GenericTypeIndicator<HashMap<String, EventPojo>>() {};
HashMap<String, EventPojo> events = dataSnapshot.child(getString(R.string.eventsNodeName)).getValue(tEvents);

In EventPojo I have a GregorianCalender:

public class EventPojo implements Comparable<EventPojo>{

    GregorianCalendar date;
...

When I try to get the HashMap from the DB, I get an InstantiationException:

java.lang.RuntimeException: java.lang.InstantiationException: Can't instantiate abstract class java.util.TimeZone

Why is firebase trying to instatiate TimeZone and not GregorianCalender?


Solution

  • The Firebase Realtime Database only stores JSON types. There is no way to serialize/deserialize a GregorianCalendar (or TimeZone) without writing custom code.

    My typical approach is to have a property of the JSON type (for example, a Long to store the timestamp), and then have a getter that returns the type that the app works with (so a GregorianCalendar in your case). To make sure Firebase doesn't try to serialize the GregorianCalendar method, mark it as @Exclude (also see: How to ignore new fields for an object model with Firebase 1.0.2 for some examples of this).

    So:

    public class EventPojo implements Comparable<EventPojo>{
        public Long timestamp
    
        @Exclude
        public GregorianCalendar getDate() {
          ...
        }
        @Exclude
        public void getDate(GregorianCalendar date) {
          ...
        }
    
        ...
    

    With this, Firebase will see the timestamp field and read it from and write it to the database, while your code just interacts with getDate() and setDate().