본문 바로가기
IT 서적/Clean Architecture

SOLID 설계원칙 7장. SRP:단일 책임 원칙(Single Responsibility Principle)

by Crystal.k 2022. 3. 4.

SOLID의 목적은 중간 수준의 소프트웨어 구조가 아래와 같도록 만드는데 목적이 있다.

  • 변경에 유연하다.
  • 이해하기 쉽다.
  • 많은 소프트웨어 시스템에 사용될 수 있는 컴포넌트의 기반이 된다.

7장. SRP: 단일 책임 원칙 (Single Responsibility Principle)

콘웨이 법칙에 따른 따름 정리: 소프트웨어 시스템이 가질 수 있는 최적의 구조는 시스템을 만드는 조직의 사회적 구조의 커다란 영향을 받는다. 따라서 각 소프트웨어 모듈은 변경의 이유가 하나, 단 하나여야만 한다. (하나의 모듈은 하나의, 오직 하나의 액터에 대해서만 책임져야 한다.)

단 한 가지 일만 해야 한다는 원칙이 아니다. 오해하지 말기.

위반하는 징후들을 살펴보자.

징후 1: 우발적 중복

Employee 클래스는 세 가지 메서드 calcuatePay(), reportHours(), save()를 가진다.

  • calculatePay() : 회계팀에서 기능을 정의하며, CFO보고를 위해 사용
  • reportHours(): 인사팀에서 기능을 정의하고 사용하며 COO 보고를 위해 사용한다.
  • save(): 데이터베이스 관리자(DBA) 기능을 정의하고, CTO보고를 위해 사용한다.

이 클래스는 SRP를 위반한다.

위반하는 이유 : 세가지 메서드가 서로 다른 세명의 액터를 책임지기 때문이다.

세 메서드를 Employee라는 단일 클래스에 배치하여 세 액터가 서로 결합되어 버렸다.

발생하는 문제 : CFO팀에서 결정한 조치가 COO팀이 의존하는 무언가에 영향을 줄 수 있다. 위의 두 개 이상의 메서드가 특정 알고리즘을 공유한다고 할 경우, 특정 알고리즘이 특정 팀(ex CFO팀)에 의해약간 수정될 때 다른 팀은 해당 알고리즘을 여전히 이용하기 때문에 원하는 결과를 얻지 못하고 문제가 발생하게 된다.

문제 발생 원인 : 서로 다른 액터가 의존하는 코드를 너무 가까이 배치했기 때문에 발생한다.

해결책 : SRP는 서로 다른 액터가 의존하는 코드를 서로 분리하라고 말한다.

징후 2: 병합

소스파일이 다양하고 많은 메서드를 포함하면 병합이 자주 발생한다. 특히 메서드가 서로 다른 액터를 책임진다면 병합이 발생할 가능성은 확실히 더 높다.

많은 사람이 서로 다른 목적으로 동일한 소스 파일을 변경하는 경우에 발생한다.

예)

DBA가 속한 CTO 팀에서 데이터베이스의 Employee테이블 스키마를 약간 수정하고, 동시에 인사담당자의 팀 COO팀에서는 reportHours() 메서드의 보고서 포맷을 변경한다고 가정한다.

두 개발자가 각각 변경사항을 적용하면 서로 충돌한다. 결과적으로 병합이 발생한다.

병합에는 항상 위험이 뒤따르게 된다.

두 팀뿐만 아니라 CFO도 영향을 받게 될 것이다.

해결책 : 서로 다른 액터를 뒷받침하는 코드를 서로 분리하는 것

해결책

방법 1) 데이터와 메서드를 분리하는 방식

즉 아무런 메서드가 없는 간단한 데이터 구조인 EmployeeData 클래스를 만들어 3개의 클래스가 공유하도록 한다.

세 가지 클래스를 인스턴스화 하고 추적해야 하는 단점을 해결하는 흔한 방법이 “퍼사드 Facad 패턴”이다.

 

다른 방법 2) 업무규칙을 데이터와 가깝게 배치하는 방식을 선호하는 경우

가장 중요한 Employee 클래스에 그대로 유지하되, 덜 중요한 나머지 메서드에 대한 퍼사드로 사용할 수 있다.(HourReporer, EmployeeSaver)

여러 메서드가 하나의 가족을 이루고, 메서드의 가족을 포함하는 각 클래스는 하나의 유효 범위가 된다. 해당 유효범위 밖에서는 감춰진 멤버가 있는지 전혀 알 수 없다.

결론

단일 책임원칙은 메서드와 클래스 수준의 원칙이다.

컴포넌트 수준에서는 공통 폐쇄 원칙이 된다. 아키텍처 수준에서는 아키텍처 경계의 생성을 책임지는 변경의 축이 된다.

반응형

댓글