是否可以在FirestoreRecyclerOptions中使用Algolia查询? [英] Is it possible to use Algolia query in FirestoreRecyclerOptions?

查看:42
本文介绍了是否可以在FirestoreRecyclerOptions中使用Algolia查询?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

为了允许我的用户执行更复杂的搜索,我正在与Algolia合作.

To allow my user performing more complex search, I'm working with Algolia.

com.algolia.search.saas.Query algolia_query =
                    new com.algolia.search.saas.Query(mLastQuery)
                    .setAttributesToRetrieve("content")
                    .setAttributesToRetrieve("category")
                    .setHitsPerPage(10);
            index.searchAsync(algolia_query, new CompletionHandler() {
                @Override
                public void requestCompleted(JSONObject jsonObject, AlgoliaException e) {
                    Log.d("algolia", jsonObject.toString());
                }
            });

我想将此jsonObject转换为与FirestoreRecyclerOptions兼容的东西,以便能够使用FirestoreRecyclerAdapter

I would like to convert this jsonObject into something compatible with FirestoreRecyclerOptions to be able to use FirestoreRecyclerAdapter

谢谢!

推荐答案

为了更好地理解,我将尝试通过一个示例进行解释.假设我们有一个FirebaseFirestore对象指向数据库的根引用,另一个CollectionReference对象指向一个名为products的集合.为此,我们可以使用以下两行代码:

For a better understanding, I'll try to explain this with an example. Let's assume we have a FirebaseFirestore object that points to the root reference of the database and a CollectionReference object that points to a collection named products. And for that we can use the following two lines of code:

FirebaseFirestore rootRef = FirebaseFirestore.getInstance();
CollectionReference productsRef = rootRef.collection("products");

让我们也假设我们有一个Cloud Firestore数据库,如下所示:

Let's aslo assume we have a Cloud Firestore database that looks like this:

Firestore-root
     |
     --- products
            |
            --- productIdOne
            |      |
            |      --- productName: "Milk"
            |
            --- productIdTwo
                   |
                   --- productName: "Soy Milk"
            |
            --- productIdThree
                   |
                   --- productName: "Bacon"

要实现此结构,请使用以下代码将这些产品以及相应的索引添加到数据库中:

To achieve this structure, let's add these products to the database and also the corresponding indexes, using the code below:

Map<String, Object> mapOne = new HashMap<>();
mapOne.put("productName", "Milk");
Map<String, Object> mapTwo = new HashMap<>();
mapTwo.put("productName", "Soy Milk");
Map<String, Object> mapThree = new HashMap<>();
mapThree.put("productName", "Bacon");

WriteBatch writeBatch = rootRef.batch();
writeBatch.set(productsRef.document(), mapOne);
writeBatch.set(productsRef.document(), mapTwo);
writeBatch.set(productsRef.document(), mapThree);
writeBatch.commit();

Client client = new Client(YourApplicationID, YourAPIKey);
Index index = client.getIndex("products");

List<JSONObject> productList = new ArrayList<>();
productList.add(new JSONObject(mapOne));
productList.add(new JSONObject(mapTwo));
productList.add(new JSONObject(mapThree));
index.addObjectsAsync(new JSONArray(productList), null);

我们还假设我们在out布局文件中有2个视图,分别是EditTextListView.

Let's also assume we have 2 views in out layout file, an EditText and a ListView.

EditText editText = findViewById(R.id.edit_text);
ListView listView = findViewById(R.id.list_view);

要在我们的ListView中实际显示这些产品,请使用以下代码:

To actually display those products in our ListView, let's use the following code:

productsRef.get()
        .addOnCompleteListener(new OnCompleteListener<QuerySnapshot>() {
            @Override
            public void onComplete(@NonNull Task<QuerySnapshot> task) {
                if (task.isSuccessful()) {
                    List<String> list = new ArrayList<>();
                    for (DocumentSnapshot document : task.getResult()) {
                        list.add(document.getString("productName"));
                    }
                    ArrayAdapter<String> arrayAdapter = new ArrayAdapter<String>(context, android.R.layout.simple_list_item_1, list);
                    listView.setAdapter(arrayAdapter);
                } else {
                    Log.d(TAG, "Error getting documents: ", task.getException());
                }
            }
        });

为了根据我们在EditText中键入的文本过滤产品,我们需要添加这样的TextChangedListener:

In order to filter the products according to the text that we type in our EditText, we need to add a TextChangedListener like this:

editText.addTextChangedListener(new TextWatcher() {
    @Override
    public void beforeTextChanged(CharSequence charSequence, int i, int i1, int i2) {}

    @Override
    public void onTextChanged(CharSequence charSequence, int i, int i1, int i2) {}

    @Override
    public void afterTextChanged(Editable editable) {
        Query query = new Query(editable.toString())
                .setAttributesToRetrieve("productName")
                .setHitsPerPage(50);
        index.searchAsync(query, new CompletionHandler() {
            @Override
            public void requestCompleted(JSONObject content, AlgoliaException error) {
                try {
                    JSONArray hits = content.getJSONArray("hits");
                    List<String> list = new ArrayList<>();
                    for (int i = 0; i < hits.length(); i++) {
                        JSONObject jsonObject = hits.getJSONObject(i);
                        String productName = jsonObject.getString("productName");
                        list.add(productName);
                    }
                    ArrayAdapter<String> arrayAdapter = new ArrayAdapter<String>(context, android.R.layout.simple_list_item_1, list);
                    listView.setAdapter(arrayAdapter);
                } catch (JSONException e) {
                    e.printStackTrace();
                }
            }
        });
    }
});

因此,为了使其正常工作,我们创建了一个新的适配器对象.这意味着对于我们在EditText中键入的每个字符,我们都会创建一个新的适配器,并使用来自数据库的结果填充该适配器.为了回答您的问题,为了实现您想要的目标,您不必更改JSONObject,您已经创建了一个新的查询对象,该对象应传递给在FirestoreRecyclerOptions上调用的setQuery()方法>对象.我只是给您提供了一个更简单的示例来了解流程.有关更多信息,我还建议您观看此 视频 .

So in order to make it work, we have created a new adapter object. This means that for every character that we type in the EditText, we create a new adapter and we populate this adapter with the results that are coming from the database. And to answer your question, in order to achieve what you want, you don't have to change the JSONObject, you have create a new query object that should be passed to the setQuery() method that is called on the FirestoreRecyclerOptions object. I just gave you a simpler example to understand the flow. For more information, I also recommend you see this video.

这篇关于是否可以在FirestoreRecyclerOptions中使用Algolia查询?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆