전체 글
[우아한테크코스] LV3 - 1차 스프린트 회고
1차 스프린트에서 만난 문제상황과 해결책 소프트 스킬 데일리 미팅 개인 일정 정리 문제점 : 근로를 진행하는 크루들이 있어 workout 시간을 온전히 활용하기는 힘들다는 문제가 있었다. 해결책 : 팀 전체적으로 진행하는 회의 및 일정을 중간에 흐름이 끊기지 않게 잘 조절할 수 있었다. 서비스 기획 회의 진행 문제점 : 회의를 진행하다보면 원래 해결하기로 했던 안건에서 점점 벗어나는 경우가 발생했다. 해결책 : 팀이 해결해야할 안건을 정하고 해당 안건을 얘기하는 회의 시간을 구체적으로 미리 정해두고 회의를 진행한다. 정해진 회의 시간이 지나면 원래 얘기하기로 했던 안건에 대해 잘 논의되었는지 확인한다. 또한 회의 중간에라도 처음 안건과는 주제가 멀어지게 된다면 즉시 브레이크를 걸고 회의를 시작했던 안건을..
[우아한테크코스] 중간 회고
우아한테크코스 레벨1과 2를 지나고 3에 들어와 팀 프로젝트를 진행하고 있다. 본격적으로 프로젝트를 시작하기에 앞서 다시 헤매지 않기 위해 여태까지 해왔던 학습 방향과 생각들을 정리하고자 한다. 레벨2 막바지부터 방학 내내 이어졌던 감정에 대해 되돌아보았다. 주변 크루들에게는 '번아웃의 3분의 2지점에 서있는 듯한 기분이다' 라고 얘기를 종종 했던 것 같다. 그런데 곰곰히 생각해보면 체력적으로 부치는 건 아니었고, 뭔가 어려운 문제를 직면했던 것도 아니었다. 꽤 긴 시간 결론을 내리지 못했었는데 감정의 핵심적인 부분은 다음과 같이 정리되었다. 공부해야할 건 많은데, 궁금한 건 많은데 해야할 것들은 쏟아져 오는 상황이다. 그런데 조금 전에 공부한 것도 기억 안나고 정리해뒀던 것들을 봐도 뭘 위해 이렇게 정..
Domain 그리고 Entity, VO에 대한 개인적인 고찰
들어가면서 우테코 레벨 2에 들어와 DB를 프로젝트에 도입하게 된 이래로 지금까지 도메인을 설계하면서, 도메인 객체에서 ID를 갖는 것이 당연하다고 생각해왔다. 여태까지는 이렇다 할 복잡한 비즈니스 로직이 없었고 간단한 검증만을 필요로 할 뿐 기본적인 CRUD 기능 구현이 주된 목표였기에 도메인 설계 시 상태값으로 ID를 가지는 것이 자연스러웠다. 하지만 상대적으로 복잡한 비즈니스 로직을 가지는 지하철 미션을 진행하면서, 도메인 객체에 ID를 부여하는 것에 대해서 다시 한 번 생각하게 되었다. 다음과 같이 노선의 역과 역사이의 구간 정보를 나타내는 Section이라는 객체를 설계하고 ID를 부여했다. public class Section { private final Long id; private fina..
스프링 @Transactional(readOnly=true)에 관한 간단한 고찰
이번 레벨2 미션들을 진행하면서 @Transactional 어노테이션을 별다른 생각 없이 DB 작업을 수행하는 기능들에 대해 선언해왔다. 그러던 중 리뷰어께서 @Transactional 어노테이션의 옵션들 중에서도 readOnly 옵션에 대해 알아보면 좋겠다는 피드백이 있었어서 이에 대해 알아보고자 한다. 일반적으로 검색하면 알 수 있는 내용은 @Transactional(readOnly=true)와 같이 어노테이션 선언 시 옵션을 주게 되면 해당 기능을 수행하는 중 Create, Update, Delete 와 같이 데이터의 변경이 발생하는 작업들이 수행되는 경우 예외를 발생시킨다는 것이다. 실제로 그러한지 알아보기 위해 바로 실험을 해봤다. // 읽기 전용 트랜잭션으로 선언 @Transactional(r..
[우아한테크코스] LV2 - 웹 지하철 미션 Step2, 3 회고
들어가면서 레벨2에서 가장 어렵다고 여겨지는 지하철 미션이 모두 끝났다. 페어미션인 step1 때부터 지금까지 폭풍처럼 시간이 지나갔던 것 같다. step2, 3는 생각보다 쉽게 구현할 수 있었다. 오히려 리팩토링 기간에 가장 시간을 많이 투자한 부분은 step1 에서 설계했던 도메인 객체인 sections였다. 처음 설계할 때 외부 라이브러리인 jGrapht를 사용할 것을 염두에 두고 설계를 했었는데 이게 결과적으로 독이 되었던 것 같다. 개인적으로 당장 필요하지 않은 기능을 고려해서 설계를 진행하는 것이 오히려 더 큰 복잡함을 낳을 수 있다는 것을 새삼 깨닫게 되었다. 그리고 객체지향의 목적에 대해 다시 한 번 생각하게 되는 계기가 되는 미션이었던 것 같다. 여태까지 객체지향을 현실의 객체들에 대한 ..
[글쓰기] Level2 - 스프링을 학습하는 방법에 관한 고찰
스프링을 학습하는 방법에 관한 고찰 묻지 말고 일단 행하라 레벨2에 들어와서 코치님들이 가장 먼저 해주신 말들이 있다. 스프링이 왜 이런 방식으로 동작하는지에 집착하지 말 것. 일단 스프링을 사용해볼 것. 그다음에는 어떻게 잘 사용할 수 있는지에 대해 고민하고 학습할 것. 분명 레벨1에서는 보이는 모든 것에 의문을 품어야 한다고 배웠다. 몇 달 동안 배우고 유지해 온 방향성이 흔들리는 순간이었다. 왜 스프링의 동작 방식을 이해하려 하지 말고 일단 사용해 보라 하는 걸까? 마치 이해하지 못한 공식을 외워서 수학 문제를 푸는 것 같은 기분이었다. 코드를 작성하면서도 지금 무언가를 공부하고 있긴 한 건가 싶었다. 모니터 앞에서도 의미 없는 시간을 보내고 있다는 괴리감을 지우기 힘들었다. 왜 먼저 행해야 하는가..
스프링의 예외처리 과정 및 처리 방법에 대하여 (2)
이전 포스팅에서 이어집니다. 스프링의 예외처리 과정 및 처리 방법에 대하여 (1) 포스팅 배경 우테코 레벨2 두번째 미션인 장바구니 기능 구현을 진행하면서 로그인 인증기능을 구현하기 위해 Interceptor를 구현해서 사용하게 되었다. 이 과정에서 Interceptor 내부에서 예외를 던 makemepositive.tistory.com 스프링이 제공하는 다양한 예외처리 방법 스프링에서는 다양한 예외 처리 전략을 수행하기 위해 HandlerExceptionResolver 인터페이스를 제공한다. public interface HandlerExceptionResolver { @Nullable ModelAndView resolveException( HttpServletRequest request, HttpSe..
스프링의 예외처리 과정 및 처리 방법에 대하여 (1)
포스팅 배경 우테코 레벨2 두번째 미션인 장바구니 기능 구현을 진행하면서 로그인 인증기능을 구현하기 위해 Interceptor를 구현해서 사용하게 되었다. 이 과정에서 Interceptor 내부에서 예외를 던져야할 필요성이 생겼는데 여기서 발생하는 예외는 어떻게 처리해야할지 고민하다 스프링의 전체적인 예외 처리 과정이 궁금해졌다. 스프링에서 예외를 처리하는 전체적인 흐름을 살펴보고 어떻게 미션에서 발생했던 문제를 해결할 수 있었는지 정리해보고자 한다. 우리가 직접 구현한 Controller에서 발생하는 Exception들은 어떻게 처리될까? Spring은 기본적인 에러 처리를 위한 BasicErrorController를 구현해뒀다. 이로 인해 별도의 추가 설정이 없다면 스프링 부트는 예외가 발생했을 때 ..