Java 스레드

기본 소개 Java에서는 경합 상태일 때 데이터의 정합성을 보장하기 위해 스레드 동기화로 한 번에 하나의 스레드만 공유 자원에 접근할 수 있도록 한다. 이를 구현하기위해 Java에서는 각 인스턴스들이 자신의 Monitor를 가지게하고, 스레드가 이 인스턴스를 사용할 때 Monitor를 점유하도록 한다. 이 Monitor는 하나의 스레드만 점유할 수 있기때문에, 다른 스레드들은 Wait Queue에서 기다리게 된다. (synchronized 키워드를 사용하면 점유하게된다) Java 스레드에는 ‘데몬 스레드(daemon thread)’와 ‘일반 스레드(non-daemon thread)’가 있다. 데몬 스레드: 백그라운드로 실행되고, 일반 스레드가 모두 종료되면 데몬 스레드의 의미가 사라지기 때문에 강제적으로 자동 종료된다....

2024-09-15 · 2 min · 249 words

Java 버전 명시

sourceCompatibility 와 targetCompatibility 를 사용하면된다. sourceCompatibility: .java 파일을 컴파일 할 때 사용할 Java 프로그래밍 언어의 버전. targetCompatibility: 생성 될 클래스파일이 호환되어야 하는 VM의 버전. 기본적으로 source와 같은 값이 되므로 같다면 명시해줄 필요가 없다. 참고 자료 https://docs.gradle.org/3.3/userguide/java_plugin.html#sec:java_convention_properties https://www.cloudhadoop.com/gradle-configure-java-version/

2024-09-15 · 1 min · 37 words

Java 메서드 파라미터의 final 자동으로 붙이기

2024-09-15 · 0 min · 0 words

Jacoco와 소나큐브 연결

build.gradle에 다음을 추가하면 소나큐브의 테스트 커버리지가 0%인 문제가 해결된다. plugins { id 'jacoco' // any other plugins } jacocoTestReport { reports { xml.enabled true } } test.finalizedBy jacocoTestReport tasks.named('sonarqube').configure { dependsOn test } Jacoco가 자바 프로젝트의 테스트 커버리지 보고서를 생성해주는 라이브러리다. 참고 자료 https://tomgregory.com/how-to-measure-code-coverage-using-sonarqube-and-jacoco/#22_Using_the_Jacoco_Gradle_plugin

2024-09-15 · 1 min · 44 words

Jackson byte를 List 형태로 반환하는 법

List<Map<String,Object>> participantJsonList = mapper.readValue(jsonString, new TypeReference<List<Map<String,Object>>>(){}); 참고 자료

2024-09-15 · 1 min · 8 words

isLetter 사용 시 주의점

배경 문자열이 영어로만 이루어져 있는지 확인하기 위해서 isLetter 함수를 사용하면 놓칠 수 있는 문제점이 있다. fun String.onlyAlphabetChars() = this.asSequence().all { it.isLetter() } isLetter() 공식 문서를 확인해보면 isLetter()은 문자 카테고리가 UPPERCASE_LETTER, LOWERCASE_LETTER, TITLECASE_LETTER, MODIFIER_LETTER, OTHER_LETTER 중 하나면 true를 반환한다. 이런 UPPERCASE_LETTER, LOWERCASE_LETTER 등에는 단순 알파벳인 a-z, A-Z 뿐만 아니라 Ä, Ë 등도 카테고리에 포함된다. https://www.compart.com/en/unicode/category/Lu a-z, A-Z만 가능하게 만드려면 해당 함수를 사용하면 안된다. 참고 자료 https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.text/is-letter.html#kotlin.text https://www.baeldung.com/kotlin/remove-non-alphanumeric-characters https://www.baeldung.com/java-character-isletter-isalphabetic

2024-09-15 · 1 min · 67 words

IP 형태의 문자열인지 확인하는 방법

Guava 라이브러리를 사용했다. // an IPv4 address private static final String INET4ADDRESS = "172.8.9.28"; // an IPv6 address private static final String INET6ADDRESS = "2001:0db8:85a3:0000:0000:8a2e:0370:7334"; // Validate an IPv4 address if (InetAddresses.isInetAddress(INET4ADDRESS)) { System.out.print("The IP address " + INET4ADDRESS + " is valid"); } else { System.out.print("The IP address " + INET4ADDRESS + " isn't valid"); } // Validate an IPv6 address if (InetAddresses.isInetAddress(INET6ADDRESS)) { System.out.print("The IP address " + INET6ADDRESS + " is valid"); } else { System....

2024-09-15 · 1 min · 89 words

Interceptor

특정 IP만 접근 허용하기 @Override public boolean preHandle(final HttpServletRequest request, final HttpServletResponse response, final Object handler) { String clientIp = request.getRemoteAddr(); administratorService.validateIp(clientIp); } getRemoteAddr() 를 통해 현재 요청을 보낸 client의 IP를 확인할 수 있다. 특정 HTTP Method만 허용하기 @Override public boolean preHandle(final HttpServletRequest request, final HttpServletResponse response, final Object handler) { if (!"GET".equals(request.getMethod())) { throw new IllegalArugmentException(); } } getMethod() 메소드를 통해 현재 요청을 보낸 HTTP 메소드를 알 수 있다.

2024-09-15 · 1 min · 70 words

IntelliJ 테스트 코드 실행 시 프로필 지정하기

Environment variables로 설정할 수 있다.

2024-09-15 · 1 min · 5 words

InputStreamReader의 close

InputStream을 character stream으로 사용할 수 있게해주는 InputStreamReader는 close를 하게되면 내부에 가지고 있는 InputStream도 함께 close되기 때문에 주의해서 사용해야된다. https://stackoverflow.com/questions/55549248/do-i-need-to-close-inputstreamreader-even-if-inputstream-should-remain-open

2024-09-15 · 1 min · 19 words

Inner class와 Static inner class의 차이

public class Test { class InnerClass { // InnerClass } static class InnerStaticClass { // static InnerClass } } Inner class는 외부 클래스를 인스턴스화해야지 inner class도 인스턴스화가 가능하다. 하지만 static은 외부 클래스 인스턴스화 필요없이도 인스턴스화가 가능하다. static이라고해서 InnerStaticClass 인스턴스가 하나만 존재하는 것이 아니니 유의해야된다. https://velog.io/@agugu95/왜-Inner-class에-Static을-붙이는거지

2024-09-15 · 1 min · 45 words

HttpServletResopnse에 string 출력하기

response.setContentType("text/html; charset=UTF-8"); response.setCharacterEncoding("UTF-8"); PrintWriter out = response.getWriter(); getOutputStream 의 경우는 바이트 기반 스트림이기 때문에 utf-8로 제대로 인코딩하지 못하는 문제가 있다. https://stackoverflow.com/questions/1992400/how-to-send-through-servletoutputstream-characters-in-utf-8-encoding

2024-09-15 · 1 min · 21 words

HTTP1_1 vs HTTP2_0

탄생 배경 HTTP/1.1 클라이언트가 웹 서버와 정보 교환을 하기위해 만드러진 프로토콜이다. 클라이언트가 서버에게 GET이나 POST 같은 메소드와 함께 요청을 보내면, 서버는 HTML이나 이미지 같은 리소스를 다시 클라이언트에게 보낸다. 이렇게 하나의 요청과 응답을 주고 받는 과정에는 한 개의 애플리케이션 레이어 프로토콜이 사용된다고 생각하면 된다. HTTP/1.1은 아래와 같이 텍스트 기반 형식으로 메시지를 보낸다. GET /index.html HTTP/1.1 Host: www.example.com HTTP/2 Google에서 개발한 SPDY라는 프로토콜을 기반으로 시작되었다. HTTP/2는 압축, 멀티플렉싱, 우선 순위 지정과 같은 기술을 사용해 웹 페이지의 로딩 시간을 줄였다....

2024-09-15 · 5 min · 1021 words

HTTP SameSite 쿠키

목표 SameSite 쿠키가 무엇인지 이해한다. SameSite 쿠키의 정책들을 이해한다. SameSite 쿠키 HTTP 쿠키에 사용할 수 있는 속성으로 cross-site로 요청을 보낼 때 해당 쿠키를 보낼 수 있을지 설정할 수 있다. CSRF 공격에 대한 대응으로 사용할 수 있는 속성이다. SameSite 속성의 쿠키를 설정하려면 아래와 같이 명시하면 된다. Set-Cookie: <cookie-name>=<cookie-value>; SameSite=Strict SameSite 정책 Strict: 크로스 사이트 요청에 항상 전송하지 않는다. 퍼스트 파티 쿠키만 전송된다. Lax: 이미지나 iframe 에서는 크로스 사이트에 전송하지 않지만, 해당 사이트로 이동할 때 쿠키가 전송된다....

2024-09-15 · 1 min · 101 words

HTTP Client 인터페이스

목표 Spring 6의 HTTP Client 인터페이스가 무엇인지 이해한다. Spring 6의 HTTP Client 인터페이스의 사용법을 이해한다. HTTP Client 인터페이스 Spring Framework 6와 Spring Boot 3부터 사용 가능한 기능 Feign과 같은 클라이언트 라이브러리와 같이 인터페이스를 기반으로 HTTP 요청을 보내고 응답을 받을 수 있는 기능을 제공한다. 사용법 인터페이스 정의 인터페이스 메소드에 어노테이션을 붙이면 된다. 사용 가능한 파라미터 URI: 요청에 대한 URL을 동적으로 설정한다. HttpMethod: 요청에 대한 HTTP 메서드를 동적으로 설정한다. @RequestHeader: 요청 헤더 @RequestBody: 요청 바디 @RequestParam: 요청 매개변수 @CookieValue: 쿠키 이름과 값 사용 가능한 반환 타입 void, Mono<Void> HttpHeaders, Mono<HttpHeaders> <T>, Mono<T> <T>, Flux<T> ResponseEntity<T>, Mono<ResponseEntity<T>> Mono<ResponseEntity<Flux<T>> interface BooksService { @GetExchange("/books") List<Book> getBooks(); @GetExchange("/books/{id}") Book getBook(@PathVariable long id); @PostExchange("/books") Book saveBook(@RequestBody Book book); @DeleteExchange("/books/{id}") ResponseEntity<Void> deleteBook(@PathVariable long id); } 클라이언트 생성 HttpServiceProxyFactory 를 통해서 클라이언트를 생성한다....

2024-09-15 · 1 min · 172 words

HTTP 3와 QUIC

이번에는 현재 IETF의 인터넷 초안 상태인 HTTP/3에 대해서 알아본다. HTTP/3는 기존의 HTTP 버전들과 다르게 TCP를 사용하지 않는다. Transport layer에서 TCP가 아닌 QUIC을 사용한다. QUIC은 Quick UDP Internet Connection의 약자로 구글에서 개발한 UDP기반의 프로토콜이다. 이 QUIC에서 제공하는 기능에는 어떤 것이 있을까. 보안 기존에 TCP + HTTP/2를 사용할 때는 보안을 위해 별도의 TLS 레이어가 필요했다. QUIC은 자체적으로 보안 기능을 내장하고 있어 별도의 TLS 레이어를 둘 필요가 없어졌다. 이렇게 결합하면 어떤 이점이 있을까? 기존의 TCP + TLS의 경우에는 클라이언트와 서버가 연결을 시작할 때 TCP의 3-Way Handshake와 TLS 자체의 Handshake가 따로 필요했었다....

2024-09-15 · 1 min · 194 words

HSTS

목표 HSTS가 무엇인지 이해한다. HSTS를 사용하는 이유를 이해한다. HSTS를 적용하는 방법을 이해한다. HSTS 웹 사이트 접속 시 HTTPS만 사용하도록 클라이언트에서 강제하는 기술이다. 일반적으로, HTTPS를 유도하기 위해서 웹 서버는 리다이렉트 시키는 방법을 사용한다. 이 때, HSTS 헤더(Strict-Transport_security)를 응답으로 주면, 해당 사이트 및 이 사이트의 하위 도메인으로 모든 연결은 HTTPS로 연결이 된다. 사용하는 이유 사용자가 HTTP로 요청을 보내고, HTTPS로 리다이렉트 되는 사이에는 공격자로부터 해당 패킷을 감청할 수 있기 때문이다. HSTS를 사용해서 클라이언트에서 요청을 보낼 때부터 HTTPS를 사용하도록 강제하면 감청 당할 확률이 줄어든다....

2024-09-15 · 1 min · 160 words

Hibernate Validator로 단위 테스트하기

목표 Spring MVC에서 컨트롤러의 파라미터로 사용되는 dto들의 어노테이션 기반 validation을 단위 테스트한다. @SpringBootTest 등을 사용해서 테스트가 느려지게 하지 않는다. 방법 dto를 검증하기위해서는 Validator가 필요하다. Validator는 ValidatorFacotry를 통해서 생성할 수 있다. val validatorFactory = Validation.buildDefaultValidatorFactory() val validator = validatorFactory.validator 아래와 같은 User 클래스가 있다면, validator를 통해서 검증을 통과했는지 테스트 해볼 수 있다. import jakarta.validation.constraints.AssertTrue; import jakarta.validation.constraints.Max; import jakarta.validation.constraints.Min; import jakarta.validation.constraints.NotNull; import jakarta.validation.constraints.Size; import jakarta.validation.constraints.Email; public class User { @NotNull(message = "Name cannot be null") private String name; @AssertTrue private boolean working; @Size(min = 10, max = 200, message = "About Me must be between 10 and 200 characters") private String aboutMe; @Min(value = 18, message = "Age should not be less than 18") @Max(value = 150, message = "Age should not be greater than 150") private int age; @Email(message = "Email should be valid") private String email; // standard setters and getters } // test code Set<ConstraintViolation<User>> violations = validator....

2024-09-15 · 1 min · 162 words

GROUP BY, ORDER BY 사용시 인덱스

인덱스는 정의되어 있는 순서가 중요하다. 만약 인덱스에 정의된 순서가 col1, col2, col3, col4 라고 정의되어 있다면 아래와 같다. GROUP BY col1 # 사용 가능 GROUP BY col1, col2 # 사용 가능 GROUP BY col1, col2, col3 # 사용 가능 GROUP BY col1, col2, col3, col4 # 사용 가능 GROUP BY col2, col2 # 사용 불가능 GROUP BY col1, col3, col2 # 사용 불가능 GROUP BY col1, col2, col3, col4, col5 # 사용 불가능 WHERE 절이 있다고하면 그 다음 컬럼부터 GROUP BY에 있다면 사용 가능하다....

2024-09-15 · 1 min · 113 words

GROUP BY 사용시 filesort가 발생하는 문제 해결하기

MySQL은 GROUP BY 사용시 자동으로 GROUP BY 열에 맞춰 정렬이 발생한다. ORDER BY NULL 를 추가해서 정렬을 하지 않도록 할 수 있다. 참고 자료 https://dba.stackexchange.com/questions/208166/group-by-needs-order-by-null-to-avoid-filesort

2024-09-15 · 1 min · 25 words