如何从Firebase含未知节点的数据库中取值并显示到RecyclerView?
Let's break down what's going on here and fix this step by step:
1. Understand the Core Issue
Your query is pointing directly to purchaseHistory/{userUid}, but if you used Firebase's push() method to add purchase records, each entry lives under a random, unique ID (the "unknown node") as a child of that user's UID. The FirebaseRecyclerAdapter needs to iterate over these child nodes—and luckily, Firebase handles this automatically if you target the correct parent reference.
2. Clean Up the setFirebaseRecyclerOptions Method
Your current method has redundant parameter passing. Let's simplify it, add null safety for the user, and ensure the query targets the right path:
public FirebaseRecyclerOptions<DataViewHistory> setFirebaseRecyclerOptions() { FirebaseUser user = mAuth.getCurrentUser(); // Guard against null user (always check this before accessing UID!) if (user == null) { // Return an empty options set if user isn't logged in return new FirebaseRecyclerOptions.Builder<DataViewHistory>() .setQuery(FirebaseDatabase.getInstance().getReference().child("dummy"), DataViewHistory.class) .build(); } // Target the user's purchaseHistory parent node // The adapter will automatically load all child nodes (the unknown push IDs) DatabaseReference userPurchasesRef = databaseReference.child("purchaseHistory").child(user.getUid()); return new FirebaseRecyclerOptions.Builder<DataViewHistory>() .setQuery(userPurchasesRef, DataViewHistory.class) .build(); }
3. Fix the Recycler Adapter Setup
Your adapter method also has redundant parameters, and there's a critical typo in onBindViewHolder (you're using dataViewCart instead of the passed dataViewHistory object). Let's fix that:
public void setFirebaseRecyclerAdapter() { this.firebaseRecyclerAdapter = new FirebaseRecyclerAdapter<DataViewHistory, ViewHolderHistory>(setFirebaseRecyclerOptions()) { @NonNull @Override public ViewHolderHistory onCreateViewHolder(@NonNull ViewGroup parent, int viewType) { View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.cartlist, parent, false); return new ViewHolderHistory(view); } @Override protected void onBindViewHolder(@NonNull ViewHolderHistory viewHolderHistory, int position, @NonNull DataViewHistory dataViewHistory) { // Fixed the typo: use the correct data object passed to the method viewHolderHistory.getTxtquantity().setText(String.valueOf(dataViewHistory.getQuantity())); // Add other view bindings here (e.g., product name, price, etc.) } }; }
4. Verify Your Data Model Matches Firebase
Make sure your DataViewHistory class has fields that exactly match the keys in your Firebase database. For example, if your database looks like this:
"purchaseHistory": { "user123Uid": { "randomPushId_abc": { "quantity": 2, "productName": "Wireless Headphones" }, "randomPushId_def": { "quantity": 1, "productName": "Phone Case" } } }
Your DataViewHistory class should look like this (with a default constructor required for Firebase deserialization):
public class DataViewHistory { private int quantity; private String productName; // Default constructor (mandatory for Firebase) public DataViewHistory() {} // Getters and setters public int getQuantity() { return quantity; } public void setQuantity(int quantity) { this.quantity = quantity; } public String getProductName() { return productName; } public void setProductName(String productName) { this.productName = productName; } }
5. Final Setup: Attach Adapter to RecyclerView
Don't forget to connect your adapter to the RecyclerView in your activity/fragment, and start listening for data changes:
// Initialize your RecyclerView RecyclerView purchaseHistoryRecycler = findViewById(R.id.your_recycler_view_id); purchaseHistoryRecycler.setLayoutManager(new LinearLayoutManager(this)); // Set up the adapter setFirebaseRecyclerAdapter(); purchaseHistoryRecycler.setAdapter(firebaseRecyclerAdapter); // Start listening for Firebase data updates firebaseRecyclerAdapter.startListening();
Key Takeaways
- Always check if
FirebaseUseris not null before accessinggetUid()to avoid null pointer exceptions. - The
FirebaseRecyclerAdapterautomatically iterates over all child nodes of the reference you pass tosetQuery—you don't need to explicitly reference the unknown push IDs. - Typos in
onBindViewHolderare easy to miss but will break your data display—double-check you're using the correct data object.
内容的提问来源于stack exchange,提问作者jumper

