package me.vickychijwani.spectre.network;

import com.google.gson.JsonArray;
import com.google.gson.JsonDeserializationContext;
import com.google.gson.JsonDeserializer;
import com.google.gson.JsonElement;
import com.google.gson.JsonObject;
import com.google.gson.JsonParseException;
import com.google.gson.JsonPrimitive;

import java.lang.reflect.Type;
import java.util.Map;

import me.vickychijwani.spectre.model.ConfigurationList;
import me.vickychijwani.spectre.model.ConfigurationParam;

public class ConfigurationListDeserializer implements JsonDeserializer<ConfigurationList> {

    @Override
    public ConfigurationList deserialize(JsonElement element, Type type,
                                         JsonDeserializationContext context)
            throws JsonParseException {
        JsonArray configJsons = element.getAsJsonObject().getAsJsonArray("configuration");
        if (configJsons.size() > 0 && !configJsons.get(0).getAsJsonObject().has("key")) {
            // new configuration format - dictionary style
            // { configuration: [{ fileStorage: {value: true, type: "bool"}, ... }] }
            return parseDictionaryStyleConfig(configJsons.get(0).getAsJsonObject());
        } else {
            // old configuration format - array of entries
            // { configuration: [ {key: fileStorage, value: true}, ... ] }
            return parseArrayOfEntriesConfig(configJsons);
        }
    }

    private ConfigurationList parseDictionaryStyleConfig(JsonObject configJson) {
        ConfigurationList config = new ConfigurationList();
        for (Map.Entry<String, JsonElement> entryJson : configJson.entrySet()) {
            String key = entryJson.getKey();
            JsonPrimitive valueJson = entryJson.getValue().getAsJsonObject()
                    .get("value").getAsJsonPrimitive();
            config.configuration.add(makeConfigParam(key, valueJson));
        }
        return config;
    }

    private ConfigurationList parseArrayOfEntriesConfig(JsonArray configJsons) {
        ConfigurationList config = new ConfigurationList();
        for (JsonElement itemJsonEl : configJsons) {
            JsonObject itemJson = itemJsonEl.getAsJsonObject();
            String key = itemJson.get("key").getAsString();
            JsonPrimitive valueJson = itemJson.getAsJsonPrimitive("value");
            config.configuration.add(makeConfigParam(key, valueJson));
        }
        return config;
    }

    private ConfigurationParam makeConfigParam(String key, JsonPrimitive value)
            throws JsonParseException {
        ConfigurationParam param = new ConfigurationParam();
        String valueStr;
        if (value.isString()) {
            valueStr = value.getAsString();
        } else if (value.isBoolean()) {
            valueStr = String.valueOf(value.getAsBoolean());
        } else if (value.isNumber()) {
            valueStr = String.valueOf(value.getAsDouble());
        } else {
            throw new JsonParseException("unknown value type in Ghost configuration list");
        }
        param.setKey(key);
        param.setValue(valueStr);
        return param;
    }

}

@@ -36,16 +36,86 @@
 twork;%0A%0A
+import android.util.Log;%0A%0Aimport com.crashlytics.android.Crashlytics;%0A
 import c
@@ -140,16 +140,16 @@
 nArray;%0A
-
 import c
@@ -844,32 +844,50 @@
 arseException %7B%0A
+        try %7B%0A    
         JsonArra
@@ -965,24 +965,28 @@
 %22);%0A        
+  
+  
 if (configJs
@@ -1067,16 +1067,20 @@
         
+    
 // new c
@@ -1118,16 +1118,20 @@
 y style%0A
+    
         
@@ -1212,32 +1212,36 @@
 %5D %7D%0A            
+    
 return parseDict
@@ -1297,32 +1297,36 @@
 ect());%0A        
+    
 %7D else %7B%0A       
@@ -1330,16 +1330,20 @@
         
+ 
+   
 // old c
@@ -1381,16 +1381,20 @@
 entries%0A
+    
         
@@ -1464,32 +1464,36 @@
 %5D %7D%0A            
+   
+ 
 return parseArra
@@ -1523,16 +1523,277 @@
 Jsons);%0A
+            %7D%0A        %7D catch (Exception e) %7B%0A            // FIXME temp log to help debug Crashlytics issue #87%0A            Crashlytics.log(Log.DEBUG, %22ParseException%22, %22Exception thrown while trying to parse JSON: %22 + element.toString());%0A            throw e;%0A
         
@@ -3024,16 +3024,16 @@
 lueStr;%0A
-
         
@@ -3031,24 +3031,210 @@
 %0A        if 
+(value == null) %7B%0A            // FIXME temp log to help debug Crashlytics issue #87%0A            throw new NullPointerException(%22value for key '%22 + key + %22' is null!%22);%0A        %7D else if 
 (value.isStr

Add temp logging for Crashlytics issue 87.