Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

App Lifecycle #2

Open
simoniful opened this issue Feb 28, 2022 · 0 comments
Open

App Lifecycle #2

simoniful opened this issue Feb 28, 2022 · 0 comments
Labels

Comments

@simoniful
Copy link
Owner

simoniful commented Feb 28, 2022

App LifeCycle

App State

  • foreground: 사용자의 높은 집중도, CPU를 포함한 system resource에서 우선순위
  • background: 화면 밖의 일

App State가 바뀔 때 UIKit은 적절한 delegate object의 method를 호출하게 된다.

  • iOS 13 이상은 UISceneDelegate를 사용하여 scene-based app에서 발생하는 life-cycle event를 제어할 수 있다.
  • iOS 12 이하는 life-cycle event에 응답하기 위해서 UIApplicationDelegate 개체를 사용하면 된다.

AppDelegate와 SceneDelegate

iOS 12 이전, 하나의 앱이 하나의 process와 하나의 UI 객체로 매칭되었던 시절에는 Process LifeCycle과 UI LifeCycle을 모두 AppDelegate에서 처리했다.

iOS 13 이후, 생태계의 변화에 따른 개발 환경의 변화로 멀티윈도우 작업이 가능하게 되면서, 결과적으로 앱들이 하나의 process를 사용하긴 하지만 다수의 UI, scene과 연결된 scene delegate, scene session들을 동시에 활성화할 수 있게 되었다.

Scene Session은 앱에서 생성한 모든 scene의 정보를 관리한다. 그리고 Scene을 감시하여 생성/삭제에 대해서 AppDelegate에게 정보를 전달한다.

앱의 주요 생명 주기 이벤트를 관리 역할이 SceneDelegate로 위임되면서 iOS13부터 AppDelegate가 하는 일은 다음과 같다.

  1. 앱의 가장 중요한 데이터 구조를 초기화하는 것
  2. 앱의 scene을 환경설정(Configuration)하는 것
  3. 앱 밖에서 발생한 알림(배터리 부족, 다운로드 완료 등)에 대응하는 것
  4. 특정한 scenes, views, view controllers에 한정되지 않고 앱 자체를 타겟하는 이벤트에 대응하는 것(앱 시작, 종료)
  5. 애플 푸쉬 알림 서비스와 같이 실행시 요구되는 모든 서비스를 등록하는것

LifeCycle Method CallStack

1. 사용자가 앱을 실행합니다: Not Running → In-Active → Active

  • application(_:didFinishLaunchingWithOptions:)
    앱이 실행되고 앱을 화면에 띄우기 위한 모든 설정이 완료된 뒤, 실제로 화면에 나타나기 직전에 호출.

    ⬇️

  • 앱 실행 후 UIKit에 Scene 연결 과정을 밟음
    application(_:configurationForConnecting:options:)
    새로운 Scene을 만들고 UIKit과 연결하기 위한 configuration을 지정.
    해당 메서드는 앱 시작시 호출되지 않고, 새로운 Scene 혹은 새 window을 가져야 하는 경우에만 호출.

    ⬇️

  • scene(:willConnectTo:options:)
    Scene이 연결될 것임을 delegate에 알림.
    기존에 application(
    :didFinishLaunchingWithOptions:)에서 했던 UIWindow 생성 작업을 해당 method에서 수행 가능.

    ⬇️

  • sceneDidBecomeActive(_:)
    앱이 Inactive에서 Active 상태로 전환되었을 때 호출(화면에 나타남).

2. 앱 실행 도중 홈으로 나갑니다: Active → In-Active → Background

  • sceneWillResignActive(_:) 앱이 Active에서 Inactive 상태로 전환될 때 호출.

    ⬇️

  • sceneDidEnterBackground(_:) 앱이 Background 상태로 전환되었을 때 호출.

2-1. 앱을 다시 켭니다: Background → Active

  • sceneWillEnterForeground(_:) 앱이 Background에서 Inactive 상태로 전환될 때 호출.

    ⬇️

  • sceneDidBecomeActive(_:) 앱이 Inactive에서 Active 상태로 전환될 때 호출.

2-2. 앱을 종료합니다 : Background or Suspended → Not Running

iOS 12까지는 multi window를 지원하지 않았기 때문에 멀티 태스킹 창에서 Swipe-up을 통해 앱을 종료. 하지만 iOS 13부터 multi window를 지원하고 만약 앱이 둘 이상의 Scene Window를 갖는다면 Swipe-up은 앱을 종료시키는 것이 아니라 Scene을 해제. 그렇게 Scene이 모두 해제 되면 앱이 종료!

  • sceneDidDisconnected(_:) UIKit에 연결된 Scene의 연결 해제를 delegate에 요청.

    ⬇️

  • application(_:didDiscardSceneSessions:) 사용자가 멀티태스킹 화면에서 한개 이상의 Scene을 종료시켰을 때 호출.

    ⬇️

  • applicationWillTerminate(_:) 앱이 사용자에 의해 종료될 때 호출(시스템에 의한 예기치 못한 종료시에는 호출되지 않음).


Q. 앱이 foreground에 있을 때와 background에 있을 때 어떤 제약사항이 있나요?

애플리케이션이 foreground에 있을 때 사용할 수 있는 메모리를 최우선적으로 가지며 부족한 메모리 만큼 background의 애플리케이션을 종료합니다. Background가 되면 추가적인 실행 시간을 할당받지 않지만 AirPlay, Picture in Picture 비디오를 사용한 오디오 통신, 사용자 위치 서비스, Voice over IP, 외부 악세서리와의 유선 통신, 블루투스 LE(Low Energy)와 통신, 혹은 디바이스를 블루투스 LE 악세서리로 변환, 서버에서의 정기적인 업데이트, Apple Push Notification 지원의 경우에는 Background 앱에 실행 시간을 할당해 줍니다.

Q. 상태 변화에 따라 다른 동작을 처리하기 위한 앱델리게이트 메서드들을 설명하시오.

  • application:willFinishLaunchingWithOptions
    launch time 에 앱의 코드가 실행되는 첫 단계
  • application:didFinishLaunchingWithOptions
    앱이 사용자에게 보여지기 전 어떠한 초기화를 진행하는 단계
  • application:didBecomeActive, scene:didBecomeActive
    앱이 Active 상태가 되었을 때 호출. UIkit은 이 메서드가 호출되면 didBecomeActiveNotification이라는 Notification을 post해서 앱 전체에서 해당 이벤트를 처리할 수 있도록 해줍니다.
  • application:willResignActive, scene:willResignActive
    앱이 Active 상태를 포기했을 때 호출. 홈 화면으로 나가거나 제어센터, 알림 센터등을 사용할 때 In-active상태가 되므로 해당 메서드가 호출됩니.
  • application:didEnterBackground, scene:didEnterBackground
    앱이 background 상태가 되었을 때 호출. 백그라운드 상태가 되면 타이머를 무효화하고 앱 상태 정보를 저장하게 됩니다. 해당 메서드는 빠르게 반환되기 때문에 만약 수행할 작업이 있고 추가적인 실행시간이 필요하다면 beginBackgroundTask(expirationHandler: )메서드를 사용하면 됩니다.
  • application:willEnterForeground, scene:willEnterForeground
    앱이 Foreground 상태가 됐을 때 호출
  • application:willTerminate
    앱이 종료되기 직전에 호출. 해당 메서드는 SceneDelegate에는 존재하지 않는다. 메서드가 호출된 후 앱이 종료되게 되면 메모리에서 완전히 제거됩니다. 따라서 메서드를 호출할 때 사용자 데이터를 저장하고 타이머를 무효화하는 등의 작업을 수행할 때 사용됩니다.

Q. 앱이 In-Active 상태가 되는 시나리오를 설명하시오.

앱이 실행되면서 Foreground에 진입하지만, 어떠한 이벤트도 받지 않는 상태, 다른 상태로 넘어가기 전, 앱은 반드시 이 상태를 거칩니다
scene:willResignActive 메서드를 통한 해당 상태로 진입 확인 가능

  • 앱을 실행할 때: Not Running → Inactive → Active
  • 앱 실행 중 홈 버튼 눌렀을 때: Active → Inactive → Background ( → Suspended)
  • 앱을 다시 키는 경우: Background → Inactive → Active
  • 앱 종료: Active → In-Active → Background → Suspended → Not Running
  • 이 외: 전화나 메시지 같은 interrupt 발생, 미리알림과 같은 알림창이 화면을 덮어 앱이 실질적으로 event를 받지 못하는 상태

Q. scene delegate에 대해 설명하시오.

앱에서 생성한 모든 scene의 정보를 관리한다. 그리고 Scene을 감시하여 생성/삭제에 대해서 AppDelegate에게 정보를 전달합니다.
iOS 13.0에서의 변화로 하나의 앱에서 여러개의 scene 을 가질 수 있게 되었습니다.

Q. UIApplication 객체의 컨트롤러 역할은 어디에 구현해야 하는가?

AppDelegate 라는 대리 객체를 통한 내부 메서드를 활용

Q. App의 Not running, Inactive, Active, Background, Suspended에 대해 설명하시오.

  • Not running : 앱이 실행되지 않았거나, 완전히 종료되어 동작하지 않는 상태
  • In-Active : 앱이 실행중이지만 사용자 이벤트를 받지 않는 상태
  • Active : 앱이 실행중이고 사용자 이벤트를 받아 상호작용할 수 있는 상태
  • Background : 앱을 실행시킨 뒤 홈화면으로 나가거나 다른 앱으로 이동하여 실질적인 동작을 하지 않는 상태
  • Suspended : 앱이 background 상태에 있다가 다시 실행될 때 최근작업을 빠르게 로드하기위해서 메모리에 관련 데이터만이 저장되어있는 상태. 앱이 background 상태로 2~3초간 유지되면 Suspended 상태로 전환됩니다. Suspended 상태의 app들은 iOS의 메모리가 부족해지면 가장 먼저 메모리에서 해제되기 때문에 앱을 오래 사용하지 않으면 다시 처음부터 실행됩니다.
    ※ In-Active + Active = Foreground
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

1 participant