본문 바로가기

전체 글52

[ Spring Boot ] 주문은 저장됐는데 이벤트는 사라졌다? 트랜잭셔널 아웃박스 패턴 주문을 저장하고, 다른 서비스에 주문이 생성되었다고 알려준다고 가정해보겠습니다. ( 갑작스러운 공격!!! )@Transactionalpublic void createOrder(CreateOrderRequest request) { Order order = orderRepository.save(request.toEntity()); eventPublisher.publish(new OrderCreated(order.getId()));}DB에도 저장하고 이벤트도 발행했습니다.그런데 여기서 조금 불안한 부분이 있습니다.“이벤트 발행은 성공했는데, DB 커밋이 실패하면?”“DB부터 커밋하고 보내면 안전한가?”흠.. 순서를 바꾸는 것만으로는 해결되지 않습니다.이번에는 DB 변경과 이벤트 발행 사이에서 생기는.. 2026. 10. 4.
[ 네트워크 ] TCP로 두 번 보냈는데, 왜 한 번에 읽힐까? 오늘은 미루고 미루던 네트워크입니다.. ㅠㅠ 우선 소켓 통신을 만든다고 가정해보겠습니다.보내는 쪽에서 HELLO와 WORLD를 따로 전송했습니다.out.write("HELLO".getBytes(StandardCharsets.UTF_8));out.write("WORLD".getBytes(StandardCharsets.UTF_8));out.flush();받는 쪽에서도 두 번 읽으면 하나씩 나오겠죠?흠.. TCP에서는 그렇게 약속하지 않습니다.한 번에 HELLOWORLD가 읽힐 수도 있고, HEL, LOWO, RLD처럼 나뉘어 읽힐 수도 있습니다.“TCP는 순서를 보장한다면서 왜 섞여서 오는 거지?”이번에는 바이트의 순서와 메시지의 경계를 구분해보겠습니다!TCP가 전달하는 것은 바이트 스트림이다위에서 가능한 .. 2026. 9. 30.
[ Java / Spring Boot ] @Bean 메서드를 직접 호출했는데, 왜 같은 객체가 나올까? 오늘의 타겟은 Spring입니다. Spring Boot에서 설정 클래스를 작성하다 보면 이런 코드를 만나게 됩니다.@Configurationpublic class AppConfig { @Bean public Repository repository() { return new Repository(); } @Bean public OrderService orderService() { return new OrderService(repository()); }}repository() 안에는 분명 new가 있습니다.그런데 orderService()에서 이 메서드를 직접 호출해도, 컨테이너에서 조회한 Repository와 같은 객체가 들어갑니다.“자바 메서드를 .. 2026. 9. 29.
[ Java ] PriorityQueue에 하나씩 넣으면 O(n log n)인데, 한 번에 만들면 O(n)이라고? 지난 글에 이어서 PQ를 또 후두리찹찹 해보도록 하겠습니다. 우선순위 큐를 처음 채울 때 보통 이렇게 작성합니다.PriorityQueue pq = new PriorityQueue();for (int value : values) { pq.offer(value);}원소 하나를 넣을 때 힙을 조정하는 비용이 O(log n)이니까, n개를 넣으면 최악 O(n log n)입니다.그런데 이미 리스트에 값이 모여 있다면 이렇게도 만들 수 있습니다.List values = Arrays.asList(7, 6, 5, 4, 3, 2, 1);PriorityQueue pq = new PriorityQueue(values);이 경로의 힙 구성은 O(n)입니다.“같은 값을 넣는데, 생성자로 넘기면 더 싸다고?”(생성자가 반복.. 2026. 9. 28.
[ Java ] PriorityQueue에 넣은 값을 바꿨는데, 왜 꺼내는 순서는 그대로일까? 코테를 풀다 보면 우선순위 큐를 자주 사용하게 됩니다. 작은 값부터 꺼내고 싶으면 PriorityQueue에 넣고, poll()로 하나씩 꺼내면 되죠. 그런데 객체를 넣었다면? 그리고 큐에 넣은 뒤에 그 객체의 우선순위를 바꿨다면? “값이 작아졌으니까 알아서 먼저 나오겠지?” ( 4개월 전 작성자의 크나큰 실수.. ) 흠..? 정말 그렇게 동작하는지 살펴보겠습니다!분명 1로 바꿨는데, 10이 먼저 나온다숫자가 작을수록 먼저 처리하는 작업 큐를 만들어보겠습니다.import java.util.Comparator;import java.util.PriorityQueue;public class PriorityQueueMutationDemo { static class Task { final Str.. 2026. 9. 27.
[ MySQL ] 인덱스를 두 컬럼에 걸었는데, 왜 정렬은 따로 할까? 오늘도 찾아온 끄적끄적 공부기록..조회 성능 좀 개선해보고자 인덱스를 공부하며 적용 시켜보고있는데 홰 복합 컬럼이 이따구로 동작하는가에 대해 의문을 갖고 시작했습니다. 우선 게시글 목록을 조회한다고 가정해보겠습니다.카테고리로 검색하고, 작성 시간으로 정렬하니까 인덱스도 이렇게 만들면 될 것 같습니다.CREATE INDEX idx_category_createdON posts (category_id, created_at);그런데 실행 계획을 보니 이런 문구가 나타납니다.Using filesort“인덱스는 정렬되어 있다면서?”“검색하는 컬럼이랑 정렬하는 컬럼까지 다 넣었는데?”흠.. 인덱스에 컬럼이 포함되어 있다는 것만으로는 부족합니다. 어떤 순서로 정렬되어 있는지까지 봐야 합니다.이번에는 복합 인덱스의 순.. 2026. 9. 27.