목록2025/01 (10)
HJW's IT Blog
3계층 아키텍처 vs 클린 아키텍처 비교표비교 항목3계층 아키텍처 (Three-Tier Architecture)클린 아키텍처 (Clean Architecture)구조Presentation (UI) 계층 Business Logic (Service) 계층 Data (Repository) 계층Entities (도메인 모델) Use Cases (비즈니스 로직) Interface Adapters (Controller, Presenter, Gateway) Frameworks & Drivers (DB, UI, External API)주요 개념계층별 역할을 나누어 관심사 분리의존성 방향을 내부(core)로 향하게 하여 높은 유지보수성과 테스트 용이성 제공의존성 흐름UI → Service → Repository (하위 ..
들어가며..이 글은 Spring Framework 없이 순수 Java로 프로젝트를 진행하며, 나의 사고 과정을 기록하고, 어떻게 이런 설계에 도달했는지를 설명하기 위해 작성된 글이다. 특히 User, Message, Channel과 관련된 Service Layer, Repository Layer 그리고 이들 간의 의존성 관리를 어떻게 설계했는지에 대한 고민과 해결 과정을 담고 있다.개요User, Message, Channel 에 대한 Service Layer, Repository Layer 와 이들 사이의 의존성 관리를 다루는 미션을 수행하는 과정에서의 일이다.1. 도메인별 팩토리 + 하드코딩된 의존성1.1 초기 구조처음 설계 단계에서는 SOLID 원칙을 준수하기 위해 Factory Pattern을 도입..
1. Class Loader SystemJVM 의 Class Loader 는 Java 프로그램 실행 시 필요한 클래스를 동적으로 로드하는 역할을 한다. 즉, 프로그램 실행시 모든 클래스를 한번에 메모리에 올리는 것이 아닌, 특정 클래스가 필요할 때 해당 클래스 파일을 로드하고 초기화 시키기에 메모리 낭비를 막을 수 있다. `Class Loader` 는 기본적으로 loading - linking - initialization 의 과정을 거친다. 자세히 알아보자 1.1 Loading이 과정에서, 클래스 파일이 로드된다. 클래스 로더는 특정 클래스의 이름을 기반으로 클래스를 찾고, JVM 메모리에 읽어들인다. 이 과정속, 클래스 로더는 주요 3가지 로더를 거치는데, 이들은 계층형 구조를 띄며, 상위 로더가 실..
들어가며HTTP Post 메서드는 기본적으로 멱등성(idempotence)이 보장되지 않는 메서드 이다. 여기서 멱등성이란 같은 요청이 여러번 반복되어 실행되더라도 결과가 변하지 않는 속성을 의미한다.예를 들어 클라이언트가 웹 양식을 서버에 제출하고, 서버는 이에 대한 응답을 보냈다고 가정하자. 이 상태에서 클라이언트가 웹페이지를 새로고침 한다면 어떻게 될까?바로 전과 같은 양식으로 동일한 데이터를 서버로 보낸다위와 같은 상황이 발생하면, 동일한 개시글 업로드, 중복된 결재 등의 문제를 야기할 수 있다.PRG Pattern 이란?PRG 는 Post / Redirect / Get 의 약어이다. 위와 같은 상황에서 데이터 중복 문제를 방지하기 위한 디자인 패턴으로 흐름은 다음과 같다.사용자가 POST 요청을..
들어가며현대 소프트웨어 개발에서 멀티스레드 프로그래밍은 빠질 수 없는 핵심 주제중 하나이다. 여러 스레드가 하나의 프로그램을 구성하여 조작할 때, 여러 이점이 있지만, 동시성 문제, 일관성 등의 문제또한 야기한다.본격적으로 Volatile 에 대해 이야기 하기 전, 변수 가시성 에 대해 이해하고 넘어가야 한다. 변수 가시성 문제 란 하나의 스레드가 특정 변수의 값을 변경 했을 때, 다른 스레드에서 그 변경 사항을 즉각적으로 확인하지 못하는 상황을 의미한다. 다음 코드를 한번 보자class SharedResource { private boolean flag = false; public void setFlagTrue(){ this.flag = true; } public void waitForFlag()..
들어가며빌더 패턴은 왜 써야 할까? 이 질문은 빌더 패턴을 공부하는 과정에서 끊임없이 던졌던 핵심 의문이었다. 개발자로서 중요한 덕목 중 하나는 무언가를 선택하고 사용할 때 그에 대한 명확한 “이유”를 가져야 한다는 것이다. 단순히 “빌더 패턴이 좋다고 하니까”라는 이유로 사용한다면, 나중에 누군가 “빌더 패턴을 왜 사용하셨나요?”라고 물었을 때 설득력 있는 대답을 하기 어려울 것이다.0. 빌더 패턴의 배경1.1 점층적 생성자 패턴의 한계점층적 생성자 패턴은 객체 생성을 위한 전통적인 방식이다. 이 패턴의 구조는 다음과 같다.public class Pizza { private final String dough; // 필수 private final String sauce; //..
들어가며..디스코드 시스템을 설계하고 구현하는 도중, 각 서버의 Channel 설계에 대해 고민을 하게 되었다.처음 “Channel”을 설계할 때, 이 엔티티(혹은 객체) 하나에 음성 채널과 채팅 채널을 모두 담을 것인지가 가장 큰 고민이었다.음성 채널: 음성 통화를 위한 기능이 필요하고, 채팅 메시지는 필요 없다.채팅 채널: 채팅 메시지가 필수이고, 음성 통화는 필요 없다.만약 둘을 하나의 부모 클래스로 묶는다면, 잘못하면 음성 채널에 채팅 기능이 들어가야 하고 채팅 채널에서 음성 채팅을 지원해야 하는 상황이 발생할 수도 있다. “서버의 채널”이라는 점에서는 같지만, 내부 동작과 필요한 기능이 전혀 다르기 때문이다.이러한 고민 속에서 나온 아이디어가 ChannelBehavior라는 인터페이스를 둬서, ..
들어가며DispatcherServlet은 Spring의 핵심 요소중 하나이다. DispatcherServlet은 Spring의 프론트 컨트롤러로서, 모든 웹 요청의 진입점 역할을 담당한다. HTTP 요청을 가장 먼저 받아 적절한 컨트롤러로 위임하는 것이 주 역할이다. DispatcherServlet과 Spring의 동작 과정을 잘 이해하기 위해선 프론트 컨트롤러 패턴의 개념과 장점에 대해 확실하게 짚고 넘어가야 한다.1. 초기 웹 어플리케이션 개발의 문제점초기 웹 어플리케이션 개발에선, 각 요청에 대해 개별적으로 처리하는 서블릿 혹은 JSP 를 작성하는 것이 일반적이었다. 한번 JSP 코드를 한번 보고 넘어가자. members = memberRepository.findAll();%>메인 i..
1. 상속은 무엇인가?Inheritance 는 간단히 말해 부모 클래스의 기능과 속성을 자식 클래스가 물려받는 관계이다. 예를 들어 다음과 같은 상황이 상속이다.class Animal{ void eat() { System.out.println("Eating..."); }}public class Cat extends Animal{ public void meow(){ System.out.println("meow"); }}public class Main { public static void main(String[] args) { Cat cat = new Cat(); cat.eat(); cat.meow(); }} 이와 같이 Cat 에는 분..
들어가며 SRP, 어디까지 적용되어야 할까.. 는 코드를 작성할 때 항상 고민하던 부분 같다. 과도하게 분리하게 되면 오히려 복잡도와 가독성이 떨어지는 것 같고, 분리를 하지 않는다면 하나의 메소드 혹은 클래스가 너무 많은 책임을 지는 것 같았다.예를 들어 UserManager 라는 클래스가 있다면. 이 클래스의 책임 범위는 어디까지 일까?사용자에 관련된 모든 기능?간단한 CRUD?Login, Logout 까지만?명확한 답을 내리기 힘든 질문 인 것 같다. 첫생각 public class UserManager { public void createUser() { ... } public void updateUser() { ... } public void deleteUser() { ... ..