[Android] 서비스 : 서비스 바인딩, 액티비티 실행하기

undefined·2024년 6월 24일
0

Android

목록 보기
6/6

StartService로 실행한 서비스를 일부 액티비티에서 bind해서 사용하는 경우가 있었다. 이때 실수했던 점들을 정리해보았다.

BindService 는 Unbind를

서비스를 종료하기 위해 StopService를 호출했는데 서비스가 계속 돌아가는 문제가 있었다.
인텐트는 잘 받는데 왜 서비스가 안 죽지..?

원인은 unbind를 하지 않고 stopService를 호출해서였다. 서비스를 바인드 한 경우, 모든 바인드가 끊겨야 서비스가 종료된다.

나중에 까먹을 걸 대비해서 코드 스니펫도 남겨둬야겠다.

  1. 서비스에 바인더를 정의한다.

     companion object {
         lateinit var binder: MyBinder
         fun isInitialized(): Boolean {
             return ::binder.isInitialized
         }
     }
    
     inner class MyBinder : Binder() {
         fun getService() = this@MyService
     }
    
     override fun onBind(intent: Intent): IBinder {
         return binder
     }
  2. 서비스에 연결/해제 시 수행할 작업을 정의한다.

     private val serviceConnection = object : ServiceConnection {
         override fun onServiceConnected(name: ComponentName?, service: IBinder) {
             val localBinder = service as? MyService.MyBinder
    
             localBinder?.let {
                 val myCustomService = it.getService()
    
                 if (myCustomService.connected.value == true) {
                     mViewModel.address.postValue(myCustomService.address.value)
                 }
             }
         }
    
         override fun onServiceDisconnected(name: ComponentName?) {
             // 서비스와 연결 해제
         }
     }
  3. 서비스를 시작한다.(필요하면)

             val intent = Intent(requireContext(), MyService::class.java)
             intent.putExtra(EXTRA_DEVICE_ADDRESS, selectedDevice.address)
             requireContext().startService(intent)
  4. 서비스에 바인드한다. (이 때 서비스가 실행되고 있는지, 바인드 시 서비스를 실행해야하는지 등에 따라 액션을 다르게 설정해야 한다.)

             val intent = Intent(requireContext(), MyService::class.java)
             requireActivity().bindService(
                 intent,
                 serviceConnection,
                 AppCompatActivity.BIND_AUTO_CREATE // 서비스가 실행되고 있지 않으면 서비스를 실행시킨다
             )
  5. 서비스를 unbind, stop 한다.

                    requireActivity().unbindService(serviceConnection)
                     requireActivity().stopService(
                         Intent(context, MyService::class.java)        
                     )

서비스에서 액티비티 시작하기

서비스를 백그라운드로 돌릴 때 특정 상황에 액티비티를 띄워주어야 하는 경우가 종종 있다.
나의 케이스에는 앱의 모든 태스크가 없어도 백그라운드에서 서비스가 돌아가야했기 때문에 이 경우 액티비티를 띄우려면 새로운 태스크를 만들어 주어야 했다.

        val intent = Intent(this, AccidentReportActivity::class.java)
        intent.putExtra("reportData", data)
        intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK)
        startActivity(intent)
profile
이것저것 하고 싶은 게 많은 병아리 개발자

0개의 댓글