使用客户端凭据流的Android / IOS秘密到期管理

时间:2017-10-11 11:40:45

标签: android ios oauth-2.0 app-secret

我想知道是否有任何策略来管理移动设备中的秘密过期。

在授权服务器允许移动客户端使用资源所有者密码流与客户端凭据进行授权的情况下,客户端机密具有到期时间。

我已经看到至少有一些方法可以安全地在Android应用上存储机密,但是,如何在不发布应用程序新版本的情况下管理秘密到期?

2 个答案:

答案 0 :(得分:5)

这就是我们在OAuth Refresh Token Standards之后的应用中所做的工作。

第1步:您的API应按照here

的规定发送标准的Auth令牌响应
 HTTP/1.1 200 OK
 Content-Type: application/json;charset=UTF-8
 Cache-Control: no-store
 Pragma: no-cache

 {
   "access_token":"2YotnFZFEjr1zCsicMWpAA",
   "token_type":"example",
   "expires_in":3600,
   "refresh_token":"tGzv3JOkF0XG5Qx2TlKWIA",
   "example_parameter":"example_value"
 }

步骤2:在共享首选项/本地缓存/本地数据库中保存该响应,我们使用共享首选项(假设accountToken是从Auth Token响应创建的类的对象)

SharedPreferences.Editor editor = getContext().getSharedPreferences("AUTH_PREFS_NAME", Context.MODE_PRIVATE).edit();
editor.putString("AUTH_ACCESS_TOKEN_KEY", accountToken.getAccess_token());
editor.putString("AUTH_REFRESH_TOKEN_KEY", accountToken.getRefresh_token());
editor.putLong("AUTH_EXPIRES_IN_KEY", accountToken.getExpires_in());
editor.putLong("AUTH_TIME_SAVED_KEY", ((int) (System.currentTimeMillis() / 1000)));
editor.commit();

步骤3:每次必须使用已保存的访问令牌时,请确保它未过期

public boolean needsTokenRefresh(String accessToken) {
    if (accessToken == null || accessToken.length() == 0) {
        // no access token to refresh. Don't refresh.
        return false;
    }

    SharedPreferences pref = mContext.getSharedPreferences("AUTH_PREFS_NAME", Context.MODE_PRIVATE);
    String refreshToken = pref.getString("AUTH_REFRESH_TOKEN_KEY", null);
    if (refreshToken == null || refreshToken.length() == 0) {
        // no refresh token. Can't refresh.
        return false;
    }

    Integer timeSaved = pref.getInt("AUTH_TIME_SAVED_KEY", 0);
    if (timeSaved == 0) {
        // No recording of having saved the token. Don't refresh.
        return false;
    }

    long expiresIn = pref.getLong("AUTH_EXPIRES_IN_KEY", 0);
    int now = (int) (System.currentTimeMillis() / 1000);
    int timePassed = Math.abs(now - timeSaved);
    boolean expired = false;
    if (expiresIn <= timePassed) {
        expired = true;
    }
    return expired;
}

如果needsTokenRefresh()返回false,则使用已保存的验证令牌。如果它返回true,则转到下一步。

第4步:再次进行身份验证,grant_type设为refresh_tokenstated in standards

步骤5:Auth调用应返回标准验证响应,如步骤1中所述,并刷新令牌并使用新的refresh_token

答案 1 :(得分:1)

我能想到的唯一方法是当你第一次运行应用程序连接到服务器并发送手机fingerPrint时,只有当fingerPrint没有在其数据库中列出时,服务器才会发送文件,该文件包含此日期的当前日期和数字签名,因此用户不会更改其值。 每次运行应用程序时,都可以通过应用VerifySignature方法检查日期和日期的完整性。