반응형

전체 글 169

Spring Data JDBC로 단순한 영속성 계층 설계하기

목차개요Spring Data JDBC의 핵심 철학핵심 구성 요소와 동작 원리실제 프로젝트 적용: 도메인 모델 구현성능 특성과 JPA 비교 분석운영 환경에서의 고려사항맺음말개요문제 배경: 영속성 계층의 복잡성Spring 기반 애플리케이션에서 데이터 접근 계층을 설계할 때 가장 먼저 떠오르는 선택지는 JPA, 그 중에서도 Hibernate입니다. JPA는 객체-관계 매핑(ORM)의 사실상 표준으로 자리잡았고, 복잡한 도메인 모델을 데이터베이스에 투명하게 매핑해 주는 강력한 도구입니다. 그러나 실제로 프로젝트에서 JPA를 어느 정도 사용하다 보면 예상치 못한 복잡성에 직면하게 됩니다. 영속성 컨텍스트의 상태 변화, 지연 로딩으로 인한 LazyInitializationException, N+1 쿼리 문제, 연쇄..

Temporal vs Kafka — 오케스트레이션과 이벤트 스트리밍 선택 기준

목차비교가 성립하는 지점과 아닌 지점전달 모델의 차이순서·재시도·상태를 다루는 방식같은 요구를 각각 어떻게 푸는가함께 쓰는 구성맺음말비교가 성립하는 지점과 아닌 지점"비동기 처리는 Kafka로 하면 되는데 Temporal이 왜 필요한가"라는 질문을 자주 만납니다. 두 도구 모두 요청을 받아 나중에 처리하고, 실패하면 다시 시도하게 해 주기 때문입니다.먼저 정리하면, Kafka는 이벤트를 저장하고 나눠 주는 로그이고, Temporal은 한 건의 처리 흐름을 끝까지 책임지는 오케스트레이터입니다. 겹치는 부분은 "비동기로 넘긴다"는 표면적인 모양뿐이고, 그 아래 책임 범위는 다릅니다.각자가 해결하는 문제문제KafkaTemporal발생한 사실을 여러 소비자에게 나눠 주기잘함하지 않음대량 이벤트를 높은 처리량으로..

Hibernate 2차 캐시와 Query Cache로 JPA 반복 조회 성능 높이기

목차개요Hibernate 캐시 계층 구조 이해2차 캐시 설정과 구현Query Cache 적용 방법성능 특성과 대안 비교운영 환경 적용 시 고려사항맺음말개요문제 배경: JPA 반복 조회의 성능 병목JPA와 Hibernate를 사용하는 프로젝트에서 가장 빈번하게 마주치는 성능 병목 중 하나는, 변경 빈도가 낮은 데이터를 트랜잭션마다 반복해서 데이터베이스에서 가져오는 패턴입니다. Hibernate 2차 캐시(Second Level Cache)와 Query Cache는 이 문제를 JPA 레이어에서 직접 해결하는 메커니즘으로, 애플리케이션 코드를 거의 수정하지 않고도 반복 조회 성능을 수 배에서 수십 배까지 끌어올릴 수 있습니다. 이 글에서는 두 캐시의 동작 원리, 설정 방법, 그리고 운영 환경에서 안전하게 적용..

Temporal vs Spring Batch — 대량 처리와 장기 흐름의 선택 기준

목차두 도구가 서 있는 자리실행 모델 비교실패와 재시작을 다루는 방식처리량과 건당 비용선택 기준과 함께 쓰는 구성맺음말두 도구가 서 있는 자리"야간에 도는 정산 처리를 Spring Batch로 짤까 Temporal로 짤까"는 자주 나오는 질문입니다. 둘 다 여러 단계를 순서대로 실행하고, 실패하면 다시 돌릴 수 있게 해 주기 때문입니다.그런데 두 도구의 출발점은 다릅니다. Spring Batch는 "많은 데이터를 한 번에 처리하는" 문제를, Temporal은 "한 건의 처리를 오래 이어 가는" 문제를 풉니다. 이 차이를 기준으로 삼으면 대부분의 선택이 정리됩니다.배치 프레임워크 쪽 구조는 앞서 Tasklet부터 파티셔닝까지 한 편으로 정리한 적이 있으니, 배치 쪽 용어가 낯설다면 그 글을 먼저 보시는 편..

PostgreSQL RLS로 멀티테넌트 데이터 격리 구현하기

목차개요RLS 동작 원리와 핵심 구조RLS 정책 설계와 구현멀티테넌트 격리 패턴 심화성능 특성과 대안 기술 비교운영 환경 적용 시 고려사항맺음말개요문제 배경: 하나의 데이터베이스, 여러 고객멀티테넌트 SaaS 아키텍처에서 가장 까다로운 문제 중 하나는 단일 데이터베이스 내에서 고객(테넌트)별 데이터를 완전히 격리하는 일입니다. PostgreSQL의 Row-Level Security(RLS)는 이 문제를 데이터베이스 엔진 수준에서 해결하는 메커니즘으로, 애플리케이션 코드가 WHERE 절을 빠뜨리거나 잘못 작성하더라도 데이터 유출이 발생하지 않도록 강제합니다. 이 글에서는 RLS의 내부 동작 원리부터 운영 환경에서의 실제 적용 패턴까지, 중급 이상의 백엔드 개발자가 현업 프로젝트에 바로 적용할 수 있는 수준..

Argo Rollouts로 Kubernetes 카나리·블루그린 배포 자동화하기

목차개요Argo Rollouts 핵심 개념과 아키텍처카나리 배포 구현블루그린 배포 구현분석 지표 기반 자동 프로모션운영 환경 적용 시 고려사항맺음말개요문제 배경: 배포는 왜 여전히 두려운가Kubernetes가 컨테이너 오케스트레이션의 표준으로 자리잡은 지 오래지만, 배포 자체의 위험성은 오히려 복잡도와 함께 증가하는 경향이 있습니다. 서비스 규모가 커질수록 단 하나의 잘못된 배포가 수만 명의 사용자에게 영향을 미치며, 롤백까지 걸리는 시간 동안 비즈니스 손실이 누적됩니다. 이 때문에 많은 팀이 "언제 배포하느냐"보다 "어떻게 배포하느냐"에 훨씬 더 많은 고민을 쏟습니다. Argo Rollouts는 이 고민에 대한 구체적인 해답으로, Kubernetes 네이티브 방식으로 카나리·블루그린·실험적 배포를 자동..

Temporal과 DB 트랜잭션 — 워크플로우 상태와 정합성 맞추기

목차두 개의 진실 원천이 생긴다이중 쓰기가 발생하는 세 자리워크플로우 시작과 커밋의 순서액티비티 안의 트랜잭션 경계조회 모델과 최종 일관성맺음말두 개의 진실 원천이 생긴다Temporal을 도입하면 시스템에 상태 저장소가 하나 늘어납니다. 서비스의 DB에는 주문이 있고, Temporal의 히스토리에는 그 주문을 처리하는 워크플로우가 있습니다. 둘은 서로를 모르고, 같은 트랜잭션으로 묶이지도 않습니다.이 사실을 인정하고 설계를 시작하는 것이 중요합니다. "워크플로우 시작과 주문 저장을 원자적으로 처리하고 싶다"는 요구는 분산 트랜잭션 요구와 같은 모양이고, 같은 방식으로만 풀립니다.무엇이 어디에 있나정보사는 곳조회 방법주문 내용·금액서비스 DBSQL처리가 몇 단계까지 갔나Temporal 히스토리워크플로우 조..

Loki와 Promtail로 Kubernetes 로그 집계 파이프라인 구축하기

대 금지 || 사용자 ID | user_id="12345" | 매우 높음 | ❌ 절대 금지 |권장 전략은 namespace, app, env, level 정도로 레이블을 최소화하고, Pod 이름이나 요청 ID 같은 고변동 값은 레이블이 아닌 로그 본문에 포함시키는 것입니다. 로그 본문은 인덱싱되지 않으므로 카디널리티 문제가 발생하지 않습니다. 검색 시에는 레이블로 스트림을 좁힌 뒤 |= "trace_id=abc-def" 처럼 텍스트 필터로 찾으면 됩니다.파이프라인 스테이지와 로그 파싱Promtail의 파이프라인은 수집된 로그를 Loki에 전송하기 전에 변환, 파싱, 필터링하는 처리 단계입니다. JSON 형식의 구조화된 로그를 처리할 때는 json 스테이지로 필드를 추출하고 레이블로 승격시킬 수 있으며, ..

Temporal Spring Boot 연동 — 워커 구성과 의존성 주입 기준

목차스타터가 해 주는 일과 해 주지 않는 일설정과 워커 구성의존성 주입이 갈리는 지점테스트 구성배포와 종료에서 걸리는 것들맺음말스타터가 해 주는 일과 해 주지 않는 일Temporal Java SDK만으로도 Spring Boot 애플리케이션에 워커를 띄울 수 있습니다. WorkflowServiceStubs, WorkflowClient, WorkerFactory를 직접 만들어 @Bean으로 등록하면 됩니다. 그런데도 스타터를 쓰는 이유는 연결·워커·등록·종료의 수명 주기를 스프링 컨텍스트에 맞춰 주기 때문입니다.주의할 점 하나를 먼저 짚습니다. Spring Boot 스타터는 워크플로우 구현 클래스에 스프링 빈을 주입해 주지 않습니다. 이것은 스타터의 한계가 아니라 Temporal의 실행 모델에서 나오는 성질..

Bounded Context와 Context Map으로 마이크로서비스 경계 설계하기

목차개요Bounded Context의 개념과 내부 구조Context Map으로 서비스 관계 설계하기마이크로서비스 경계 도출 과정구현 예제: 주문 시스템의 Bounded Context 분리운영 환경 적용 시 고려사항맺음말개요문제 배경마이크로서비스 아키텍처를 설계할 때 가장 어려운 질문은 "서비스를 어떻게 나눌 것인가?"입니다. 기능 단위로 나눌 것인지, 팀 단위로 나눌 것인지, 데이터베이스 테이블 단위로 나눌 것인지—기준이 불분명하면 잘못된 경계로 인해 서비스 간 결합도가 높아지고, 결국 분산 모놀리스(Distributed Monolith)라는 최악의 결과를 낳습니다. Domain-Driven Design(DDD)의 Bounded Context와 Context Map은 이 질문에 구조적인 답을 제시합니다...

카테고리 없음 2026.09.21
반응형