의존성 주입

CosmoNumb·2024년 7월 22일

Spring

목록 보기
8/24

@Autowired를 사용하여 클래스 내에 주입하는 개념은 의존성 주입(Dependency Injection, DI)이라는 디자인 패턴을 사용하는 것입니다. 의존성 주입은 객체 지향 프로그래밍에서 객체 간의 의존성을 관리하고, 객체의 생성을 외부에서 제어하여 코드의 결합도를 낮추고 유연성을 높이는 방법입니다. 이를 통해 테스트 용이성, 유지보수성 및 코드 재사용성을 높일 수 있습니다.

의존성 주입의 개념

의존성 주입은 객체가 필요한 의존성을 직접 생성하거나 찾지 않고, 외부에서 주입받는 방법입니다. 스프링 프레임워크에서는 @Autowired 어노테이션을 사용하여 자동으로 의존성을 주입할 수 있습니다.

왜 의존성 주입을 사용하는가?

  1. 결합도 감소:

    • 객체 간의 결합도를 낮춰줍니다. 한 클래스가 다른 클래스에 강하게 의존하지 않도록 합니다.
    • StudentService 클래스가 StudentRepository의 구체적인 구현에 의존하지 않으므로, 나중에 StudentRepository의 구현을 변경하더라도 StudentService 클래스를 수정할 필요가 없습니다.
  2. 유연성 증가:

    • 인터페이스를 통해 다양한 구현체를 주입할 수 있으므로, 코드의 유연성과 확장성이 증가합니다.
    • 예를 들어, StudentRepository의 구현체를 교체하거나, 테스트 목적으로 가짜(Mock) 객체를 주입할 수 있습니다.
  3. 테스트 용이성:

    • 의존성 주입을 사용하면, 테스트 시에 필요한 의존성을 쉽게 주입할 수 있습니다. 이를 통해 단위 테스트를 작성할 때 실제 데이터베이스가 아닌 가짜 객체를 사용할 수 있습니다.
    • 이를 통해 테스트가 독립적이고 빠르게 수행될 수 있습니다.
  4. 객체 생명주기 관리:

    • 스프링 컨테이너가 객체의 생명주기를 관리하므로, 객체 생성 및 소멸에 대한 걱정을 덜 수 있습니다.
    • 스프링이 객체의 생성, 초기화, 소멸을 관리합니다.

@Autowired 예시

다음은 @Autowired를 사용한 의존성 주입 예시입니다:

StudentRepository 인터페이스

package repository;

import model.Student;
import org.springframework.data.jpa.repository.JpaRepository;

public interface StudentRepository extends JpaRepository<Student, Long> {
    // 추가적인 쿼리 메서드 정의 가능
}

StudentService 클래스

package service;

import model.Student;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import repository.StudentRepository;
import java.util.List;

@Service  // 스프링이 이 클래스를 서비스로 인식하도록 합니다.
public class StudentService {

    @Autowired  // 스프링이 StudentRepository를 주입하도록 합니다.
    private StudentRepository studentRepository;

    public List<Student> getAllStudents() {
        return studentRepository.findAll();
    }

    public Student getStudentById(Long id) {
        return studentRepository.findById(id).orElse(null);
    }

    public Student saveStudent(Student student) {
        return studentRepository.save(student);
    }

    public void deleteStudent(Long id) {
        studentRepository.deleteById(id);
    }
}

직접 인스턴스화와 의존성 주입의 차이

직접 인스턴스화

public class StudentService {
    private StudentRepository studentRepository = new StudentRepositoryImpl();

    // 메서드들...
}
  • 문제점:
    • 클래스가 StudentRepositoryImpl의 구체적인 구현에 강하게 결합됩니다.
    • StudentRepository의 다른 구현체로 교체하려면 StudentService 코드를 수정해야 합니다.
    • 테스트 시 가짜 객체를 주입하기 어렵습니다.

의존성 주입 사용

public class StudentService {

    @Autowired
    private StudentRepository studentRepository;

    // 메서드들...
}
  • 장점:
    • 클래스가 인터페이스에만 의존하므로 결합도가 낮아집니다.
    • 다양한 구현체를 유연하게 주입할 수 있습니다.
    • 테스트 시 가짜 객체를 주입하기 쉽습니다.

요약

의존성 주입을 통해 클래스 간의 결합도를 낮추고, 코드의 유연성, 테스트 용이성 및 유지보수성을 높일 수 있습니다. 스프링 프레임워크는 @Autowired 어노테이션을 사용하여 이러한 의존성 주입을 간편하게 지원합니다. 직접 객체를 생성하는 방식보다 의존성 주입을 사용하는 것이 더 좋은 이유는, 코드의 확장성과 재사용성을 높이고, 객체 간의 의존성을 관리하는 데 도움이 되기 때문입니다.

0개의 댓글