{
"breviario": {
"metaLiturgia": {
"fecha" : "Martes 5 de febrero del 2019",
"tiempo" : "PROPIO DE LOS SANTOS",
"semana" : "",
"mensaje": "",
"salterio": "",
"color":0,
"meta": ""
},
"santo": {
"nombre": "Santa Águeda, virgen y mártir",
"vida": "Padeció el martirio en Catania (Sicilia), probablemente en la persecución de Decio. Desde la antigüedad su culto se extendió por toda la Iglesia y su nombre fue introducido en el Canon romano."
},
"oficio": {
"himno": {
"texto": "Testigos de amor~de Cristo Señor,~mártires santos.§Rosales en flor~de Cristo el olor,~mártires santos.§Palabras en luz~de Cristo Jesús,~mártires santos.§Corona inmortal~del Cristo total,~mártires santos. Amén."
},
"salmodia": {
...
public class Oficio {
private Invitatorio invitatorio;
private Himno himno;
private Salmodia salmodia;
private String oracion;
private String responsorio;
private OficioLecturas oficioLecturas;
public Oficio () {}
public Himno getHimno() {
return himno;
}
public void setHimno(Himno himno) {
this.himno = himno;
}
// ...
}
public class Himno {
private String texto;
public Himno () {}
public Spanned getTexto() {
Spanned str = Utils.fromHtml(Utils.getFormato(texto));
return str;
}
public void setTexto(String texto) {
this.texto = texto;
}
//...
}
DocumentReference docRef = db.collection("liturgia").document("breviario")
.collection("oficio").document("20190204");
docRef.get().addOnSuccessListener(new OnSuccessListener<DocumentSnapshot>() {
@Override
public void onSuccess(DocumentSnapshot documentSnapshot) {
Oficio oficio = documentSnapshot.toObject(Oficio.class);
Himno himno=oficio.getHimno();
Log.d(TAG,oficio.getOracion().toString()); //Correct
}
});
E/AndroidRuntime:致命异常:主进程:org.my.app,PID:10532 java.lang.RuntimeException:无法反序列化对象。无法将com.google.firebase.firestore.documenttype对象转换为类型org.my.app.model.himno(在“himno”字段中找到)(位于com.google.firebase.firestore.util.CustomClassMapper.Deserializeerror(com.google.firebase:firebase-firestore@@17.1.2:524)(位于com.google.firebase.firestore.util.CustomClassMapper.ConvertBean7.1.2:674)在com.google.firebase.firestore.util.CustomClassMapper.ConvertBean(com.google.firebase:firebase-firestore@@17.1.2:503)在com.google.firebase.firestore.util.CustomClassMapper.DeserializeToClass(com.google.firebase:firebase-firestore@@17.1.2:242)在
您将得到以下错误:
无法将类型为com.google.firebase.firestore.documentreference的对象转换为类型为org.my.app.model.himno(在“himno”字段中找到)
因为您正在尝试将DocumentReference
对象转换为Himno
对象。在Java中没有办法实现这一点,因为它们之间没有继承关系。
您试图从以下位置获取的文档:
db.collection("liturgia").document("breviario").collection("oficio").document("20190204");
类型为oficio
,因此以下代码行:
Oficio oficio = documentSnapshot.toObject(Oficio.class);
会工作得很好。问题是当您试图获取Himno
对象时,该对象嵌套在Oficio
类下,如下所示:
Himno himno=oficio.getHimno();
这将无法按照您的方式工作,因为文档中的Himno
属性包含的值类型为DocumentReference
而不是Himno
。
请参见,himno
属性有一个引用。如果要获取文档引用,只需使用:
DocumentReference documentReference = documentSnapshot.getDocumentReference("himno");
如果要使用:
Himno himno=oficio.getHimno();
然后将Himno
属性更改为Himno
类型,而不是DocumentReference
类型。
正如@anees在他的aswer中指出的,您的代码中的另一个问题是getTexto()
方法应该返回一个String
而不是一个spanned
对象,因为这是数据库中存储的方式。
请参见,texto
属性保存的是字符串,而不是spanned
。但这并不是您的错误发生的原因。
还请注意,以下句子:
Firestore中的自定义类必须包含
public class Oficio {
public Invitatorio invitatorio;
public Himno himno;
public Salmodia salmodia;
public String oracion;
public String responsorio;
public OficioLecturas oficioLecturas;
}
编辑:
根据你的评论:
我将getTexto()的类型从spaned更改为String,但不起作用。
仅将getTexTo()
方法的返回类型从spanned
更改为String
不会帮助您解决主要错误。
我不明白如何将himno属性更改为类型为himno而不是DocumentReference。
您没有分享将数据添加到数据库的方式,但实际上非常简单。首先,从这些文档中删除himno
属性。然后,在添加新文档时,不是添加DocumentReference
,而是添加Himno
类型的对象,正如我还看到您在Oficio
类中声明的那样。这也意味着,当您使用以下代码行时:
Himno himno=oficio.getHimno();
将返回Himno
类型的对象,而不是DocumentReference
。这是因为它是根据其数据类型存储的。
在RealTimeDatabase中,可以只获取一个对象(Oficio par示例),并且可以从该对象获取对另一个嵌套对象的引用(Himno par示例)。
这也可以在Cloud Firestore中完成,但您需要根据数据库中存在的属性的数据类型获取数据。如果属性的类型为DocumentReference
,则不能将其作为Himno
类型获取,除非您这样添加它。
请参阅文档中的“自定义对象”部分
是的,我明白了。这就是为什么我告诉您要根据数据存储的数据类型获取数据的原因。因此,如果您将数据存储为DocumentReference
,请根据它获取数据。如果您希望以himno
的形式获取它,那么首先将其存储为himno
并相应地获取它。
编辑2:
是的,你能做到。您是如何在数据库中添加该引用的?以与添加引用相同的方式添加himno
对象。
我不明白我怎么能做到这一点。
当您通过创建OFICIO
类型的对象向数据库添加数据时,请以正确的方式设置Himno
对象。试试看:
Oficio oficio = new Oficio();
Himno himno = new Himno();
himno.setTexto("Your Text");
oficio.setHimno(himno);
docRef.set(oficio);
我误会了?
是的。要能够管理云Firestore数据库,您至少应该对以下方面有基本的了解:
我不能读取属性作为自定义类'Himno'。当我尝试时,即使我注释一行,我也会得到一个“运行时间异常”:。然而,我可以得到属性到相应的变量。 E/AndroidRuntime:致命异常:主进程:组织。我的应用程序,PID:10532 java。lang.RuntimeException:无法反序列化对象。无法转换com类型的对象。谷歌。火基。消防商店。文档引用类型org。我的应用程序。模型Himno
问题内容: 我有一个名为的类,该类具有一个作为参数的构造函数: 具有以下属性: 并且是我的应用程序的其他类,并具有以下构造函数: ,并且是的子类。 我想用Gson 反序列化数组,所以我写道: 以定义为: 调试时,实例具有正确的“ MainActivity”作为上下文,而其成员变量的上下文为null。 Gson 使用正确的构造函数创建了对象,但使用默认的无参数构造函数创建了实例。我怎样才能解决这个问
我有一个名为PageItem的类,它有一个构造函数,该构造函数将上下文作为参数: 具有以下属性: 新闻提供者(Newsprovider)和主题(Topic)是我的应用程序的其他类,具有以下构造函数:
但它返回一个id为空且产品为空的对象。当然,我不需要为这个简单的操作编写自定义的吗?
(数据类)实体。JAVA (数据类)实体。JAVA 我试着说: 我犯了一个错误: 我已经把和我错过了什么?
我对对象接口的jackson序列化有问题。 我有课 哪个实现 还有上课 哪个实现 上课 我要和Jackson连载Container得到结果 但事实上我得到了结果 尽管我在映射中指定了点的序列化类型(),但在嵌套对象“point”中具有属性“name”。接口点视图没有方法getName,但结果中存在点的字段“name”。 若我从类容器中的方法getMap中删除注释(),我将得到结果 现在点没有属性"