我的要求是,我想确定用户是否在5分钟内处于非活动状态,然后用户从应用程序中自动注销并上传登录并注销服务器上的日志.
我已经尝试了上面链接中的所有答案,但该答案适用于单一活动,但我想跟踪它以进行多项活动.
为此,我创建了抽象类
public abstract class SessionTimeOutActivity extends BaseActivity { public static final long DISCONNECT_TIMEOUT = 1000 * 60; // 5 min = 5 * 60 * 1000 ms private static Handler disconnectHandler = new Handler(new Handler.Callback() { @Override public boolean handleMessage(Message msg) { Log.d("SessionTimeOutActivity","disconnectHandler"); return false; } }); private Runnable disconnectCallback = new Runnable() { @Override public void run() { // Perform any required operation on disconnect Log.d("SessionTimeOutActivity","disconnectCallback"); Toast.makeText(getApplicationContext(),"Session time out",Toast.LENGTH_LONG).show(); Intent intent = new Intent(getApplicationContext(),LoginActivity.class); startActivity(intent); intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TASK | Intent.FLAG_ACTIVITY_CLEAR_TOP); finish(); } }; public void resetDisconnectTimer() { disconnectHandler.removeCallbacks(disconnectCallback); disconnectHandler.postDelayed(disconnectCallback,DISCONNECT_TIMEOUT); } public void stopDisconnectTimer() { disconnectHandler.removeCallbacks(disconnectCallback); } @Override public void onUserInteraction() { Log.d("SessionTimeOutActivity","onUserInteraction"); resetDisconnectTimer(); } @Override public void onResume() { super.onResume(); // resetDisconnectTimer(); } @Override public void onStop() { super.onStop(); // stopDisconnectTimer(); } }
app中的其他活动
public class MenuActivtyNav extends SessionTimeOutActivity{ ..... }
MenuActivity
public class MenuActivty extends SessionTimeOutActivity{ .... }
问题是
1)在锁定屏幕中自动注销不起作用,它不调用disconnectCallback
2)使用应用程序时,它会显示Toast消息“Session time out”
解决方法
问题1.您应该避免在Android上的活动中长时间运行任务,尤其是当它们不可见时,因为系统可能会终止您的活动或应用程序进程,因此代码将无法运行.
问题2.每个活动都会将断开连接回调发送到您的处理程序,如果用户正在与第二个活动进行交互,则第一个活动的回调将不会被重置并将触发.
解.
现在让我们考虑解决这个问题的方法.
最好有一个地方来跟踪不活动.它可以是单例,也可以使用应用程序对象.
并分别处理2个案例:第一个是您的用户在应用程序内部并且没有使用它而另一个是您的用户不在应用程序中时.
对于第一个目标,您可以采用与当前目标类似的方法,但在应用程序中创建共享disconnectCallback.将处理程序,回调和重置回调逻辑移动到Application类并创建
@Override public void onUserInteraction()
在Application上调用resetCallback.这将使所有活动使用相同的回调并解决问题2.
对于第二个目标,您可以使用Activity Lifecycle Callbacks.
每次暂停活动时都会保存时间戳.然后,每次恢复活动时,将此时间戳与恢复时间进行比较,如果大于5分钟,则注销用户并路由到登录屏幕.它将解决问题1.您需要保留此时间戳,因为应用程序可能被系统杀死,并且内存中共享的所有内容都将被删除.例如,使用共享首选项.
最后一件事,当应用程序进入后台时,您需要取消回调.您可以在活动回调的onActivityPaused(活动活动)中执行此操作,在您将触发第二种情况的逻辑的位置.