如何从具有嵌套数组和对象结构的firebase数据库中检索数据?

时间:2017-05-31 12:59:22

标签: android json firebase firebase-realtime-database

我尝试了很多地方的数据提取代码,但我到处都知道如何在一个简单的列表中检索数据。由于我的JSON结构很复杂,我现在无法更改它,所以请帮我从firebase数据库中检索数据。 请帮忙,因为我无法理解Firebase代码 。以下是我的代码和JSON数据库: enter image description here

CategoryModel.xml

package com.example.firedb;

import android.os.Parcel;
import android.os.Parcelable;

import java.util.ArrayList;

/**
 * Created by Android on 5/31/2017.
 */

public class CategoryModel {

    private ArrayList<CategoryList> categoryList;

    public CategoryModel() {
    }

    public CategoryModel(ArrayList<CategoryList> categoryList) {
        this.categoryList = categoryList;
    }

    public ArrayList<CategoryList> getCategoryList() {
        return categoryList;
    }

    public void setCategoryList(ArrayList<CategoryList> categoryList) {
        this.categoryList = categoryList;
    }


    // CategoryList

    public  static class CategoryList {

        public int Category_id;
        public String Category_name;
        public ArrayList<String>Emails;
        public ArrayList<String>Epabx;
        public ArrayList<String>Category_Fax;
        public ArrayList<Persons> persons;

        public CategoryList() {
        }
        //constructor of CategoryList

        public CategoryList(int category_id, String category_name,
                            ArrayList<String> emails, ArrayList<String> epabx, ArrayList<String> category_Fax,
                            ArrayList<Persons> persons) {
            Category_id = category_id;
            Category_name = category_name;
            Emails = emails;
            Epabx = epabx;
            Category_Fax = category_Fax;
            this.persons = persons;
        }

        // getters and setters of CategoryList

        public int getCategory_id() {
            return Category_id;
        }

        public void setCategory_id(int category_id) {
            Category_id = category_id;
        }

        public String getCategory_name() {
            return Category_name;
        }

        public void setCategory_name(String category_name) {
            Category_name = category_name;
        }

        public ArrayList<String> getEmails() {
            return Emails;
        }

        public void setEmails(ArrayList<String> emails) {
            Emails = emails;
        }

        public ArrayList<String> getEpabx() {
            return Epabx;
        }

        public void setEpabx(ArrayList<String> epabx) {
            Epabx = epabx;
        }

        public ArrayList<String> getCategory_Fax() {
            return Category_Fax;
        }

        public void setCategory_Fax(ArrayList<String> category_Fax) {
            Category_Fax = category_Fax;
        }

        public ArrayList<Persons> getPersons() {
            return persons;
        }

        public void setPersons(ArrayList<Persons> persons) {
            this.persons = persons;
        }


    }

    //Persons

    public static class Persons {

        private int Person_ID;
        private String Name;
        private String Designation;
        private ArrayList<String> Office_Phone;
        private ArrayList<String> Residence_Phone;
        private String VOIP;
        private String Address;
        private ArrayList<String>Fax;
        private String Ext;
        private ArrayList<String>Extra_info;
        private String Category_name;

        public Persons() {
        }

        // Constructor of Persons
        public Persons(int person_ID, String name, String designation, ArrayList<String> office_Phone,
                       ArrayList<String> residence_Phone, String VOIP, String address, ArrayList<String> fax, String ext,
                       ArrayList<String>extra_info, String category_name) {
            Person_ID = person_ID;
            Name = name;
            Designation = designation;
            Office_Phone = office_Phone;
            Residence_Phone = residence_Phone;
            this.VOIP = VOIP;
            Address = address;
            Fax = fax;
            Ext = ext;
            Extra_info=extra_info;
            Category_name=category_name;
        }

        // Getter and Setters of Persons

        public int getPerson_ID() {
            return Person_ID;
        }

        public void setPerson_ID(int person_ID) {
            Person_ID = person_ID;
        }

        public String getName() {
            return Name;
        }

        public void setName(String name) {
            Name = name;
        }

        public String getDesignation() {
            return Designation;
        }

        public void setDesignation(String designation) {
            Designation = designation;
        }

        public ArrayList<String> getOffice_Phone() {
            return Office_Phone;
        }

        public void setOffice_Phone(ArrayList<String> office_Phone) {
            Office_Phone = office_Phone;
        }

        public ArrayList<String> getResidence_Phone() {
            return Residence_Phone;
        }

        public void setResidence_Phone(ArrayList<String> residence_Phone) {
            Residence_Phone = residence_Phone;
        }

        public String getVOIP() {
            return VOIP;
        }

        public void setVOIP(String VOIP) {
            this.VOIP = VOIP;
        }

        public String getAddress() {
            return Address;
        }

        public void setAddress(String address) {
            Address = address;
        }

        public ArrayList<String> getFax() {
            return Fax;
        }

        public void setFax(ArrayList<String> fax) {
            Fax = fax;
        }

        public String getExt() {
            return Ext;
        }

        public void setExt(String ext) {
            Ext = ext;
        }

        public ArrayList<String> getExtra_info() {
            return Extra_info;
        }

        public void setExtra_info(ArrayList<String> extra_info) {
            Extra_info = extra_info;
        }

        public String getCategory_name() {
            return Category_name;
        }

        public void setCategory_name(String category_name) {
            Category_name = category_name;
        }

    }

}

CardviewActivity: 之前我使用过资产文件,但现在我想从firebase获取数据,其代码在线模糊不清

package com.example.firedb;

import android.content.Intent;
import android.graphics.Color;
import android.graphics.drawable.Drawable;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.support.v7.widget.Toolbar;
import android.text.Editable;
import android.text.LoginFilter;
import android.text.TextWatcher;
import android.util.Log;
import android.view.Gravity;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.RelativeLayout;
import android.widget.TextView;

import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;

import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;

import static android.R.attr.button;


public class CardViewActivity extends AppCompatActivity {
    Toolbar mActionBarToolbar;
    private RecyclerView mainRecyclerView;
    private RecyclerView.Adapter mainAdapter;
    private RecyclerView.LayoutManager mainLayoutManager;
    private static String LOG_TAG = "CardViewActivity";
    EditText inputSearchMain;
    private ArrayList<CategoryModel.CategoryList> categoryLists;
    TextView toolbar_title_main;
    ImageView back_cardviewActivity;
//    DatabaseHandler db;

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

//         db = new DatabaseHandler (CardViewActivity.this);

        mActionBarToolbar = (Toolbar) findViewById(R.id.tool_bar);
        toolbar_title_main=(TextView)findViewById(R.id.toolbar_title);


//        mActionBarToolbar.setTitle("Hry. Govt. Telephone Directory");
       // mActionBarToolbar.setLogo(R.drawable.logotoolbar);

//        mActionBarToolbar.setTitleMargin(5,2,2,2);
        setSupportActionBar(mActionBarToolbar);
        getSupportActionBar().setDisplayShowTitleEnabled(false);
        toolbar_title_main.setText("Hry. Govt. Telephone Directory");
        back_cardviewActivity=(ImageView)findViewById(R.id.back);
        back_cardviewActivity.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                onBackPressed();
            }
        });

        categoryLists=new ArrayList<CategoryModel.CategoryList>();
        categoryLists.addAll(getmcategoryset());
        mainRecyclerView=(RecyclerView)findViewById(R.id.recyclerView_Main);
        mainRecyclerView.setHasFixedSize(true);
        mainLayoutManager=new LinearLayoutManager(this);
        mainRecyclerView.setLayoutManager(mainLayoutManager);
//        Log.d( "onCreate: ", "List Size: "+categoryLists.size());
        mainAdapter=new RecyclerViewAdapterMain(getmcategoryset());
        mainRecyclerView.setAdapter(mainAdapter);
        inputSearchMain = (EditText) findViewById(R.id.inputSearchMain);

        addTextListener();
    }

    public void addTextListener(){

        inputSearchMain.addTextChangedListener(new TextWatcher() {

            public void afterTextChanged(Editable s) {}

            public void beforeTextChanged(CharSequence s, int start, int count, int after) {}

            public void onTextChanged(CharSequence query, int start, int before, int count) {

                query = query.toString().toLowerCase();

                final ArrayList<CategoryModel.CategoryList> filteredList = new ArrayList<CategoryModel.CategoryList>();

                for (int i = 0; i < categoryLists.size(); i++) {

                    final String text = categoryLists.get(i).getCategory_name().toLowerCase();
                    if (text.contains(query)) {

                        filteredList.add(categoryLists.get(i));
                    }
                }

                mainRecyclerView.setLayoutManager(new LinearLayoutManager(CardViewActivity.this));
                mainAdapter = new RecyclerViewAdapterMain(filteredList);
                mainRecyclerView.setAdapter(mainAdapter);
                mainAdapter.notifyDataSetChanged();  // data set changed
            }
        });
    }

    private ArrayList<CategoryModel.CategoryList> getmcategoryset() {
//        JSONObject obj = new JSONObject(readJSONFromAsset());

        try {

            ArrayList<CategoryModel.CategoryList>categoryList = new ArrayList<CategoryModel.CategoryList>();
            JSONObject jsonObject = new JSONObject(readJSONFromAsset());

            JSONArray categoryArray = jsonObject.getJSONArray("Category");
            Log.d("getmcategoryset", "category count: "+categoryArray.length());
            for (int i = 0; i < categoryArray.length(); i++)
            {
                JSONObject job = categoryArray.getJSONObject(i);

                int categoryId = job.getInt("Category_id");
                String categoryName = job.getString("Category_name");

                //this is for email array
                ArrayList<String> emails = new ArrayList<>();
                JSONArray emailArray = job.getJSONArray("Emails");
                for (int j = 0; j< emailArray.length(); j++){
//                    JSONObject jobE = emailArray.getString(j);
                    emails.add(emailArray.getString(j));
                }

                //This i for Epabx array
                ArrayList<String> epabx = new ArrayList<>();
                JSONArray epabxArray = job.getJSONArray("Epabx");
                for (int j = 0; j < epabxArray.length(); j++){
//                    JSONObject jobE = epabxArray.getString(j);
                    epabx.add(epabxArray.getString(j));
                }

                //This i for Category_Fax array
                ArrayList<String> category_Fax = new ArrayList<>();
                JSONArray category_FaxJson = job.getJSONArray("Category_Fax");
                for (int j = 0; j < category_FaxJson.length(); j++){
//                    JSONObject jobE = category_FaxJson.getString(j);
                    category_Fax.add(category_FaxJson.getString(j));
                }

                //This i for Persons array
                ArrayList<CategoryModel.Persons> personsList = new ArrayList<>();
                JSONArray personsArray = job.getJSONArray("Persons");
                for (int j = 0; j < personsArray.length(); j++){
                    JSONObject jobIn = personsArray.getJSONObject(j);

                    int Person_ID = jobIn.getInt("Person_ID");
                    String Name = jobIn.getString("Name");
                    String Designation = jobIn.getString("Designation");

                    //this is for Office_Phone array
                    ArrayList<String>Office_Phone = new ArrayList<>();
                    JSONArray office_Phone = jobIn.getJSONArray("Office_Phone");
                    for (int k=0; k < office_Phone.length(); k++)
                    {
                        Office_Phone.add(office_Phone.getString(k));
                    }

                    //this is for Residence_Phone array
                    ArrayList<String>Residence_Phone = new ArrayList<>();
                    JSONArray residence_Phone = jobIn.getJSONArray("Residence_Phone");
                    for (int k=0; k < residence_Phone.length(); k++)
                    {
                        Residence_Phone.add(residence_Phone.getString(k));
                    }

                    String VOIP = jobIn.getString("VOIP");
                    String Address = jobIn.getString("Address");


                    //this is for Fax array
                    ArrayList<String>Fax = new ArrayList<>();
                    JSONArray fax = jobIn.getJSONArray("Fax");
                    for (int k=0; k < fax.length(); k++)
                    {
                        Fax.add(fax.getString(k));
                    }

                    String Ext = jobIn.getString("Ext");

                    //this is for Extra_info array
                    ArrayList<String>Extra_info = new ArrayList<>();
                    JSONArray extra_info = jobIn.getJSONArray("Extra_info");
                    for (int k=0; k < extra_info.length(); k++)
                    {
                        Extra_info.add(extra_info.getString(k));
                    }

                    personsList.add(new CategoryModel.Persons(Person_ID, Name, Designation, Office_Phone, Residence_Phone,
                            VOIP, Address, Fax, Ext,Extra_info,categoryName));
//                    db.addPerson(new CategoryModel.Persons(Person_ID, Name, Designation, Office_Phone, Residence_Phone,
//                            VOIP, Address, Fax, Ext,Extra_info));
                }

                //here your Category[] value store in categoryArrayList
                categoryList.add(new CategoryModel.CategoryList(categoryId, categoryName, emails, epabx, category_Fax, personsList));

//                db.addCategory(new CategoryModel.CategoryList(categoryId, categoryName, emails, epabx, category_Fax, personsList));

                Log.i("categoryList size = ", ""+categoryArray.length());
                Log.i("cat_name=",""+categoryName);
            }

            if (categoryList != null)
            {
                Log.i("categoryList size = ", ""+categoryArray.length());
            }
            return categoryList;
        } catch (JSONException e) {
            e.printStackTrace();
            return null;
        }

    }

    @Override
    protected void onResume() {
        super.onResume();
//        ((RecyclerViewAdapterMain) mainAdapter).setOnItemClickListener(new RecyclerViewAdapterMain()
//                .CategoryClickListener() {
//            public void onItemClick(int position, View v) {
//                Log.i(LOG_TAG, " Clicked on Item " + position);
//            }
//        });
    }


}

RecyclerViewAdapter:

package com.example.firedb;

import android.content.Context;
import android.content.Intent;
import android.os.Bundle;
import android.support.v7.widget.RecyclerView;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.TextView;

import java.util.ArrayList;
import java.util.Arrays;


public class RecyclerViewAdapterMain extends RecyclerView.Adapter<RecyclerViewAdapterMain.CategoryObjectHolder> {
    private static String LOG_TAG = "categoryRecyclrVwAdptr";
    private  ArrayList<CategoryModel.CategoryList> mcategoryset;
    private static CategoryClickListener categoryClickListener;

    public static class CategoryObjectHolder extends RecyclerView.ViewHolder  {
        TextView category_name;
        /*TextView category_emails;
        TextView category_epabx;
        TextView category_fax;*/

        public CategoryObjectHolder(View itemView){
            super(itemView);
            category_name=(TextView)itemView.findViewById(R.id.category_name);
            /*category_emails=(TextView)itemView.findViewById(R.id.category_emails);
            category_epabx=(TextView)itemView.findViewById(R.id.category_epabx);
            category_fax=(TextView)itemView.findViewById(R.id.category_fax);*/
            Log.i(LOG_TAG, "Adding Listener");

        }
//        @Override
//        public void onClick(View v) {
//            categoryClickListener.onItemClick(getAdapterPosition(), v);
//        }
    }
//    public void setOnItemClickListener(CategoryClickListener categoryClickListener) {
//        this.categoryClickListener = categoryClickListener;
//    }

    public RecyclerViewAdapterMain(ArrayList<CategoryModel.CategoryList> myDataset) {
        mcategoryset = myDataset;
    }

    public CategoryObjectHolder onCreateViewHolder(ViewGroup parent,int viewType){
        View view= LayoutInflater.from(parent.getContext()).inflate(R.layout.card_view_row_main_activity,parent,false);
        CategoryObjectHolder categoryObjectHolder=new CategoryObjectHolder(view);
        return categoryObjectHolder;
    }

    @Override
    public void onBindViewHolder(CategoryObjectHolder holder, final int position) {
        /*final StringBuilder stringBuilder_emails = new StringBuilder();
        for (String email : mcategoryset.get(position).getEmails()) {
            if (!stringBuilder_emails.toString().isEmpty()) {
                stringBuilder_emails.append(", ");
            }
            stringBuilder_emails.append(email);
        }

        final StringBuilder stringBuilder_Epabx = new StringBuilder();
        for (String epabx : mcategoryset.get(position).getEpabx()) {
            if (!stringBuilder_Epabx.toString().isEmpty()) {
                stringBuilder_Epabx.append(", ");
            }
            stringBuilder_Epabx.append(epabx);
        }

        final StringBuilder stringBuilder_Category_Fax = new StringBuilder();
        for (String category_Fax : mcategoryset.get(position).getCategory_Fax()) {
            if (!stringBuilder_Category_Fax.toString().isEmpty()) {
                stringBuilder_Category_Fax.append(", ");
            }
            stringBuilder_Category_Fax.append(category_Fax);
        }*/

        holder.category_name.setText(mcategoryset.get(position).getCategory_name());
        /*holder.category_emails.setText(stringBuilder_emails.toString());
        holder.category_epabx.setText(stringBuilder_Epabx.toString());
        holder.category_fax.setText(stringBuilder_Category_Fax.toString());*/
        holder.itemView.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {

                Intent i = new Intent (v.getContext(), PeopleListActivity.class);
                i.putParcelableArrayListExtra("Persons",mcategoryset.get(position).getPersons());
                i.putStringArrayListExtra("emails",mcategoryset.get(position).getEmails());
                //i.putExtras(b);
                v.getContext().startActivity(i);

            }
        });
    }
    public void addItem(CategoryModel.CategoryList dataObj, int index) {
        mcategoryset.add(index, dataObj);
        notifyItemInserted(index);
    }

    public void deleteItem(int index) {
        mcategoryset.remove(index);
        notifyItemRemoved(index);
    }

    @Override
    public int getItemCount() {
        return mcategoryset.size();
    }

    public interface CategoryClickListener {
        public void onItemClick(int position, View v);
    }
}

2 个答案:

答案 0 :(得分:5)

从Firebase数据库获取数据的唯一方法是使用ValueEventListener。 Firebase使用异步调用,因此您无法调用该函数,获取数据并使用它。您必须在特定的数据库引用中设置ValueEventListener。

对于您的实际问题,您必须创建一个数组,设置Firebase参考,添加ValueEventListener并在内部添加ClassList中每次出现的CategoryList。最后,仍然在ValueEventListener内部,您可以使用CategoryList的数组作为参数创建CategoryModel,并更新您的UI,以查看CategoryModel中的数据:

CategoryModel categoryModel;
ArrayList<CategoryList> array = new ArrayList<>();
FirebaseDatabase database = FirebaseDatabase.getInstance();
DatabaseReference categoryRef = database.getReference("Category");
categoryRef.addValueEventListener(new ValueEventListener() {
    @Override
    public void onDataChange(DataSnapshot dataSnapshot) {
        // This method is called once with the initial value and again
        // whenever data at this location is updated.
        for (DataSnapshot childSnapshot: dataSnapshot.getChildren()) {
            CategoryList categoryList = childSnapshot.getValue(CategoryList.class);
            array.add(categoryList);
        }
        categoryModel = new CategoryModel(array);
        // Method to show the data in category model, 
        // usually populating an ListView or something
        updateUI()
    }

    @Override
    public void onCancelled(DatabaseError error) {
        // Failed to read value
        Log.w(TAG, "Failed to read value.", error.toException());
    }
});

为了使这个工作,你的CategoryList类必须实现他的成员的所有setter所以“datasnapshot.getValue()”工作。 另一种方法是,在CategoryList中创建一个以这种方式重新接收DataSnapshot的构造函数:

public CategoryList(DataSnapshot snapshot){
    Category_id = snapshot.child("Category_id").getValue(int.class);
    Category_name = snapshot.child("Category_name").getValue(String.class);
    GenericTypeIndicator<List<String>> stringList = new GenericTypeIndicator<List<String>>() {};
    Emails = snapshot.child("Emails").getValue(stringList);
    Epabx= snapshot.child("Epabx").getValue(stringList);
    Category_Fax= snapshot.child("Category_Fax").getValue(stringList);
    GenericTypeIndicator<List<Persons>> personsList = new GenericTypeIndicator<List<Persons>>() {};
    persons = snapshot.child("Persons").getValue(personsList);
}

如果您创建构造函数,则必须替换此行:

CategoryList categoryList = childSnapshot.getValue(CategoryList.class);

用这个:

CategoryList categoryList = new CategoryList(childSnapshot);

您可以看到我使用GenericTypeIndicator处理数据集合,这是一个帮助类,可以让Firebase使用列表,地图,集合或其他集合。

答案 1 :(得分:1)

只是推荐!这不是一个好的数据结构,您应该对数据进行非规范化。然后您可以通过ChildEventListenerValueEventListener观察数据。

例如:

-Category
--CategoryId
---CategoryList
---Persons
----user1: true
----user2: true, etc.

-Users
--user1Id
---user1details
--user2Id
---user2details, etc.

以下是一些有关非规范化数据的有用链接

Link1Link2