usar studio examples consultas como java android gson realm

java - studio - realm windows



Deserialización de Gson de la Lista<String> en realmList<RealmString> (4)

El mensaje de error " Expected a string but was NAME " se puede resolver recuperando el nombre del objeto json en el JsonReader antes del objeto json real (que es una String en su caso).

Puedes echar un vistazo a la documentación de Android para JsonReader . Tiene una explicación detallada y un fragmento de código. También puede echar un vistazo al método readMessage en el fragmento de código de ejemplo en la documentación.

He modificado su método de read a lo que creo que debería ser. NOTA: No probé el código, por lo que puede haber algunos errores menores en él.

@Override public RealmPerson read(JsonReader in) throws IOException { RealmPerson rList = new RealmPerson(); in.beginObject(); String name = ""; while (in.hasNext()) { name = in.nextName(); if (name.equals("userId")) { String userId = in.nextString(); // update rList here } else if (name.equals("otherStuff")) { // since otherStuff is a RealmList of RealmStrings, // your json data would be an array // You would need to loop through the array to retrieve // the json objects in.beginArray(); while (in.hasNext()) { // begin each object in the array in.beginObject(); name = in.nextName(); // the RealmString object has just one property called "value" // (according to the code snippet in your question) if (name.equals("val")) { String val = in.nextString(); // update rList here } else { in.skipValue(); } in.endObject(); } in.endArray(); } else { in.skipValue(); } } in.endObject(); return rList; }

Déjeme saber si esto ayuda.

Estoy usando la adaptación con gson para deserializar mi json en objetos de reino. Esto funciona muy bien en su mayor parte. El problema surge cuando se trata de

RealmList (String (o cualquier otro tipo de datos básico))

Como Realm no admite RealmList donde E no extiende el objeto Realm, envolví String en un RealmObject.

public class RealmString extends RealmObject { private String val; public String getValue() { return val; } public void setValue(String value) { this.val = value; } }

Mi objeto de reino es el siguiente

public class RealmPerson extends RealmObject { @PrimaryKey private String userId; ... private RealmList<RealmString> stringStuff; private RealmList<SimpleRealmObj> otherStuff; <setters and getters> }

SimpleRealmObj funciona bien ya que solo tiene elementos de cadena

public class SimpleRealmObj extends RealmObject { private String foo; private String bar; ... }

¿Cómo puedo deserializar stringStuff? Intenté usar un TypeAdapter de GSON

public class RealmPersonAdapter extends TypeAdapter<RealmPerson> { @Override public void write(JsonWriter out, RealmPerson value) throws IOException { out.beginObject(); Log.e("DBG " + value.getLastName(), ""); out.endObject(); } @Override public RealmPerson read(JsonReader in) throws IOException { QLRealmPerson rList = new RealmPerson(); in.beginObject(); while (in.hasNext()) { Log.e("DBG " + in.nextString(), ""); } in.endObject(); return rList; }

Sin embargo todavía golpeo el IllegalStateException

2334-2334 / com.qualcomm.qlearn.app E // PersonService.java: 71 ﹕ main com.google.gson.JsonSyntaxException: java.lang.IllegalStateException: se esperaba una cadena pero era NAME en la línea 1 columna 3 ruta $.

Probé RealmList, el adaptador RealmString anteriormente sin éxito. La única solución que logré encontrar hasta ahora es https://github.com/realm/realm-java/issues/620#issuecomment-66640786 Alguna opción mejor?


Mi gson typeAdapter fue el culpable. El error anterior se vio como no estaba deserializando el json en RealmPerson correctamente, el primer campo no es una cadena, por lo tanto

in.nextString ()

fue borking

Miré un código de ejemplo y me di cuenta, no tuve que usar

in.beginObject () y in.endObject ()

Deserializar una cadena. El código de abajo funciona.

public class QLRealmStringAdapter extends TypeAdapter<QLRealmString> { @Override public void write(JsonWriter out, QLRealmString value) throws IOException { Log.e("DBG " + value.getValue(), ""); out.value(value.getValue()); } @Override public RealmString read(JsonReader in) throws IOException { RealmString rString = new RealmString(); if (in.hasNext()) { String nextStr = in.nextString(); System.out.println("DBG " + nextStr); rString.setValue(nextStr); } return rString; }

}

Espero que esto ayude a alguien.


Necesito un serializador y deserializador jackson para convertir Arraylist a RealmList


Es mejor usar JsonSerializer y JsonDeserializer lugar de TypeAdapter para su RealmObject , debido a 2 razones:

  1. Le permiten delegar (des) la serialización para su RealmObject al serializador Gson (de) predeterminado, lo que significa que no necesita escribir la placa de calderín usted mismo .

  2. Hay un error extraño en Gson 2.3.1 que podría causar un Error durante la deserialización (probé el enfoque TypeAdapter y encontré este error).

Aquí le indicamos cómo (reemplace la Tag con su clase RealmObject ):

( context.serialize que context.serialize y context.deserialize continuación son equivalentes a gson.toJson y gson.fromJson , lo que significa que no necesitamos analizar la clase Tag nosotros mismos).

Analizador + serializador para RealmList<Tag> :

public class TagRealmListConverter implements JsonSerializer<RealmList<Tag>>, JsonDeserializer<RealmList<Tag>> { @Override public JsonElement serialize(RealmList<Tag> src, Type typeOfSrc, JsonSerializationContext context) { JsonArray ja = new JsonArray(); for (Tag tag : src) { ja.add(context.serialize(tag)); } return ja; } @Override public RealmList<Tag> deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context) throws JsonParseException { RealmList<Tag> tags = new RealmList<>(); JsonArray ja = json.getAsJsonArray(); for (JsonElement je : ja) { tags.add((Tag) context.deserialize(je, Tag.class)); } return tags; } }

Clase de etiqueta:

@RealmClass public class Tag extends RealmObject { private String value; public String getValue() { return value; } public void setValue(String value) { this.value = value; } }

Luego registre su clase de convertidor con Gson:

Gson gson = new GsonBuilder() .registerTypeAdapter(new TypeToken<RealmList<Tag>>() {}.getType(), new TagRealmListConverter()) .create();