2022-10-15-TIL
2022-10-15-TIL
Today I Learned
클린 아키텍처
클린 아키텍처는 로버트 C. 마틴이 정리한 아키텍처 원칙으로, 핵심은 의존성 규칙이다. 소스 코드 의존성은 바깥(프레임워크, DB, UI)에서 안쪽(유스케이스, 엔티티)으로만 향해야 하고, 안쪽 원은 바깥 원의 존재를 몰라야 한다. DB 접근처럼 안쪽이 바깥 기능을 써야 할 때는 안쪽에 인터페이스(포트)를 두고 바깥에서 구현해서 의존 방향을 뒤집는다. 그 결과 비즈니스 규칙을 프레임워크나 DB 없이 테스트할 수 있고, 바깥 기술을 바꿔도 안쪽 코드는 그대로 남는다. 계층형 아키텍처와 비교하면, 영속성 계층이 아래에 있는 구조에서 도메인이 가장 안쪽에 있는 구조로 바뀐다는 점이 다르다.
- https://wikidocs.net/book/8110
Kotlin Coroutines vs Java Virtual Threads
둘 다 “적은 OS 스레드로 많은 동시 작업을 처리한다”는 같은 문제를 다른 층위에서 푼다.
- Kotlin 코루틴은 언어와 라이브러리 수준의 기능이다.
suspend함수를 컴파일러가 상태 머신으로 바꿔, 일시 중단 지점에서 스레드를 놓아주고 나중에 이어서 실행한다. 일시 중단 가능한 함수는suspend로 표시해야 하므로 호출 체인 전체에 전파된다. 대신 구조화된 동시성(부모 스코프가 끝나면 자식 코루틴도 정리)과 취소 전파가 API에 녹아 있다. - Java 가상 스레드(JEP 425, JDK 19 프리뷰)는 JVM 수준의 기능이다. 가상 스레드는
java.lang.Thread의 인스턴스이고, 블로킹 I/O를 만나면 JVM이 가상 스레드를 캐리어(OS) 스레드에서 떼어 냈다가 다시 올린다. 기존의 요청당 스레드 방식 코드를 거의 그대로 둔 채 확장성을 얻는 것이 목표다. JEP는 가상 스레드를 풀링하지 말고 작업마다 새로 만들라고(Executors.newVirtualThreadPerTaskExecutor()) 권하며,synchronized블록이나 네이티브 호출 안에서 블로킹하면 캐리어 스레드에 고정(pinning)되어 이점이 사라진다고 경고한다(JEP 425).
링크한 글은 현재 삭제되어 내용을 다시 확인하지 못했다. 정리하면, 가상 스레드는 기존 블로킹 코드를 살리는 쪽이고 코루틴은 명시적인 일시 중단과 구조화된 동시성을 주는 쪽이라 서로를 완전히 대체하는 관계는 아니다.
- https://itnext.io/kotlin-coroutines-vs-java-virtual-threads-a-good-story-but-just-that-91038c7d21eb
Kotlin Companion Object
Kotlin에는 static 키워드가 없다. 클래스 이름으로 호출하는 멤버가 필요하면 클래스 안에 companion object를 선언한다. 이름을 생략하면 Companion이라는 이름이 붙는다(Kotlin: Object declarations and expressions).
1
2
3
4
5
6
7
class User private constructor(val name: String) {
companion object {
fun of(name: String): User = User(name.trim())
}
}
val user = User.of(" kim ")
Java의 static과 다른 점은 컴패니언 객체가 실제 객체라는 것이다. 그래서 인터페이스를 구현할 수 있고, 클래스 이름 자체를 그 인터페이스 타입 값으로 넘길 수 있다. JVM에서 진짜 static 메서드가 필요하면(Java 코드에서 호출하는 경우 등) @JvmStatic을 붙인다. 컴패니언 객체는 해당 클래스가 로드될 때 초기화되어, Java의 static 초기화 블록과 같은 시점을 갖는다.
- https://www.bsidesoft.com/8187
Method Inlining in the JVM
메서드 인라이닝은 자주 호출되는 메서드의 호출 부분을 메서드 본문으로 바꿔 넣는 최적화다. javac가 아니라 실행 중에 JVM의 JIT 컴파일러가 한다. 그래서 같은 .class 파일도 새 JVM에서 더 빨라질 수 있다.
Baeldung 글에 따르면 JIT은 두 가지를 본다. 호출 횟수가 임계값을 넘어 “뜨거운(hot)” 메서드여야 하고, 바이트코드 크기가 -XX:FreqInlineSize로 정해진 한도보다 작아야 한다. static, private, final 메서드는 대체로 인라이닝되고, public 메서드는 구현이 하나뿐이라고 판단될 때만 인라이닝된다. 하위 클래스가 추가로 로드되면 그 가정이 깨진다. 실제로 어떤 메서드가 인라이닝되는지는 -XX:+PrintCompilation -XX:+UnlockDiagnosticVMOptions -XX:+PrintInlining 플래그로 확인할 수 있다.
실무에서 가져갈 점은 작은 메서드로 쪼개는 것이 성능을 해친다는 걱정은 대부분 필요 없다는 것이다. 뜨거운 경로의 작은 메서드는 JIT이 합쳐 준다. IntelliJ의 Inline 리팩터링은 이름만 같을 뿐 소스 코드를 바꾸는 편집 기능이라 JIT 인라이닝과는 별개다.
- https://www.baeldung.com/jvm-method-inlining
- https://medium.com/codex/method-inlining-in-java-84caec9b3e18
- https://www.jetbrains.com/help/idea/inline.html
책 추천
추천받은 책 목록이다. 확인한 것은 『클라우드 네이티브 애플리케이션 디자인 패턴』(카순 인드라시리, 한빛미디어)과 『소프트웨어 아키텍처 101』(마크 리처즈, 닐 포드, 한빛미디어)이다. 나머지 두 링크는 상품 페이지가 열리지 않아 제목을 다시 확인하지 못했다.
- http://www.yes24.com/Product/Goods/109858899
- http://m.yes24.com/Goods/Detail/113804176
- https://book.interpark.com/product/BookDisplay.do?_method=Detail&sc.shopNo=0000400000&dispNo=&sc.prdNo=355382913&sc.saNo=002001023&bkid1=category&bkid2=ct028023&bkid3=c1&bkid4=001
- http://www.yes24.com/Product/Goods/104491433
Test DB
datacharmer/test_db는 MySQL과 PostgreSQL에서 쓸 수 있는 샘플 데이터베이스다. 직원 약 30만 명과 급여 기록 약 280만 건이 employees, departments, dept_manager, dept_emp, titles, salaries 여섯 테이블에 들어 있고, 내보낸 데이터 크기는 167MB다. 아주 크지는 않지만 인덱스 유무에 따른 실행 계획 차이나 페이지네이션 성능을 실험해 보기에는 충분한 규모다. mysql < employees.sql로 적재하고, 함께 들어 있는 검증 스크립트로 데이터가 제대로 들어갔는지 확인한다(test_db README).
- https://github.com/datacharmer/test_db
댓글
아직 댓글이 없습니다