从Firebase数据库并行检索数据并与Android中的UI同步

时间:2017-01-14 11:07:49

标签: android firebase firebase-realtime-database

我试图在我的应用中实现firebase数据库,但是我在同时从多个节点检索数据并更新ui时遇到了问题。 我将所有Firebase方法存储在一个单独的类中。 这是从节点检索一个数据的方法之一的示例。

public static void getTrainerCity(final Trainer trainer) {
    dbref.child(USER_CITY).child(trainer.getId()).addValueEventListener(new ValueEventListener() {
        @Override
        public void onDataChange(DataSnapshot dataSnapshot) {
            trainer.setCity(dataSnapshot.getValue(String.class));
        }

        @Override
        public void onCancelled(DatabaseError databaseError) {

        }
    });
}

然后,为了得到一个完整的培训师,我做

public static void getTrainer(final boolean isAthlete, final String trainerId, Trainer trainer) {
    trainer.setId(trainerId);
    getTrainerCity(trainer);
    getTrainerName(trainer);
    getTrainerAge(trainer);
    getTrainerNumber(trainer);
    getTrainerEmail(trainer);
    getTrainerGym(trainer);
    getTrainerPhoto(trainer);
    getTrainerStudyDegree(trainer);
    getTrainerDescription(trainer);
    if(!isAthlete) {
        getTrainerAthletes(trainer);
    }
}

当我在UI中调用此方法时,由于这些方法不在主线程上运行,因此我无法一次性获取整个Trainer对象。这意味着培训师会不断更新。但是,我只想在设置了与方法相关的对象的所有字段时通知UI(我必须填充列表并初始化用户)。你会怎么做?

我想过要附加听众,但似乎我需要大量的听众。谢谢你们

编辑:这就是Db的结构 This is how db is structured

2 个答案:

答案 0 :(得分:2)

这样的场景RxJava闪耀.....你可以做的是在Observable.create()中包装firebase查询然后使用类似RxJava zip运算符的东西来结合所有查询。替代方案(如果可能的话,可以避免)是嵌套导致可怕的callback hell

的所有查询

例如,getTrainerCity

可能包含以下内容
public static Observable<String> getTrainerCity(int trainerId) {
    return Observable.create(subscriber -> {
        dbref.child(USER_CITY).child(trainerId).addValueEventListener(new ValueEventListener() {
            @Override
            public void onDataChange(DataSnapshot dataSnapshot) {
                String city = dataSnapshot.getValue(String.class);
                subscriber.onNext(city);
                subscriber.onCompleted();
            }

            @Override
            public void onCancelled(DatabaseError databaseError) {
            }
        });    
    });
}

答案 1 :(得分:1)

您应首先获取培训师节点,然后解析所提取的数据。 我假设您有一个Trainer节点,其中包含所有信息(城市,名称,年龄......)

public static void getTrainer(final Trainer trainer) {
    dbref.child(trainer_node).addValueEventListener(new ValueEventListener() {
        @Override
        public void onDataChange(DataSnapshot dataSnapshot) {
            Trainer trainer = dataSnapshot.getValue(Trainer.class);
            String name = trainer.getName();
            String city = trainer.getCity();
            int age = trainer.getAge();
    .
    .
    .

        }

        @Override
        public void onCancelled(DatabaseError databaseError) {

        }
    });
}

修改 数据结构可能就像这样

-users_node
--user1
---id:userid 
---name: username
---city:usercity
---email:useremail
---workouts
----workoutid1:true
----workoutid2:true

--user2
---id:..

-athletes_node
--user1:true
--user2:true
--userX:true

-workouts_node
--workoutid1
---workout details here
--workoutid2
---workout details here