代码之家  ›  专栏  ›  技术社区  ›  Hayk Mkrtchyan

无法在OnSaveInstanceState-Android之后执行此操作

  •  0
  • Hayk Mkrtchyan  · 技术社区  · 6 年前

    我有一个授权应用程序。在该应用程序中,用户有 accessToken refreshToken . 我做了类似这样的事情,如果用户登录其他硬件而不是真正的硬件,他会自动注销。假设我有我登录的电话1。现在我正在登录phone2。当我授权我的令牌更改时。因此,如果令牌被更改而不是自动注销,我会签入phone1。但有时候在注销之后我会出现这样的错误 例外情况:

    java.lang.illegalStateException:之后无法执行此操作 OnSaveInstanceState。

    这是我在令牌过期时注销的地方。 注意这是一个

    Call<RefreshTokenActivation> newToken = apiClient.newToken(supportObjToken);
            newToken.enqueue(new Callback<RefreshTokenActivation>() {
                @Override
                public void onResponse(Call<RefreshTokenActivation> call, Response<RefreshTokenActivation> response) {
                    if (response.isSuccessful()) {
    
                } else {
                    if (response.code() == 401) {
    
                        //Perform this call if refresh token is expired
    
                        new Handler().postDelayed(new Runnable() {
                            @Override
                            public void run() {
                                Activity activity = (Activity) context;
                                MainActivity mainActivity = (MainActivity) activity;
                                mainActivity.logOut();
                            }
                        }, 1000);
                    }
                }
            }
    

    如果响应为401,则意味着我的令牌已过期。如果令牌已过期,则在第二秒钟后,我将用户 mainActivity .

    以下是MainActivity中的代码:

    public class MainActivity extends AppCompatActivity
        implements FragmentChangeListener, TabLayoutLocationInterface {
    private ConnectionDetector connectionDetector;
    private SlidePageTabsMainFragment slidePageTabsMainFragment;
    private MainFragment mainFragment;
    private RelativeLayout logOut;
    
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
    
        SharedPreferencesManager.init(this);
    
        setContentView(R.layout.activity_main);
    
        logOut = (RelativeLayout) findViewById(R.id.list6);
        connectionDetector = new ConnectionDetector(this);
        slidePageTabsMainFragment = new SlidePageTabsMainFragment();
        mainFragment = new MainFragment();
    
        connectionEnable();
        userLogOut();
    }
    
    public void connectionEnable() {
        if (!connectionDetector.isConnected()) {
            Toast.makeText(this, "Please check your Internet", Toast.LENGTH_LONG).show();
        } else {
            Boolean loggedIn = SharedPreferencesManager.getInstance().getUserLogged();
            if (loggedIn) {
                this.replaceFragment(slidePageTabsMainFragment, true);
            } else {
                this.replaceFragment(mainFragment, true);
            }
        }
    }
    
    @Override
    public void replaceFragment(BaseFragment fragment, Boolean isAddToBackStack) {
        String backStateName = fragment.getFragmentName();
        FragmentManager manager = getSupportFragmentManager();
    
        FragmentTransaction transaction = manager.beginTransaction();
        transaction.replace(R.id.main_fragment_container, fragment, backStateName);
        transaction.addToBackStack(backStateName);
        transaction.commit();
    }
    
    @Override
    public int getTabLayoutLocation() {
        SlidePageTabsMainFragment slidePageTabsMainFragment = (SlidePageTabsMainFragment)
                getSupportFragmentManager().findFragmentByTag("SlidePageTabsMainFragment");
        if (slidePageTabsMainFragment == null) {
            return 0;
        }
        return slidePageTabsMainFragment.getTabLayoutLocation();
    }
    
    //If user click logOut button
    public void userLogOut() {
        logOut.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                SharedPreferencesManager.getInstance().setUserLogin(false);
                SharedPreferencesManager.getInstance().removeUser();
                getSupportFragmentManager().popBackStack(null, FragmentManager.POP_BACK_STACK_INCLUSIVE);
                replaceFragment(mainFragment, false);
            }
        });
    }
    
    
    //A function for automatic logOut
    public void logOut() {
        SharedPreferencesManager.getInstance().setUserLogin(false);
        replaceFragment(new MainFragment(), false);
        getSupportFragmentManager().popBackStack(null, FragmentManager.POP_BACK_STACK_INCLUSIVE);
        recreate();
        SharedPreferencesManager.getInstance().removeUser();
    }
    
    @Override
    protected void onResume() {
        super.onResume();
        Log.d("Test", "Text");
    }
    

    }

    我认为没有什么困难。所以我得到了这个例外 transaction.commit(); 排队 replaceFragment() 方法 MainActivity . 在那个电话里,你看,我在打电话 mainActivity.logOut(); 你看到了 主要活动 这个 logOut 功能。

    //A function for automatic logOut
    public void logOut() {
        SharedPreferencesManager.getInstance().setUserLogin(false);
        replaceFragment(new MainFragment(), false);
        getSupportFragmentManager().popBackStack(null, FragmentManager.POP_BACK_STACK_INCLUSIVE);
        recreate();
    }
    

    所以在这个方法中,我改变了 SharedPreferences 值(在应用程序打开时检查是否需要用户登录?)在那之后,我要把碎片换成 mainFragment (这是基本片段,是的,我正在处理片段)。之后,我弹出所有碎片,因为注销后,如果我单击后退按钮,它将返回,所以弹出后,我重新创建应用程序。重新创建后,感觉像是应用程序第一次打开。好吧,那为什么它会抛出这样的异常呢?知道吗?

    1 回复  |  直到 6 年前
        1
  •  1
  •   Chirag Solanki    6 年前

    transaction.commitAllowingStateLoss(); transaction.commit();

    commit() commitAllowingStateLoss() this