[Android] 의존성 DI 알아보기 - 1

Bluewave·2025년 2월 25일

안드로이드

목록 보기
3/14
post-thumbnail

💗DI in Code

Hilt란?

Dagger 기반의 Android용 의존성 주입 라이브러리
-> 앱에서 의존성을 쉽게 주입 & 관리

의존성 (DI: Dependency Injection)

B의 기능이 추가or변경되거나 형식이 바뀌면 그게 A에 영향을 미침 => 이렇게 클래스를 필요로 하는 것이 의존성!

  • 특정 클래스가 자신이 의존하고 있는 객체를 얻는 방법 3가지
    • A 클래스 안에서 B 인스턴스를 생성하여 초기화
    • 다른 곳에서 객체를 가져옴 (Context, getSystemService() 등)
    • 객체를 파라미터로 제공받음 (A가 B를 파라미터로 받음)
      => DI!

📖 의존성 개념 쉽게 이해하기 with 라면

Dependency = 필요로 하는 것

  • 준비물
    • 냄비
    • 라면 봉지
    • 가스레인지

라면이 가스레인지에 의존하고 있음 = 라면을 만들려면 가스레인지가 있어야 함


의존성 직접 생성

class Ramen {
    private val stove = Stove()  // ❌ 스스로 Stove를 만듦 (강한 결합)

    fun cook() {
        stove.heatUp()
        println("라면 끓이는 중...")
    }
}

-> Stove가 바뀌면 Ramen도 수정해야 함


의존성 주입 - 낮은 결합

class Ramen(private val stove: Stove) {  // ✅ 생성자로 받음 (의존성 주입)
    fun cook() {
        stove.heatUp()
        println("라면 끓이는 중...")
    }
}

fun main() {
    val stove = Stove()  // 외부에서 생성
    val ramen = Ramen(stove)  // ✅ 의존성 주입
    ramen.cook()
}
  • Ramen은 더 이상 Stove를 직접 만들지 x!
  • Stove 변경돼도 Ramen 코드 수정 x
  • 테스트할 때도 가짜 Stove 넣을 수 있음

📖 배달 음식에 비유해보자면

  • 배달앱에서 햄버거 세트 주문
  • 우리가 햄버거 만들지 x
  • 배달원이 햄버거를 직접 배달해줌

=> 이 과정이 의존성 주입!

  • 햄버거: 우리가 원하는 객체
  • 배달원: 햄버거를 제공하는 의존성
  • 배달원이 햄버거 직접 제공: 햄버거가 배달원을 직접 만들 필요 없음!

=> 나는 햄버거 집이 무엇이든 배달원이 주는 대로 받기만 하면 됨: 유연성 증가!

  • 의존성: 내가 직접 만들 필요 없이, 외부에서 제공받아야 하는 것
  • 의존성을 직접 만드는 것이 강한 결합, 주입을 하는 것이 낮은 결합(높은 유연성)

의존성 미사용 vs 사용

class Car {
    private val engine = Engine()

    fun start() {
        engine.start()
    }
}

fun main(args: Array) {
    val car = Car()
    car.start()
}

의존성 미사용 문제점

  • 결합(의존성) 강함
  • Engine 생성자가 변경되면 Car에서도 수정해야 함
  • Carr를 재사용할 때, Engine을 상속한 Gas나 Electric이라는 클래스를 재사용하기가 쉽지 않음
class Car(private val engine: Engine) {
    fun start() {
        engine.start()
    }
}

fun main(args: Array) {
    val engine = Engine()
    val car = Car(engine)
    car.start()
}

DI 이점

  • 코드 재사용 가능
  • 리팩터링 편의성
  • 테스트 편의성

💗DI in Android

의존성 주입 방법 in Android

  1. 생성자를 통한 주입

    • Activity & Fragment에 생성자 주입 불가능!
      => 앱 크래시 발생
      => 안드로이드 프레임워크가 직접 생성하기 때문에 직접 객체 생성 불가능
      => Hilt와 같은 DI 라이브러리를 사용하는 이유! ⭐⭐
  2. setter를 통한 주입
    객체를 생성한 후에 별도의 set 메서드나 lateinit 변수를 통해 의존성을 할당하는 방식

    class Car {
      lateinit var engine: Engine //setter를 통한 주입
    
      fun start() {
          engine.start() // 주입된 engine 객체 사용
      }
    }
    
    fun main(args: Array) {
        val car = Car() // Car 객체 먼저 생성
        car.engine = Engine() // 의존성 주입!
        car.start()
    }

    -> 생성자에서 engine을 주입하는 것 x, 객체를 생성한 후 따로 주입


참고 사이트

Velog - WorldOneTop.log

티스토리 - PINLIB STUDIO

profile
Developer's Logbook

0개의 댓글