반응형
Notice
Recent Posts
Recent Comments
Link
일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | 3 | 4 | 5 | 6 | 7 |
8 | 9 | 10 | 11 | 12 | 13 | 14 |
15 | 16 | 17 | 18 | 19 | 20 | 21 |
22 | 23 | 24 | 25 | 26 | 27 | 28 |
29 | 30 | 31 |
Tags
- Visual Studio 패키지에 실패했습니다.
- Visual Studio 재설치
- Nginx Reverse Proxy
- .NET Core
- Visual Studio 2015 강제 삭제
- 웹 크롤링
- Tomcat Error
- tomcat
- Vue configureWebpack
- Visual Studio 2015 삭제
- Vue.config
- vue.js
- Visual Studio 2015 설치
- javascript
- vue3
- Visual Studio 강제 삭제
- 디자인 패턴 사례
- 웹 자동화
- Vue3 configureWebpack
- spring
- MSSQL 동적 쿼리
- .NET Core Proxy
- Selenium 환경
- 업무 자동화
- MSSQL 문자열
- 리버스 프록시 예제
- vue
- SQLP
- Selenium 설치
- 프록시 예제
Archives
- Today
- Total
금백조의 개발 블로그
[디자인 패턴]전략 패턴(Strategy Pattern) 실사용 사례 본문
디자인 패턴(Design pattern)/전략 패턴(Strategy Pattern)
[디자인 패턴]전략 패턴(Strategy Pattern) 실사용 사례
금백조 2023. 9. 20. 20:54반응형
서론
각 구현 클래스에서 Exception이 발생할 경우 로그를 생성하는 CreateLog 클래스가 존재했습니다.
로그가 생성될 때 구현 클래스의 종류에 따라 서비스 상태를 업데이트 해야하는 로직이 필요했습니다.
이를 위해 전략 패턴(Strategy Pattern)을 적용한 사례를 글로 써봅니다.
본론
상황
- 아래의 A,B,CService 클래스가 CreateLog클래스를 참조하여 로그를 생성하고 있다.
요구사항
- CreateLog 클래스에서 각 서비스의 상태를 업데이트해야 하는 로직을 구현해야한다.
public class AService {
public void doSomeThing(){
//AService 구현 로직...
try{
} catch (Exception e){
new CreateLog().doCreateLog();
}
}
}
public class BService {
public void doSomeThing(){
//BService 구현 로직...
try{
} catch (Exception e){
new CreateLog().doCreateLog();
}
}
}
public class CService {
public void doSomeThing(){
//CService 구현 로직...
try{
} catch (Exception e){
new CreateLog().doCreateLog();
}
}
}
public class CreateLog(){
public void doCreateLog(){
//로그 생성 로직...
}
}
전략 패턴을 사용하지 않는다면?
- 구현 클래스의 종류를 파악하기 위해 구분하는 파라미터를 전달해야 하고 if else 문으로 분기처리를 해야한다. 이를 클래스 다이어그램, 구현 코드로 보면 아래와 같다.
클래스 다이어그램
구현 코드
public class AService {
public void doSomeThing(){
//AService 구현 로직...
try{
} catch (Exception e){
new CreateLog("AService").doCreateLog();
}
}
}
public class BService {
public void doSomeThing(){
//BService 구현 로직...
try{
} catch (Exception e){
new CreateLog("BService").doCreateLog();
}
}
}
public class CService {
public void doSomeThing(){
//CService 구현 로직...
try{
} catch (Exception e){
new CreateLog("CService").doCreateLog();
}
}
}
public class CreateLog(){
private String serviceName;
public CreateLog(){
}
public CreateLog(String serviceName){
this.serviceName= serviceName;
}
public void doCreateLog(){
//로그 생성 로직...
//테이블 상태 업데이트
if(serviceName == "AService"){
AServiceUpdateStatus();
} else if(serviceName == "BService"){
BServiceUpdateStatus();
} else if(serviceName == "CService"){
CServiceUpdateStatus();
}
}
public void AServiceUpdateStatus(){
System.out.println("A서비스 상태 업데이트");
}
public void BServiceUpdateStatus(){
System.out.println("B서비스 상태 업데이트");
}
public void CServiceUpdateStatus(){
System.out.println("C서비스 상태 업데이트");
}
}
단점
- 새로운 서비스가 추가될 때 마다 if else 분기처리 로직에 추가를 해줘야한다. 즉 서비스가 추가될 때 마다 CreateLog클래스도 수정을 해야한다. 이는 객체 지향 설계 5원칙(SOLID) 중 확장에 유연하고 수정을 최소화하는 개방 폐쇄 원칙(OCP)에 위배된다.
전략 패턴(Strategy Pattern) 적용
- 각 서비스에 상태를 업데이트해야 하는 로직을 하나의 전략 인터페이스로 추상화하고 전략 객체를 구현한다. CreateLog 클래스에 각 서비스마다 호출해야할 전략 객체들을 주입한다. 이를 클래스 다이어그램, 구현 코드로 보면 아래와 같다.
클래스 다이어그램
구현 코드
전략 추상화 인터페이스 생성
public interface UpdateStatusStrategy {
void doUpdateStatus();
}
전략 객체 구현
public class AServiceUpdateStatusStrategy implements UpdateStatusStrategy {
@Override
void doUpdateStatus(){
System.out.println("A서비스 상태 업데이트");
}
}
public class BServiceUpdateStatusStrategy implements UpdateStatusStrategy {
@Override
void doUpdateStatus(){
System.out.println("B서비스 상태 업데이트");
}
}
public class CServiceUpdateStatusStrategy implements UpdateStatusStrategy {
@Override
void doUpdateStatus(){
System.out.println("C서비스 상태 업데이트");
}
}
전략 객체 주입
public class AService {
public void doSomeThing(){
//AService 구현 로직...
try{
} catch (Exception e){
new CreateLog(new AServiceUpdateStatusStrategy()).doCreateLog();//전략 주입
}
}
}
public class BService {
public void doSomeThing(){
//BService 구현 로직...
try{
} catch (Exception e){
new CreateLog(new BServiceUpdateStatusStrategy()).doCreateLog();//전략 주입
}
}
}
public class CService {
public void doSomeThing(){
//CService 구현 로직...
try{
} catch (Exception e){
new CreateLog(new CServiceUpdateStatusStrategy()).doCreateLog();//전략 주입
}
}
}
public class CreateLog(){
private UpdateStatusStrategy updateStatusStrategy;
public CreateLog(){
}
public CreateLog(UpdateStatusStrategy updateStatusStrategy){
this.updateStatusStrategy= updateStatusStrategy;
}
public void doCreateLog(){
//로그 생성 로직...
//테이블 상태 업데이트
if(updateStatusStrategy != null){
doUpdateStatus();
}
}
private void doUpdateStatus(){
updateStatusStrategy.doUpdateStatus();//전략 실행
}
}
장점
- 새로운 서비스가 추가되어도 전략 객체를 구현하고 주입만 하면 되므로 CreateLog 클래스는 수정하지 않아도 된다. 이는 OCP 원칙에 부합한다.
참고
반응형