com.google.firebase.database.DatabaseException:不支持序列化数组,请改用列表

时间:2016-07-30 11:34:40

标签: java android firebase firebase-realtime-database

我正在尝试使用以下代码保留自定义对象:

DatabaseReference databaseReference = FirebaseDatabase.getInstance().getReference();
DatabaseReference curWorkoutExercisesRef = databaseReference.child("workouts")
            .child(mCurrentWorkout.getId())
            .child("workoutExercises");

WorkoutExercise we = new WorkoutExercise(exercise);
curWorkoutExercisesRef.push().setValue(we);

这是我的目标:

public class WorkoutExercise {

    private String id;
    private Exercise exercise;

    public WorkoutExercise() {}

    // getters, setters, other methods 
    // ...
}

public class Exercise {

    private String id;
    private String title;

    private List<BodyPart> bodyParts;

    public Exercise() {}

    // getters, setters, other methods 
    // ...
}

public class BodyPart {

    private String id;
    private String name;

    public BodyPart() {}

    // getters, setters, other methods 
    // ...
}

每次我收到此错误 - com.google.firebase.database.DatabaseException: Serializing Arrays is not supported, please use Lists instead。我的对象不包含任何数组,因此这个错误看起来很混乱。我找到了一种方法来修复此错误 - 如果我将@Exclude注释添加到bodyParts类的Exercise列表中,一切正常,但显然不是我想要实现的。

看来Firebase无法持久保存包含内部列表的对象?这里有任何简单的解决方法或最佳实践吗?谢谢!

P.S。我正在使用firebase-database:9.2.1

7 个答案:

答案 0 :(得分:12)

我设法找到导致此次崩溃的原因。我在另一台运行Android 5.x的设备上安装了该应用,Firebase在那里引发了一个不那么令人困惑的例外:

com.google.firebase.database.DatabaseException: No properties to serialize found on class android.graphics.Paint$Align

似乎Firebase(与Gson 不同)尝试序列化所有可能的getter,即使他们没有与全局变量(类成员/字段)直接连接,在我的特定情况下我的对象包含一个返回Drawable - getDrawable()的方法。显然,Firebase并不知道如何将drawable转换为json。

有趣的时刻(可能是Firebase SDK中的一个错误):在运行Android 4.4.1的旧设备上,我仍然在同一项目和配置中获得原始异常:

Caused by: com.google.firebase.database.DatabaseException: Serializing Arrays is not supported, please use Lists instead

答案 1 :(得分:6)

如果这有助于其他收到相同错误的人,我收到同样的错误,解决方案最终成为以下内容:

<强>更改:

databaseReference.child("somechild").setValue(etName.getText());

databaseReference.child("somechild").setValue(etName.getText().toString());

正如@fraggjkee指出的那样,Firebase会尝试序列化getter,这就是firebase尝试序列化.getText()的结果时的类似问题。

希望这有助于其他人!

答案 2 :(得分:4)

将@Exclude添加到FB尝试解释的函数,例如返回Drawable的函数。

@Exclude
public Drawable getUnitColorImage(){
    return TextDrawable.builder().buildRound("", prefColor);
}

答案 3 :(得分:1)

我有一个类似的问题,我试图使用groovy而不是Java,我想groovy正在为我生成其他get方法。我将我的域类从Pogo(src / main / groovy)转换为Pojo(src / main / java),现在一切运行良好

答案 4 :(得分:1)

//this will recreate your Object list by the constructor


private void handleData(){ 

    orderList = Db.getCarts();
    orders = new ArrayList<>();
    Double totalPrice = 0.0;

    for (Order order : orderList){
        // totalPrice = totalPrice + ( price * quantity )
        totalPrice += (Double.valueOf(order.getPrice())* Integer.valueOf(order.getQuantity()));
        orders.add(new Order(order.getProductId(),order.getProductName(),order.getQuantity(),order.getPrice(),order.getDiscount(),order.getImage()));
    }
}

 private void alertDialog() {

    AlertDialog.Builder alert = new AlertDialog.Builder(getContext());
    alert.setTitle("One more step!");
    alert.setMessage("Enter your address");

    final EditText edtaddress = new EditText(getContext());
    LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(
            LinearLayout.LayoutParams.MATCH_PARENT,
            LinearLayout.LayoutParams.MATCH_PARENT
    );

    edtaddress.setLayoutParams(layoutParams);
    alert.setView(edtaddress);
    alert.setIcon(R.drawable.ic_shopping_cart_black_24dp);

    alert.setPositiveButton("YES", new DialogInterface.OnClickListener() {
        @Override
        public void onClick(DialogInterface dialog, int which) {
            Request request = new Request(
                    Common.currentUser.getPhone(),
                    Common.currentUser.getName(),
                    edtaddress.getText().toString(),
                    textTotal.getText().toString(),
                    orders
            );

            // Submit to firebase
            // We will using system.currentMillis to key
            requestReference.child(String.valueOf(System.currentTimeMillis()))
                    .setValue(request);
            //Delete cart
            Db.deleteCart();
            Toast.makeText(getContext(), "Thank you , Order Place", Toast.LENGTH_SHORT).show();
            getActivity().finish();
        }
    });

    alert.setNegativeButton("No", new DialogInterface.OnClickListener() {
        @Override
        public void onClick(DialogInterface dialog, int which) {
            dialog.dismiss();
        }
    });

    alert.show();

}

答案 5 :(得分:0)

以下是我如何解决这个问题的方法。 我在尝试更新数据库中的int字段时发生了此问题。我从编辑文本字段中获取文本,忘记将其转换为int。这导致了失败。因此,如果出现此问题,请尝试检查您要发送到数据库的数据类型。

答案 6 :(得分:0)

当您使用 hashmap 设置值时,请使用它来获取您上传的图片的 url。

task.getResult().getDownloadUrl().toString()