【问题标题】:Unexpected Behavior When Query by .whereArrayContains().whereArrayContains() 查询时的意外行为
【发布时间】:2019-04-26 13:01:39
【问题描述】:

我有一个 RecyclerView,它利用 FireaseUI 并按“时间戳”字段(按顺序)对“轮询”节点中的所有对象进行排序。

新片段 - .onViewCreated()

 Query queryStore = FirebaseFirestore.getInstance()
            .collection(POLLS_LABEL)
            .orderBy("timestamp", Query.Direction.ASCENDING);
    //Cloud Firestore does not have any ordering; must implement a timestampe to order sequentially

    FirestoreRecyclerOptions<Poll> storeOptions = new FirestoreRecyclerOptions.Builder<Poll>()
            .setQuery(queryStore, Poll.class)
            .build();
    mFirestoreAdaper = new FirestoreRecyclerAdapter<Poll, PollHolder>(storeOptions) {
        @Override
        protected void onBindViewHolder(@NonNull final PollHolder holder, final int position, @NonNull Poll model) {
            holder.mPollQuestion.setText(model.getQuestion());
            String voteCount = String.valueOf(model.getVote_count());
            //TODO: Investigate formatting of vote count for thousands
            holder.mVoteCount.setText(voteCount);
            Picasso.get()
                    .load(model.getImage_URL())
                    .fit()
                    .into(holder.mPollImage);
            holder.mView.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View view) {
                    Intent toClickedPoll = new Intent(getActivity(), PollHostActivity.class);
                    String recyclerPosition = getSnapshots().getSnapshot(position).getId();
                    Log.v("Firestore ID", recyclerPosition);
                    toClickedPoll.putExtra("POLL_ID", recyclerPosition);
                    startActivity(toClickedPoll);

                }
            });
        }

我的应用中有另一个布局订阅了同一个节点,但是通过“关注者”和“时间戳”进行查询:

以下片段 - .onViewCreated()

  Query queryStore = FirebaseFirestore.getInstance()
            .collection(POLLS_LABEL)
            .whereArrayContains("followers", mUserId)
            .orderBy("timestamp", Query.Direction.ASCENDING);

    FirestoreRecyclerOptions<Poll> storeOptions = new FirestoreRecyclerOptions.Builder<Poll>()
            .setQuery(queryStore, Poll.class)
            .build();
    mFirestoreAdaper = new FirestoreRecyclerAdapter<Poll, PollHolder>(storeOptions) {
        @Override
        protected void onBindViewHolder(@NonNull final PollHolder holder, final int position, @NonNull Poll model) {
            holder.mPollQuestion.setText(model.getQuestion());
            String voteCount = String.valueOf(model.getVote_count());
            //TODO: Investigate formatting of vote count for thousands
            holder.mVoteCount.setText(voteCount);
            Picasso.get()
                    .load(model.getImage_URL())
                    .fit()
                    .into(holder.mPollImage);
            holder.mView.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View view) {
                    Intent toClickedPoll = new Intent(getActivity(), PollHostActivity.class);
                    String recyclerPosition = getSnapshots().getSnapshot(position).getId();
                    Log.v("Firestore ID", recyclerPosition);
                    toClickedPoll.putExtra("POLL_ID", recyclerPosition);
                    startActivity(toClickedPoll);

                }
            });
        }

在第一个场景中,UI 项在添加到 Firebase 时会实时填充到我的 RecyclerView 中。但是,当我通过“.whereArrayContains”查询时,我没有得到同样的行为,我很好奇为什么。仅当我重新启动应用程序时,这些项目才会重新出现:

编辑:

我把下面这行注释掉了:

// .whereArrayContains("followers", mUserId)

并且行为按预期执行,因此我可以将问题隔离到 .whereArrayContains() 查询。这是每个 Fragment 之间的唯一区别。

【问题讨论】:

    标签: java android firebase google-cloud-firestore firebaseui


    【解决方案1】:

    发生这种情况是因为当您在同一查询中使用 whereArrayContains()orderBy() 方法时,需要 index。要使用它,请转到您的 Firebase Console 并手动创建它,或者如果您使用的是 Android Studio,您会在 logcat 中找到一条听起来像这样的消息:

    W/Firestore:(0.6.6-dev)[Firestore]:侦听查询(数组 array_contains YourItem 按时间戳排序的产品)失败:状态{code=FAILED_PRECONDITION, description=查询需要索引。你可以在这里创建它:...

    您只需单击该链接或将网址复制并粘贴到网络浏览器中,您的索引就会自动创建。

    为什么需要这个索引?

    您可能已经注意到,Cloud Firestore 中的查询非常快,这是因为 Firestore 会自动为您在文档中的任何字段创建索引。当您需要订购商品时,需要按上述说明创建特定索引。但是,如果您打算手动创建索引,请同时从下拉列表中选择相应的Array contains 选项,如下图所示:

    【讨论】:

    • 感谢您的回答,您能否分享应用程序冷启动并且我们需要设置索引的任何其他指南
    猜你喜欢
    • 2011-07-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-01-24
    相关资源
    最近更新 更多