Android : "강제 종료"후 애플리케이션을 자동으로 다시 시작하는 방법은 무엇입니까?


81

Android 애플리케이션에서 예외를 제대로 처리하지 않으면 일반적으로 "Force Closed"오류가 발생합니다.

강제 종료 된 경우 애플리케이션을 자동으로 다시 시작하려면 어떻게해야합니까?

이에 사용되는 특정 권한이 있습니까?


5
예외를 바로 잡으십시오. 자동으로 다시 시작되는 애플리케이션은 사용자를 짜증나게 할 수 있습니다.
Tomas Andrle 2010

12
응용 프로그램이 충돌 한 경우 다시 시작하고 싶습니다. 특히 사용자가 내 응용 프로그램에있을 때 성가신 것보다 더 친숙 할 것이라고 생각합니다. 그리고 예, 모든 예외를 올바르게 처리하려고합니다. :)
Johnny

2
@Johnny : 문제에 대한 해결책을 공유하십시오.
Code_Life 2012-07-02

예외 발생시 애플리케이션을 다시 시작 하려면 이 문서 를 확인 하십시오 .
들은 Chintan Rathod

답변:


100

이를 수행하려면 다음 두 가지를 수행해야합니다.

  1. 응용 프로그램 충돌의 표준 방식 인 "강제 종료"를 피하십시오.
  2. 어쨌든 충돌이 발생하면 다시 시작 메커니즘을 설정하십시오.

이를 수행하는 방법은 아래를 참조하십시오.

  1. 전화 Thread.setDefaultUncaughtExceptionHandler()케이스하는 모든 캐치되지 않는 예외 잡기 위해 uncaughtException()메소드가 호출됩니다. "강제 종료"가 나타나지 않고 응용 프로그램이 응답하지 않는 것은 좋지 않습니다. 응용 프로그램이 충돌했을 때 다시 시작하려면 다음을 수행해야합니다.

  2. 에서 onCreate방법, 당신의 주요 활동에 초기화 PendingIntent회원 :

    Intent intent = PendingIntent.getActivity(
        YourApplication.getInstance().getBaseContext(),
        0,
        new Intent(getIntent()),
        getIntent().getFlags());
    

그런 다음 uncaughtException()방법에 다음을 입력하십시오 .

AlarmManager mgr = (AlarmManager) getSystemService(Context.ALARM_SERVICE);
mgr.set(AlarmManager.RTC, System.currentTimeMillis() + 2000, intent);
System.exit(2);

을 (를) 호출해야합니다 System.exit(). 그렇지 않으면 작동하지 않습니다. 이런 식으로 애플리케이션은 2 초 후에 다시 시작됩니다.

결국 응용 프로그램이 충돌했다는 의도에 플래그를 설정할 수 있으며 onCreate()방법 에서 "죄송합니다, 응용 프로그램이 충돌했습니다.


4
나는 그것을 알아 냈다. 이제 문제는 uncaughtException 메서드를 구현하는 곳입니다 ?? PLZ 도움. 감사.
Jay Mayu 2011

2
@MayuMayooresan 응용 프로그램 클래스 또는 활동을 확장하고 onCreate ()에서 다음을 수행 할 수 있습니다. Thread.setDefaultUncaughtExceptionHandler (new UncaughtExceptionHandler () {...});
AgentKnopf

1
활동을 확장하는 경우 애플리케이션의 진입 점 역할을 할 수있는 모든 활동에 대해 동일한 작업을 수행해야합니다 (예 : 창이 죽을 때와 같이 Android OS가 시작하기로 결정할 수있는 활동 포함)
Mick

1
앱 관리 메뉴를 통해 프로세스를 강제로 중지 한 후 ICS에서 작동하지 않는 것 같습니다.
sunghun

5
YourApplication은 무엇을 의미합니까? @Mahesh 조언을 사용했지만 작동하지 않았습니다. 누군가 그것을 설명하십시오.
Shervin Gharib

16

요령은 애초에 강제 종료를하지 않는 것입니다.

메서드 를 사용 하면Thread.setDefaultUncaughtExceptionHandler() 응용 프로그램을 강제 종료하는 예외를 포착 할 수 있습니다.

봐 가지고 이 질문에 를 사용하는 예를 들어, UncaughtExceptionHandler응용 프로그램에 의해 제기 된 예외를 기록 할 수 있습니다.


1
단서 감사합니다. 다음 질문은 UncaughtExceptionHandler.uncaughtException이 언제 호출됩니까? 사용자가 "강제 닫기"버튼을 클릭하지 않은 경우에도 UncaughtExceptionHandler.uncaughtException이 호출됩니까?
Johnny

3
@Johnny 응용 프로그램에서 처리되지 않은 예외가 발생하면 강제 종료가 발생합니다. UncaughtExceptionHandler를 사용하면 응용 프로그램이 모든 예외를 처리 할 수 ​​있으며 사용자는 강제 닫기 대화 상자를 볼 수 없습니다. 즉, 강제 닫기 대화 상자가 표시되었을 때 UncaughtExceptionHandler가 호출됩니다. 그러나 애플리케이션이 포착하는 예기치 않은 예외를 처리하는 방법에주의해야합니다. 아무 일도 일어나지 않는 척하는 것은 분명히 위험합니다.
Dave Webb

설명 해주셔서 감사합니다. UncaughtExceptionHandler에 대해 잘 설명합니다. 그러나 강제 종료 후 자동으로 다시 시작되는 응용 프로그램을 보았습니다. 예 : Launcher (좋은 예는 아니지만 타사 앱도이 방식으로 작동하는 것을 보았습니다). 내 앱이 이렇게 작동하려면 어떻게해야합니까? 어떤 종류의 시스템 권한을 사용해야합니까?
Johnny

10

크 리터 시즘이나 기타 오류 신고 서비스를 이용하시는 분은 거의 맞습니다.

final UncaughtExceptionHandler defaultHandler = Thread.getDefaultUncaughtExceptionHandler();
Thread.setDefaultUncaughtExceptionHandler(new UncaughtExceptionHandler() {
            public void uncaughtException(Thread thread, Throwable ex) {
              Intent launchIntent = new Intent(activity().getIntent());
              PendingIntent pending = PendingIntent.getActivity(CSApplication.getContext(), 0,
                    launchIntent, activity().getIntent().getFlags());
              getAlarmManager().set(AlarmManager.RTC, System.currentTimeMillis() + 2000, pending);
              defaultHandler.uncaughtException(thread, ex);
            }
});

2
public class ForceCloseExceptionHandalingActivity extends Activity {
    /** Called when the activity is first created. */
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
        setContentView(MyLayout());
        Thread.setDefaultUncaughtExceptionHandler(new Thread.UncaughtExceptionHandler() {
            @Override
            public void uncaughtException(Thread paramThread, Throwable paramThrowable) {
                myHandaling(paramThread, paramThrowable);
            }
        });
    }

    private ViewGroup MyLayout(){
        LinearLayout mainLayout = new LinearLayout(this);
        mainLayout.setOrientation(LinearLayout.VERTICAL);  
        Button btnHello =new Button(this);
        btnHello.setText("Show all button");
        btnHello.setOnClickListener(new OnClickListener() {         
            @Override
            public void onClick(View v) {                   
                setContentView(MyLayout2());            
            }
        });             
        mainLayout.addView(btnHello);       
        return mainLayout;
    }

    private ViewGroup MyLayout2(){
        LinearLayout mainLayout = new LinearLayout(this);
        mainLayout.setOrientation(LinearLayout.VERTICAL);  
        Button btnHello =new Button(this);
        btnHello.setText("I am a EEROR uncaughtException");
        btnHello.setOnClickListener(new OnClickListener() {         
            @Override
            public void onClick(View v) {                   
                Log.e("Alert","btn  uncaughtException::");
                Toast.makeText(ForceCloseExceptionHandalingActivity.this, "Alert uncaughtException222",Toast.LENGTH_LONG).show();
                View buttone = null;
                setContentView(buttone);            
            }
        });     
        Button btnHello2 =new Button(this);
        btnHello2.setText("I am a EEROR Try n catch");
        btnHello2.setOnClickListener(new OnClickListener() {            
            @Override
            public void onClick(View v) {   

                try{
                    View buttone = null;
                    setContentView(buttone);
                }
                catch (Exception e) {
                    Log.e("Alert","Try n catch:::");
                    Toast.makeText(ForceCloseExceptionHandalingActivity.this, "Alert Try n catch",Toast.LENGTH_LONG).show();
                    setContentView(MyLayout());
                }

            }
        });     
        mainLayout.addView(btnHello);
        mainLayout.addView(btnHello2);
        return mainLayout;
    }
    public void myHandaling(Thread paramThread, Throwable paramThrowable){
        Log.e("Alert","Lets See if it Works !!!" +"paramThread:::" +paramThread +"paramThrowable:::" +paramThrowable);
        Toast.makeText(ForceCloseExceptionHandalingActivity.this, "Alert uncaughtException111",Toast.LENGTH_LONG).show();
        Intent in =new Intent(ForceCloseExceptionHandalingActivity.this,com.satya.ForceCloseExceptionHandaling.ForceCloseExceptionHandalingActivity.class);
        startActivity(in);
        finish();
        android.os.Process.killProcess(android.os.Process.myPid()); 
    }
    @Override
    protected void onDestroy() {
        Log.e("Alert","onDestroy:::");
        Toast.makeText(ForceCloseExceptionHandalingActivity.this, "Alert onDestroy",Toast.LENGTH_LONG).show();
        super.onDestroy();  
    }

이 코드는 "Thread.setDefaultUncaughtExceptionHandler"를 가져와 닫힌 후 호출합니다 ..
Satya

2

패키지에이 클래스를 추가하기 만하면됩니다.

public class MyExceptionHandler implements
    java.lang.Thread.UncaughtExceptionHandler {
private final Context myContext;
private final Class<?> myActivityClass;

public MyExceptionHandler(Context context, Class<?> c) {
    myContext = context;
    myActivityClass = c;
}

public void uncaughtException(Thread thread, Throwable exception) {
    StringWriter stackTrace = new StringWriter();
    exception.printStackTrace(new PrintWriter(stackTrace));
    System.err.println(stackTrace);// You can use LogCat too
    Intent intent = new Intent(myContext, myActivityClass);
    String s = stackTrace.toString();
    //you can use this String to know what caused the exception and in which Activity
    intent.putExtra("uncaughtException", "Exception is: " + stackTrace.toString());
    intent.putExtra("stacktrace", s);
    myContext.startActivity(intent);
    //for restarting the Activity
    Process.killProcess(Process.myPid());
    System.exit(0);
}}

애플리케이션 또는 모든 활동 클래스에서 onCreate () 메소드 내에서 다음을 호출하면됩니다.

Thread.setDefaultUncaughtExceptionHandler(new MyExceptionHandler(this,
            SplashScreenActivity.class));
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.