0

Need to Do:
Basically i want Firestore => collection "order" => docs having customerid and productid on each doc => onSuccess => add to OrderPOJOList => call getCustomerName() then getProductName() => get Names in order => add to respective ArrayList => in end combine all data from three arraylist (OrderPOJOList, CustomerName, ProductName) to CurrentOrderPOJOList => set to Adapter.

Problem: the two listeners in getCustomerName() & getProductName() runs asynchronously and adds Name to arrayList randomly... all i want is to show data on Adapter in order but sometimes names get exchange on list due to listners running asynchronously.

What should i do to get my customer and product names from firestore in sequence to display?

public class CurrentOrders extends AppCompatActivity {
    private List<CurrentOrdersPOJO> currentOrdersPOJOList;
    private List<OrderPOJO> orderPOJOList;
    private FirebaseFirestore firebaseFirestore;
    private String DocId, Area, cname, pname;
    private OrderPOJO orderPOJO;
    private CurrentOrdersPOJO currentOrdersPOJO;
    private int count = -1, count1 = -1, i;
    private RecyclerView recyclerView;
    private List<String> customerName, productName;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_current_orders);

        //Current User Unique ID
        DocId = getIntent().getStringExtra("DocumentId");
        Area = getIntent().getStringExtra("Area");
        Log.w("ReachedCurrentOrders", "Doc Id: " + DocId + "\nArea: " + Area);

        currentOrdersPOJOList = new ArrayList<>();
        customerName = new ArrayList<String>();
        productName = new ArrayList<String>();
        orderPOJOList = new ArrayList<>();

        recyclerView = findViewById(R.id.activity_current_order_recyclerView);
        firebaseFirestore = FirebaseFirestore.getInstance();

        recyclerView.setLayoutManager(new LinearLayoutManager(this, LinearLayoutManager.VERTICAL, false));
        recyclerView.addItemDecoration(new DividerItemDecoration(this, LinearLayoutManager.VERTICAL));

        firebaseFirestore.collection("order")
                .whereEqualTo("area", Area)
                .whereEqualTo("status", "active")
                .get()
                .addOnSuccessListener(new OnSuccessListener<QuerySnapshot>() {
                    @Override
                    public void onSuccess(final QuerySnapshot queryDocumentSnapshots) {
                        if (!queryDocumentSnapshots.isEmpty()) {

                            for (final QueryDocumentSnapshot queryDocumentSnapshot : queryDocumentSnapshots) {
                                count++;
                            }

                            for (final QueryDocumentSnapshot queryDocumentSnapshot : queryDocumentSnapshots) {

                                orderPOJO = queryDocumentSnapshot.toObject(OrderPOJO.class);
                                orderPOJOList.add(orderPOJO);

                                Log.d("Tagging", "The Customer UID: " + orderPOJO.getC_uid() + "\nThe Product Doc ID: " + orderPOJO.getP_docid());

                                count1++;

                                if (count == count1) {
                                    getCustomerName();
                                }

                            }//endof for loop

                        } else {
                            Toast.makeText(CurrentOrders.this, "No Orders in Your Area", Toast.LENGTH_SHORT).show();
                            Log.d("CurrentOrder", "Exception Here");
                        }

                    }

                });
    }//endofOnCreate

    public void getCustomerName() {
        count1 = -1;
        //Getting Customer Name from ID
        for (i = 0; i <= count; i++) {
            firebaseFirestore.collection("customer").document(orderPOJOList.get(i).getC_uid()).get().addOnSuccessListener(new OnSuccessListener<DocumentSnapshot>() {
                @Override
                public void onSuccess(DocumentSnapshot documentSnapshot) {
                    if (documentSnapshot.exists()) {

                        cname = documentSnapshot.getString("name");
                        customerName.add(cname);

                        count1++;

                        if (count1 == count) {
                            getProductName();
                        }

                    } else {
                        Log.d("CurrentOrders", "Exception Here" + documentSnapshot.exists());
                    }
                }
            });
        }
    }//end of function

    public void getProductName() {
        count1 = -1;
        //Product Getting Name
        for (i = 0; i <= count; i++) {
            firebaseFirestore.collection("product").document(orderPOJOList.get(i).getP_docid()).get().addOnSuccessListener(new OnSuccessListener<DocumentSnapshot>() {
                @Override
                public void onSuccess(DocumentSnapshot documentSnapshot) {
                    if (documentSnapshot.exists()) {
                        pname = documentSnapshot.getString("name");
                        productName.add(pname);

                        count1++;

                        if (count1 == count) {
                            callAdapter();
                        }
                    } else {
                        Log.d("CurrentOrders", "Exception Here" + documentSnapshot.exists());
                    }
                }

            });
        }
    }//endofFunction

    public void callAdapter() {
        for (int i = 0; i <= count; i++) {

            currentOrdersPOJO = new CurrentOrdersPOJO(customerName.get(i), orderPOJOList.get(i).getComplete_address(),
                    productName.get(i), orderPOJOList.get(i).getQuantity(), orderPOJOList.get(i).getStatus(), orderPOJOList.get(i).getArea(), orderPOJOList.get(i).getO_date());

            currentOrdersPOJOList.add(currentOrdersPOJO);
        }
        recyclerView.setAdapter(new CurrentOrdersAdapter(currentOrdersPOJOList, CurrentOrders.this));
    }//endofFunction

}//endofclass

[screenshot of an activity showing list that varies everytime][1]

  [1]: https://i.stack.imgur.com/X48JF.jpg
bhusak
  • 1,320
  • 1
  • 9
  • 19
Anas Yousuf
  • 423
  • 1
  • 6
  • 17

2 Answers2

1

A similar question has been asked on another thread, it seems that you can synchronously return data because the method itself is a task, you could try to use the Taks.await(task) method to wait for the operation to end maybe that's the answer you're looking for.

Ricardo
  • 166
  • 1
  • 4
  • **java.lang.IllegalStateException: Must not be called on the main application thread** This is what i get if i use Tasks.await(task) @Ricardo – Anas Yousuf Oct 22 '19 at 14:21
0

I Have solved this problem by using mentioned solution by @Ricardo above AND combining the solution with using Asynctask(Background Thread) as it was first giving IllegalStateException because of calling Tasks.await(task) on Main UI Thread.

So, Use: Tasks.await(task) on Aysnctask(Background Thread)

Anas Yousuf
  • 423
  • 1
  • 6
  • 17