728x90
반응형

Java 19

[Spring] 화이트리스트(Whitelist)를 활용한 XSS 공격 철벽 방어하기

XSS란? XSS와 CSRF 개념 및 차이점 정리 XSS와 CSRF 차이점 정리신입 시절, 기술 면접을 준비하거나 보안 관련 문서를 읽을 때마다 항상 헷갈리던 두 단어가 있었습니다.바로 XSS와 CSRF입니다.둘 다 웹 해킹 기법이라는 건 알겠는데, 막상 "정확히 뭐가 달라?"라show5116.tistory.com 웹 애플리케이션을 개발할 때 빼놓을 수 없는 보안 위협 중 하나가 바로 XSS(Cross-Site Scripting)입니다.악의적인 사용자가 웹 페이지에 악성 스크립트를 삽입해 다른 사용자의 정보를 탈취하거나 비정상적인 동작을 유발하는 공격이죠. XSS를 막기 위해 같은 위험한 태그를 막는 블랙리스트(Blacklist) 방식을 종종 사용하지만, 우회 기법이 끊임없이 발전하기 때문에 완벽한 방..

Backend/Spring 2026.04.02

자바 String vs StringBuilder 비교: 불변성과 JDK 버전별 동작 원리

자바를 처음 배울 때 "String은 불변(Immutable) 객체라 + 연산자로 문자열을 더하면 메모리 낭비가 심하니 무조건 StringBuilder를 쓰세요!"라는 말을 많이 들어보셨을 거예요.저 역시 신입 시절에는 이 규칙에 강박을 가져서, 가벼운 문자열 두세 개를 합칠 때도 코드를 길게 늘여가며 StringBuilder를 썼던 기억이 납니다. 하지만 실무에서 코드를 까보고 여러 레퍼런스를 찾아보면서, 자바 컴파일러가 JDK 버전에 따라 이 + 연산을 꽤 똑똑하게 최적화해주고 있다는 사실을 알게 되었어요.오늘은 String과 StringBuilder의 근본적인 차이를 짚어보고, JDK 버전별로 문자열 더하기 연산이 내부적으로 어떻게 동작하는지 저의 경험과 함께 공유해 드릴게요!1. String과 S..

Backend/Java 2026.03.19

[Spring] 커스텀 어노테이션 4편: Lombok은 어떻게 코드를 만들어낼까? (AST 조작)

어느덧 커스텀 어노테이션 시리즈의 마지막 편입니다!1편의 기본 개념을 시작으로, 2편에서는 런타임에 메소드를 가로채는 AOP를, 3편에서는 클래스 정보를 동적으로 읽어오는 Reflection을 다루었죠. 오늘은 어노테이션 활용의 끝판왕이자, 우리가 숨 쉬듯 사용하고 있는 Lombok(@Getter, @Setter)의 동작 원리인 AST(Abstract Syntax Tree) 조작에 대해 이야기해 보려 합니다. 솔직히 말씀드리면, 4년 차인 저도 실무에서 AST를 직접 조작하는 코드를 구현하지는 않습니다.유지보수도 까다롭고 구현 난이도도 너무 높기 때문이죠.하지만 우리가 매일 쓰는 도구의 원리를 아는 것과 모르는 것은 문제 해결 능력에서 큰 차이를 만듭니다.가벼운 마음으로 "아, 롬복이 이렇게 일하는구나!..

Backend/Spring 2026.03.04

[Spring] 커스텀 어노테이션 3편: 리플렉션(Reflection)으로 메일 폼 자동 생성기 만들기

지난 2편에서는 AOP를 이용해 메소드 앞뒤에 공통 로직을 끼워 넣는 방법을 배웠습니다.하지만 가끔은 메소드 호출을 가로채는 것만으로는 부족할 때가 있습니다."객체 안에 어떤 필드가 있는지 런타임에 다 훑어서, 특정 어노테이션이 붙은 값들만 뽑아낼 수 없을까?" 하는 고민이죠. 저도 실무에서 메일 발송 기능을 구현할 때 비슷한 고민을 했습니다.메일 폼에 들어갈 데이터가 매번 달라지는데, 그때마다 수동으로 Map에 담아주는 게 너무 번거로웠거든요. 오늘은 이 문제를 리플렉션(Reflection)으로 우아하게 해결한 경험을 공유해 드릴게요.1. 리플렉션(Reflection)이란?리플렉션은 구체적인 클래스 타입을 알지 못해도 컴파일된 바이트 코드를 통해 클래스의 메소드, 필드, 어노테이션 정보를 들여다보고 조..

Backend/Spring 2026.03.03

[Spring] 커스텀 어노테이션 1편: 어노테이션의 기본 개념과 3가지 동작 원리 이

Spring으로 개발하다 보면 수많은 어노테이션을 만납니다.코드 위에 @ 하나만 붙였을 뿐인데 트랜잭션이 걸리고, JSON으로 변환되는 모습을 보면 가끔은 '마법 같다'는 생각이 들기도 하죠.저도 연차가 쌓이면서 반복되는 로직을 줄이고 싶을 때 "이걸 내가 직접 만들어서 자동화할 순 없을까?"**라는 고민을 하게 되었습니다.오늘부터 시작할 시리즈는 그 마법의 정체를 파악하고, 우리만의 지팡이(커스텀 어노테이션)를 만드는 과정을 담았습니다.그 첫 번째 시간으로 어노테이션의 본질과 이를 동작하게 만드는 3가지 방법에 대해 깊이 있게 다뤄보겠습니다.1. 어노테이션(Annotation)이란 무엇인가?사전적 의미로 어노테이션은 '주석'입니다.하지만 우리가 코드에 쓰는 // 주석과는 결이 다릅니다.일반 주석이 개발..

Backend/Spring 2026.02.27

[Java] Stream vs For 문, 무엇을 써야 할까? - 성능, 메모리, 그리고 Clean Code

지난 글에서는 Java Stream의 개념과 동작 원리에 대해 알아보았습니다.스트림은 코드를 우아하게 만들어주는 강력한 도구지만, 현업에서 코드를 짜다 보면 항상 이런 고민에 부딪힙니다."이거 그냥 For 문 돌리는 게 더 빠르지 않나?" "Stream을 남발하면 메모리 문제가 없을까?" 오늘은 개발자들 사이의 영원한 논쟁 주제인 [For 문(Enhanced For Loop) vs Stream API]를 성능, 메모리 구조(Stack/Heap), 그리고 유지보수성 관점에서 깊이 있게 비교해 보겠습니다.1. 성능: 속도는 누가 더 빠를까?결론부터 말씀드리면, 단순 반복 처리 속도는 For 문이 더 빠릅니다.왜 For 문이 더 빠를까?컴파일러 최적화: For 문은 자바 언어 탄생부터 존재한 가장 기본적인 문..

Backend/Java 2026.02.05

[Java] 자바 스트림(Stream) - 스트림의 정체와 핵심 원리

Java 8이 등장하면서 자바 생태계에는 큰 변화가 있었습니다.(물론 지금은 20번대가 등장하지만...)람다(Lambda)와 함께 등장한 스트림(Stream API)은 우리가 코드를 작성하는 스타일을 완전히 뒤바꿔 놓았죠.하지만 막상 스트림을 쓰다 보면 "이게 그냥 for문보다 편해서 쓰는 건가?", "내부적으로 어떻게 돌아가는 거지?"라는 의문이 들 때가 있습니다.이번 시리즈에서는 총 2편에 걸쳐 자바 스트림을 깊이 있게 파헤쳐 보려 합니다.1편: Stream이 무엇이며, 어떤 원리로 동작하는가? (현재 글)2편: Stream vs For 문, 성능과 Clean Code 관점에서의 비교그럼, 스트림의 세계로 들어가 보겠습니다.1. 스트림(Stream)이란 무엇인가?스트림은 자바 8부터 추가된 기능으로,..

Backend/Java 2026.02.05

[Java] 가장 효율적인 List 초기화 방법과 상황별 패턴 정리 (불변 vs 가변)

Spring 프로젝트(특히 Spring Security) 코드를 작성하다 보면 다음과 같은 형태의 코드를 자주 마주치게 됩니다.return Collections.singleton(new SimpleGrantedAuthority("ROLE_USER")); "그냥 new ArrayList를 쓰면 되지, 왜 굳이 Collections.singleton을 사용할까?"라는 의문이 드실 수 있습니다.게다가 이 반환값을 받아서 무심코 .add()를 호출했다가는 UnsupportedOperationException이라는 런타임 에러를 만나게 됩니다.오늘은 실무에서 자주 헷갈리는 Java List의 가장 효율적인 초기화 방법들과 '수정 가능(Mutable)' 여부를 명확하게 정리해 드리겠습니다.1. 불변(Immutabl..

Backend/Java 2026.02.02

[Lombok] @NonNull 완벽 가이드: 필드 vs 파라미터 적용 차이와 빌더 패턴 활용법

우리는 보통 null 체크를 위해 코드를 짤 때 if (param == null) 같은 조건문을 수없이 반복하곤 하죠.코드는 길어지고, 가독성은 떨어지고요.오늘은 이 문제를 깔끔하게 해결해 주는 Lombok의 @NonNull 어노테이션에 대해 이야기해 보려 합니다.특히 필드에 붙일 때와 메서드에 붙일 때의 차이점, 그리고 @Builder 패턴과 함께 사용할 때의 시너지를 실무 관점에서 정리해 보겠습니다.1. Lombok @NonNull이란?Lombok의 @NonNull은 말 그대로 "이 값은 절대 Null이어서는 안 돼!"라고 선언하는 것입니다.단순히 "Null이 아니면 좋겠어"라는 표시(Marking)만 하는 것이 아니라, 컴파일 시점에 자동으로 Null Check 로직을 생성해 줍니다.주의: org...

Backend/Spring 2026.02.01

[Spring] 트랜잭션은 롤백되어야 하지만, 실패 이력은 DB에 남기고 싶을 때

Spring으로 개발을 하다 보면 이런 요구사항을 마주칠 때가 있습니다."비즈니스 로직이 실패하면 데이터는 Rollback 되어야 한다. 하지만, 그 실패 원인(로그)은 DB에 저장(Commit) 되어야 한다."언뜻 보면 간단해 보이지만, Spring의 트랜잭션 전파(Propagation) 속성을 정확히 이해하지 못하면 로그까지 같이 롤백되어 사라지는 난관에 봉착하게 됩니다.오늘은 이 문제를 해결하는 가장 깔끔한 방법을 정리해 봅니다.1. 문제 상황다음과 같은 서비스 로직이 있다고 가정해 봅시다.@Service@RequiredArgsConstructorpublic class MyService { private final FailHistoryRepository failHistoryRepository;..

Backend/Spring 2026.02.01