繁体   English   中英

AWS Cognito身份池登录和持久性

[英]AWS Cognito Identity Pool Login and Persistence

主要目标

通过在Android应用中使用Cognito用户池和Cognito联合身份来持久登录。 该应用程序应处理令牌刷新(通过SDK?)。 电子邮件用作用户名。 在整个应用程序中仅允许使用1个唯一的用户名(电子邮件)。 示例:如果用户以电子邮件/用户名test@gmail.com登录到Facebook,则他们应该不能通过用户池通过test@gmail.com注册用户。

设定

我创建了一个身份库,身份验证提供者是我的Cognito用户池,Facebook和Google。 我正在使用适用于Facebook和Google的本地SDK进行登录。

我有一个SplashScreenActivity,它检查用户是否已登录并相应地重定向他们(LoginActivity或MainActivity)

如果通过用户池登录,则将我的用户池与currentUser.getSession(authenticationHandler)一起使用会很好。

第一次

  • 未登录
  • AuthenticationHandler:getAuthenticationDetails:userId为null
  • 显示登录活动

登录

  • 通过用户池登录
  • 成功-> MainActivity

重新启动应用

  • 的AuthenticationHandler:的onSuccess
  • 显示MainActivity

如果我通过Facebook登录并通过CognitoCachingCredentialsProvider设置登录名,则不会更新currentUser ,因此我的getSession()调用不起作用。 但是,我所能做的就是调用getCachedIdentityId() 我的CognitoCachingCredentialsProvider不会过期吗?

此外,如果我使用从用户池创建的用户登录并注销currentUser.getUserId()与我先前登录的用户池用户getCachedIdentityId()返回,但getCachedIdentityId()为null

private void logout() {
    EasyPrefs.clear(this); //clear shared preferences for local variables
    authHelper.getCredentialsProvider().clear(); //clear cached CognitoCredentialsProvider

    CognitoUser currentUser = AuthHelper.getInstance().getUserPool().getCurrentUser();
    currentUser.signOut(); //this is pointless if I login with federated identity

    //TODO: Logout of Google?
    //TODO: Logout of Facebook?

    //assume logout was successful?
    startActivity(new Intent(this, SplashScreenActivity.class));
    finish();
}

问题

  • 由于我正在使用用户池,facebook和google处理本机登录,我是否必须手动管理访问令牌并刷新令牌? 还是CognitoCachingCredentialsProvider可以为我处理此问题?
  • 我可以(通过用户池,facebook或google)登录用户并保持登录状态,如何检查?
  • 当用户通过facebook / google登录时,是否可以在用户池中本地创建用户?

最终狂乱

如果您曾经使用过Firebase Auth-这就是我想要该功能的应用程序! 使用Firebase用户,Facebook登录名和Google登录名设置Firebase Auth非常容易。

  • 用身份提供商登录
  • 将令牌传递给Firebase
  • 获取Firebase用户
  • 完成。

要注销? firebaseUser.logout()。 就那么简单。

SplashScreenActivity

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

    authHelper = AuthHelper.getInstance();
    authHelper.init(this);

    //Check if a cached identity exists?
    //This will return an identity if user is user pool, facebook, google
    String cachedIdentityId = authHelper.getCredentialsProvider().getCachedIdentityId();
    Logger.d(TAG, cachedIdentityId == null ? "cachedIdentityId is null" : cachedIdentityId);

    //This is never null unless app data has been cleared?
    CognitoUser currentUser = authHelper.getUserPool().getCurrentUser();

    //Even if I call currentUser.signOut(), this still returns a userId
    String cachedUserId = currentUser.getUserId(); //because aws sucks
    Logger.d(TAG, cachedUserId == null ? "cachedUserId is null" : cachedUserId);

    //if user pool user is signed in, this will goto MainActivity
    currentUser.getSession(authenticationHandler);

    //not doing anything with cachedIdentityId because....?
}

private AuthenticationHandler authenticationHandler = new AuthenticationHandler() {
    @Override
    public void onSuccess(CognitoUserSession userSession, CognitoDevice newDevice) {
        startActivity(new Intent(SplashScreenActivity.this, MainActivity.class));
    }

    @Override
    public void getAuthenticationDetails(AuthenticationContinuation authenticationContinuation, String userId) {

        //wait a few seconds, then goto LoginActivity
        handler.postDelayed(timerTask, SECONDS * 2);
    }

    @Override
    public void getMFACode(MultiFactorAuthenticationContinuation continuation) {

    }

    @Override
    public void authenticationChallenge(ChallengeContinuation continuation) {

    }

    @Override
    public void onFailure(Exception exception) {
        Logger.e(TAG, AuthHelper.formatException(exception));

        //wait a few seconds, then goto LoginActivity
        handler.postDelayed(timerTask, SECONDS * 2);
    }
};

LoginActivity

我本机处理每个登录方案(用户池,facebook,google)

private void setLogins(String key, String token) {
    Map<String, String> logins = new HashMap<>();
    logins.put(key, token);
    authHelper.getCredentialsProvider().setLogins(logins);

    new RefreshCognitoCredentials().execute();
}

private class RefreshCognitoCredentials extends AsyncTask<Void, Void, String> {

    @SuppressLint("LongLogTag")
    @Override
    protected String doInBackground(Void... voids) {
        Map<String, String> logins = authHelper.getCredentialsProvider().getLogins();

        for(String key : logins.keySet()) {
            Logger.d(TAG, key + " - " + logins.get(key));
        }

        try {
            authHelper.getCredentialsProvider().refresh();
        } catch(NotAuthorizedException exception) {
            authHelper.getCredentialsProvider().clear();
            return null;
        }

        return authHelper.getCredentialsProvider().getIdentityId();
    }

    @SuppressLint("LongLogTag")
    @Override
    protected void onPostExecute(String response) {
        if(response == null) {
            Toast.makeText(getApplicationContext(), "Logins don't match. Please include at least one valid login for this identity or identity pool.", Toast.LENGTH_LONG).show();
            return;
        }

        Logger.d(TAG, response);
        startActivity(new Intent(AuthActivity.this, MainActivity.class));
        finish();
    }
}

作为AWS Amplify框架的一部分发布的新AWSMobileClient在这里可能会有所帮助: https : AWSMobileClient

您将具有Cognito用户池的基本注册功能:

AWSMobileClient.getInstance().signUp()

如果配置了身份池,它将自动获取这些凭据。 所有令牌获取/刷新/等。 是自动处理的。 您还可以使用社交登录:

AWSMobileClient.getInstance().federatedSignIn(
IdentityProviders.FACEBOOK.toString(), “FACEBOOK_TOKEN_HERE”, new Callback<UserState>() {
            @Override
            public void onResult(final UserState userState) {
                //Handle the result
            }

            @Override
            public void onError(Exception e) {
                Log.e(TAG, "sign-in error", e);
        });

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM