최근 진행했던 프로젝트에서 동시성 제어를 해결해야 했다. 자바에서 동시성 제어를 위해 제공하는 건 세 가지 방법이 있다. 첫째, synchronized, 둘째, Atomic variable, 셋째, volatile. 나는 이 중 Atomic variable을 사용했는데, 왜 Atomic Variable을 사용했는지 이유를 정리해보고자 한다. 나름의 리서치를 통해 Atomic Variable을 사용하긴 했지만 반드시 Atomic Variable을 사용해야 한다고 주장하는 글도 아니다. 성능 저하를 막기 위해 가장 일반적으로 알고 있는 synchronized 같은 경우는 가장 안전하다고 알려져 있지만, 성능 저하가 발생한다는 단점이 있다. 현재는 스케줄로 동작하지만 내가 작업한 부분의 경우, 후에 대규모 호..
비밀글로는 아직 정리가 덜 된 글을 몇 개 올리긴 했지만, 공개글로는 그동안 거의 글을 올리지 않았다. 그래서 간단히 그동안 내게 있었던 일들을 정리해본다. 1. 코로나 확진 평소처럼 감기일거라고 생각했는데, 혹시 몰라 받은 코로나 검사에서 확진되었다. 아침에 확진문자받는데 나도 내가 확진이라고 하니 놀랐고, 확진이라고 알아서 그런지 그 이후로 상태가 내내 안좋았다. 다행히 시간이 좀 지난 지금은 괜찮긴 한데, 나는 코로나 이후로 왜인지 모든 의욕을 잃어버렸다. 2. 사랑니 뽑아야지 뽑아야지 하고 있던 사랑니를 드디어 뽑았다. 아직은 오른쪽만. 코로나 격리 풀리자마자 사랑니 수술한거라 이 기간은 공부를 거의 못했다. 3. 이직에 한 걸음 더 어느 회사에서 서류전형을 통과했으니 다음 전형으로 진행하자는 연..

TASK 이번에 맡아서 개발한 부분은 A시스템에서 B시스템이 사용할 파일을 업로드받고 B시스템, C시스템으로 API 연동하여 전송, 후처리 요청까지 하는 부분이었다. 그렇게 큰 업무는 아니었지만 이 기능이 본 프로젝트를 진행하는 이유였기 때문에 중요했다. 관건은 작업 요청 목록이 여러 개 있고, 스케줄로 작업을 실행하는데 작업이 하나 이미 실행중이라면 다음 작업은 작업이 끝날 때까지 실행되지 않아야 하고, 여러 시스템과 연동하면서 발생할 예외 처리를 적절히 해주어야 한다는 것이다. 당연히 트랜잭션도 고려해야했다. 그래서 개발을 진행하며 Transaction이 시작되고 끝나기까지 내부 코드는 어떻게 돌아가는지 살펴보고(Transaction 관련 내부 코드 뜯어보기) 중첩된 @Transactional을 실험..

로그인을 거쳐야만 수행 가능한 동작을 테스트코드로 작성해서 테스트해야 하는 경우가 있다. 나의 경우 로그인하면 Session에 정보를 저장하는데, 컨트롤러에 들어가기 전 interceptor에서 권한 체크를 해준다. 이 경우 테스트코드는 아래와 같이 짜면 된다. interceptor에서 Session에 id가 존재하는지 확인하고 존재한다면 컨트롤러로 들어가 게시물 신고 취소를 진행하게 된다. 그래서 테스트를 정상적으로 수행되도록 짜려면 session에 id를 넣고 그 session도 같이 넘겨줘야하는데 위 방법이 그 방법이다.

오늘은 개인프로젝트에 @ControllerAdvice를 추가해서 유효하지 않은 파라미터를 공통으로 처리해주는 작업을 하고 있었다. 테스트코드 작성해서 테스트하는데 분명 제대로 작성했는데 @ControllerAdvice가 적용되지 않는 것이었다. @ControllerAdvice가 다른 패키지에 있었는데, 혹시나 해서 컨트롤러 안에 @ExceptionHandler 메서드만 넣으니까 잘 작동하고. 위 이미지를 비교해보면 알 수 있듯이 제대로 작동하지 않은 경우에는 DefaultHandlerExceptionResolver로 BindException이 처리됐고, 제대로 작동한 경우에는 ExceptionHandlerExceptionResolver로 처리가 됐다. DefaultHandlerExceptionResolv..

개인프로젝트를 헤로쿠에 배포해놓고 있었는데, 갑자기 저런 메일이 왔다. 세번째 줄 보면 your database credentials and hostname will have changed, but we will update your app's config variables accordingly to reflect the new database connection string. 이라고 되어 있다. 내 개인프로젝트는 헤로쿠에서 제공하는 postgresql을 사용하고 있다. 이 DB에 접근하기 위한 정보가 credentials이고. 그런데 보안때문에 credentials 변경이 발생한다는 것이다. 문제는 종료되었다는 메일이 왔는데도 내 credentials는 변경되지 않았다. 헤로쿠에 올라가있는 서버를 다시..

오늘 테스트 중에 NullPointerException이 발생하는 상황이 있었고, 아래와 같이 로그를 남기고 있었다. 아래는 단순 예시. 이렇게 로그를 남기니 아래와 같은 결과가 있었다. 그런데 NullPointerException이 어디에서 발생하는지 알아야 처리를 할 수 있는데 저 정보만으로는 처리가 어려웠다. 그래서 스택트레이스를 표시해줘야했는데 아래와 같이 변경해서 표시할 수 있었다. 결과는 아래와 같다. 그래서 문득 궁금해졌다. Exception의 최상위인 Throwable은 toString()을 어떻게 정의하고 있는지, 로그에서는 e와 e.toString()을 어떻게 처리하는지. 그래서 코드를 뜯어봤다! 참고로 로그 라이브러리로 logback을 사용하고 있다. 위의 메서드를 먼저 살펴봤다. L..
NOR게이트 두 개가 연결되어 있다고 하자. 한 NOR게이트의 출력은 다른 NOR게이트의 입력으로 들어가고, 다시 그 게이트의 출력은 첫번째 NOR게이트의 입력으로 들어간다. 간단히 나타내기 위해 1번 게이트, 2번 게이트라고 하자. 1번 게이트와 2번 게이트에는 입력으로 연결된 스위치가 있다. 1번 게이트에 연결된 스위치를 닫게 되면 게이트의 입력으로 1이 들어가게 되어 2번 게이트의 입력으로 출력인 1이 들어가게 된다. 그러면 2번 게이트는 1이라는 출력을 갖게 되고(NOR게이트이기 때문) 그 출력은 다시 1번 게이트의 입력으로 들어가게 되어 결과적으로 출력이 연결된 전구에 불이 들어오게 된다. 이때, 1번 게이트에 연결된 스위치를 떼더라도 1이라는 입출력이 회로에서 반복되기 때문에 불은 계속 켜져 ..