有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

java如何正确地从Firebase中提取数据?

Firebase非常新,但用于大型项目

我刚刚完成了我的登录活动,我正在尝试从我的Firebase中提取(字符串)用户名和(长)分数。我需要更新数据并使其不为空

请,我需要有关MainActivity.class的逻辑/应用程序的帮助,它通过(字符串)电子邮件和(字符串)authID以及Firebase API传递。我已经做了研究,但我已经到了一个地步,我不知道我做错了什么。在我看来一切都很好。请帮忙

提前谢谢你

我的Firebase数据如下(我认为):

{
HOME:{
user_accts:{
          $uid:{
              score:{(Long) num}
              userName:{(String) email}
          }
}
}//end of JSON unit

下面是我的UserAccount类:

package com.frankbrenyahapps.maphunt;

public class UserAccount {

    // private String firstName = null;
    // private String lastName = null;
    private String userName = null;
    private long score = 0;

    public UserAccount() {}

    public UserAccount(String userName, Long score) {
        // this.firstName = firstName;
        // this.lastName = lastName;
        this.userName = userName;
        this.score = score;
    }

    public long getScore() {
        return this.score;
    }

    public String getUserName() {
        return userName;
    }
}//end of class

以下是本课程的全部内容:

public class MainActivity extends AppCompatActivity implements NavigationView.OnNavigationItemSelectedListener {

    public static final String FIREBASE_TO_HOME = "https:..";

    public static final String FIREBASE_TO_HOME_TO_USERACCTS = "https:...";

    private static final String FIREBASE_USER_AUTHID = "FIREBASE-AUTH-UID";

    private static final String FIREBASE_USER_EMAIL = "FIREBASE-AUTH-EMAIL";

    private static final String USER_PREF_AUTH = "USER-AUTH";

    private static final String USER_PREF_SCORE = "USER-SCORE";

    Firebase homeRef;
    Firebase userRef;

    private String userAuthUid;
    private String userEmail;
    private Long userScore;

    SharedPreferences bountyHuntPrefs;
    SharedPreferences.Editor prefEditor;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main_nav_drawer);
        Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
        setSupportActionBar(toolbar);
        homeRef = new Firebase(FIREBASE_TO_HOME);
        bountyHuntPrefs = getPreferences(MODE_PRIVATE);
        prefEditor = bountyHuntPrefs.edit();

        TextView emailTextView = (TextView) findViewById(R.id.emailTextView);
        TextView scoreTextView = (TextView) findViewById(R.id.scoreTextView);
        Button resetPass = (Button) findViewById(R.id.button_resetPass);

        DrawerLayout drawer = (DrawerLayout) findViewById(R.id.drawer_layout);
        ActionBarDrawerToggle toggle = new ActionBarDrawerToggle(
            this, drawer, toolbar, R.string.navigation_drawer_open, R.string.navigation_drawer_close);
        drawer.setDrawerListener(toggle);
        toggle.syncState();

        NavigationView navigationView = (NavigationView) findViewById(R.id.nav_view);
        navigationView.setNavigationItemSelectedListener(this);

        // add user to homeDB
        // update the users account
        // User passed auth, get them in
        userEmail = getIntent().getStringExtra(FIREBASE_USER_EMAIL);
        userAuthUid = getIntent().getStringExtra(FIREBASE_USER_AUTHID);
        if (userAuthUid!=null) {
            prefEditor.putString(USER_PREF_AUTH, userAuthUid).apply();
            userAuthUid = null;
        }

        getUserDataFromMemory();
        // TODO: Set user info into UI elements
        emailTextView.setText(userEmail);
    scoreTextView.setText(String.valueOf(userScore));//Long.toString(userScore)
        resetPass.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                AlertDialog.Builder builder = new AlertDialog.Builder(MainActivity.this);
                builder.setTitle("Reset Password?")
                    .setMessage("Are you sure you want to reset your password?")
                    .setPositiveButton("Reset", new DialogInterface.OnClickListener() {
                        @Override
                        public void onClick(DialogInterface dialog, int which) {
                            homeRef.resetPassword(userEmail, new Firebase.ResultHandler() {
                                @Override
                                public void onSuccess() {
                                    Toast.makeText(MainActivity.this, "Request Sent", Toast.LENGTH_LONG).show();
                                }

                                @Override
                                public void onError(FirebaseError firebaseError) {
                                    Toast.makeText(MainActivity.this, "Error, could not reset", Toast.LENGTH_LONG).show();
                                }
                            });
                        }
                    })
                    .setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
                        @Override
                        public void onClick(DialogInterface dialog, int which) {
                            // dismiss
                        }
                    })
                    .create()
                    .show();
            }
        });

    }

    @Override
    public void onBackPressed() {
        ...
    }

    @SuppressWarnings("StatementWithEmptyBody")
    @Override
    public boolean onNavigationItemSelected(MenuItem item) {
        // Handle navigation view item clicks here.
        ...
    }

    private void getUserDataFromMemory() {

        userScore = bountyHuntPrefs.getLong(USER_PREF_SCORE, 0);

        userRef = new Firebase(FIREBASE_TO_HOME_TO_USERACCTS).child(bountyHuntPrefs.getString(USER_PREF_AUTH, ""));
        userRef.addListenerForSingleValueEvent(new ValueEventListener() {
            @Override
            public void onDataChange(DataSnapshot dataSnapshot) {
                for(DataSnapshot userSnapShot: dataSnapshot.getChildren()){
                    UserAccount user = userSnapShot.getValue(UserAccount.class);
                    userEmail = user.getUserName();
                    if (userScore == 0)
                        userScore = user.getScore();
                    prefEditor.putLong(USER_PREF_SCORE, userScore).apply();
                }
            }

            @Override
            public void onCancelled(FirebaseError firebaseError) {
                Toast.makeText(MainActivity.this, "Invalid Authentication", Toast.LENGTH_LONG).show();
                homeRef.unauth();
                homeRef = null;
                finish();
            }
        });
        UserAccount user = new UserAccount(userEmail, userScore);
        userRef.setValue(user);
    }

    @Override
    protected void onStop() {
        // Log user out and kill activity
        super.onStop();
        homeRef.unauth();
    }

    @Override
    protected void onResume() {
        super.onResume();
        userAuthUid = getPreferences(MODE_PRIVATE).getString(USER_PREF_AUTH, userAuthUid);
    }
}//end of class

LOGCAT错误:

11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     FATAL EXCEPTION: main
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime: Process: com.frankbrenyahapps.maphunt, PID: 4796
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime: com.firebase.client.FirebaseException: Failed to bounce to type
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.firebase.client.DataSnapshot.getValue(DataSnapshot.java:185)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.frankbrenyahapps.maphunt.MainActivity$2.onDataChange(MainActivity.java:219)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.firebase.client.Query$1.onDataChange(Query.java:158)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.firebase.client.core.ValueEventRegistration.fireEvent(ValueEventRegistration.java:45)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.firebase.client.core.view.DataEvent.fire(DataEvent.java:45)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.firebase.client.core.view.EventRaiser$1.run(EventRaiser.java:38)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at 安卓.os.Handler.handleCallback(Handler.java:739)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at 安卓.os.Handler.dispatchMessage(Handler.java:95)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at 安卓.os.Looper.loop(Looper.java:135)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at 安卓.app.ActivityThread.main(ActivityThread.java:5221)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at java.lang.reflect.Method.invoke(Native Method)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at java.lang.reflect.Method.invoke(Method.java:372)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.安卓.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:899)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.安卓.internal.os.ZygoteInit.main(ZygoteInit.java:694)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:  Caused by: com.fasterxml.jackson.databind.JsonMappingException: Can not instantiate value of type [simple type, class com.frankbrenyahapps.maphunt.UserAccount] from Integral number; no single-int-arg constructor/factory method
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.fasterxml.jackson.databind.deser.std.StdValueInstantiator.createFromInt(StdValueInstantiator.java:320)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.fasterxml.jackson.databind.deser.BeanDeserializerBase.deserializeFromNumber(BeanDeserializerBase.java:1012)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.fasterxml.jackson.databind.deser.BeanDeserializer._deserializeOther(BeanDeserializer.java:138)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserialize(BeanDeserializer.java:123)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.fasterxml.jackson.databind.ObjectMapper._readMapAndClose(ObjectMapper.java:2888)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.fasterxml.jackson.databind.ObjectMapper.readValue(ObjectMapper.java:2034)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.firebase.client.DataSnapshot.getValue(DataSnapshot.java:183)
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.frankbrenyahapps.maphunt.MainActivity$2.onDataChange(MainActivity.java:219) 
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.firebase.client.Query$1.onDataChange(Query.java:158) 
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.firebase.client.core.ValueEventRegistration.fireEvent(ValueEventRegistration.java:45) 
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.firebase.client.core.view.DataEvent.fire(DataEvent.java:45) 
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.firebase.client.core.view.EventRaiser$1.run(EventRaiser.java:38) 
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at 安卓.os.Handler.handleCallback(Handler.java:739) 
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at 安卓.os.Handler.dispatchMessage(Handler.java:95) 
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at 安卓.os.Looper.loop(Looper.java:135) 
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at 安卓.app.ActivityThread.main(ActivityThread.java:5221) 
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at java.lang.reflect.Method.invoke(Native Method) 
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at java.lang.reflect.Method.invoke(Method.java:372) 
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.安卓.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:899) 
11-16 20:59:43.445 4796-4796/com.frankbrenyahapps.maphunt E/AndroidRuntime:     at com.安卓.internal.os.ZygoteInit.main(ZygoteInit.java:694)

共 (1) 个答案

  1. # 1 楼答案

    你似乎只在读一个用户,但却试图在孩子们身上循环。这意味着userSnapShot.getValue(UserAccount.class)将在userNamescore属性上被调用,这些属性本身不是UserAccount对象

    解决方案是移除循环:

    userRef = new Firebase(FIREBASE_TO_HOME_TO_USERACCTS).child(bountyHuntPrefs.getString(USER_PREF_AUTH, ""));
    userRef.addListenerForSingleValueEvent(new ValueEventListener() {
        @Override
        public void onDataChange(DataSnapshot dataSnapshot) {
            UserAccount user = dataSnapshot.getValue(UserAccount.class);
            userEmail = user.getUserName();
            if (userScore == 0)
                userScore = user.getScore();
            prefEditor.putLong(USER_PREF_SCORE, userScore).apply();
        }
    

    更新-对评论中问题的回答

    当您没有数据的读取权限时,通常会调用onCancelled()方法

    更新用户的分数可以像userRef .child("score").setValue(42)一样简单。或者通过保存整个用户:user.setScore(42); userRef.setValue(user);(您需要为此创建一个setScore()方法)