songining
article thumbnail
๐Ÿ›ฐ SIA ์ž…์‚ฌ ์ƒ๋ฐ˜๊ธฐ ํšŒ๊ณ 
์ผ๊ธฐ ๐Ÿ‘€ 2023. 7. 3. 00:20

์ฃผ๋‹ˆ์–ด ๊ฐœ๋ฐœ์ž์˜ ์ƒ๋ฐ˜๊ธฐ ํšŒ๊ณ  ์‹œ๊ฐ„์ด ์ •๋ง ๋นจ๋ฆฌ๊ฐ„๋‹ค. ๋ฒŒ์จ 1๋…„์ค‘ ์ ˆ๋ฐ˜์ด ์ง€๋‚ฌ๋‹ค๋Š”๊ฒŒ ๋ฏฟ๊ธฐ์ง€ ์•Š๋Š”๋‹ค ๐Ÿฅน ์ž…์‚ฌ๋ฅผ ๊ฒฐ์ •ํ•˜๋ฉฐ ํ˜ผ์ž ๋˜์ƒˆ๊ฒผ๋˜ ์ƒ๊ฐ๋“ค์ด ์žˆ๋‹ค. 1. ์ฃผ์–ด์ง„ ์—…๋ฌด๋งŒํผ์€ ์ œ๋Œ€๋กœ ์ดํ•ดํ•˜๊ณ  ๋๊นŒ์ง€ ๋งก์€ ์—ญํ• ์„ ์ถฉ์‹คํžˆ ํ•ด๋‚ด๊ธฐ 2. ์˜์‚ฌ ์†Œํ†ต์„ ํ™œ๋ฐœํžˆ ํ•˜๊ธฐ 3. ๋ฌด์กฐ๊ฑด์ ์ธ ์ˆ˜์šฉ๋ณด๋‹ค๋Š” ๋‚ด ์ฃผ๊ด€์„ ๊ฐ€์ง€๊ณ  ๋šœ๋ ทํ•˜๊ฒŒ ์˜๊ฒฌ์„ ํ‘œํ˜„ํ•˜๊ธฐ ์‹œ๊ฐ„์„ ๋’ค๋Œ์•„๋ณด๋‹ˆ ๊ทธ๋ž˜๋„ ๊ฝค ์‹ค์ฒœํ•˜๋ฉฐ ์—ด์‹ฌํžˆ ํšŒ์‚ฌ์ƒํ™œ์„ ํ–ˆ๋‹ค๋Š” ์ƒ๊ฐ์ด ๋“ ๋‹ค. ์ธํ„ด์„ ํ•  ๋•Œ๋ณด๋‹ค ์—…๋ฌด์˜ ๋‚œ์ด๋„๊ฐ€ ๋†’์•„์กŒ๊ณ  ์ˆ˜๋งŽ์€ ๋ ˆ๊ฑฐ์‹œ ์ฝ”๋“œ๋“ค์„ ๋งŒ๋‚˜๊ธฐ๋„ ํ•˜๊ณ  ํฌ๊ณ  ์ž‘์€ ์ฑŒ๋ฆฐ์ง€๋“ค์ด ์žˆ์—ˆ๋‹ค. ๋ฌธ์ œ๋“ค์„ ํ•˜๋‚˜์”ฉ ํ•ด๊ฒฐํ•ด๋‚˜๊ฐ€๋ฉฐ ์Šค์Šค๋กœ ์–ป๋Š” ๊นจ๋‹ฌ์Œ๋„ ์žˆ์—ˆ๊ณ  ์–ด๋Š์ •๋„ ๋…ธํ•˜์šฐ๊ฐ€ ์ƒ๊ธด ๊ฒƒ ๊ฐ™๊ธฐ๋„ ํ•˜๋‹ค. ํŒ€์›๋ถ„๋“ค์ด ๋„์™€์ฃผ์…”์„œ ์—…๋ฌด์— ์ž˜ ์ ์‘ํ•  ์ˆ˜ ์žˆ์—ˆ๊ณ  ์ถ”ํ›„์— ๋ˆ„๊ตฐ๊ฐ€ ๋“ค์–ด์˜จ๋‹ค๋ฉด ๋‚˜๋„ ๋ฐ›์€ ๋„์›€์„ ๋‚จ๋“ค์—๊ฒŒ ๋งˆ..

๋ณดํ˜ธ๋˜์–ด ์žˆ๋Š” ๊ธ€์ž…๋‹ˆ๋‹ค. ๋‚ด์šฉ์„ ๋ณด์‹œ๋ ค๋ฉด ๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ ์ž…๋ ฅํ•ด์ฃผ์„ธ์š”.
๋ณดํ˜ธ๋˜์–ด ์žˆ๋Š” ๊ธ€์ž…๋‹ˆ๋‹ค. ๋‚ด์šฉ์„ ๋ณด์‹œ๋ ค๋ฉด ๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ ์ž…๋ ฅํ•ด์ฃผ์„ธ์š”.
[Kotlin] associateBy, groupBy
Language/Kotlin 2023. 2. 21. 16:45

collections API ์ค‘ ํ•˜๋‚˜๋กœ ์ปฌ๋ ‰์…˜์„ Map ํ˜•ํƒœ๋กœ ๋ณ€ํ˜•์‹œ์ผœ์ฃผ๋Š” API ์ด๋‹ค. associateBy ํ•จ์ˆ˜์™€ groupBy ํ•จ์ˆ˜๋Š” ์ง€์ •๋œ key์— ์˜ํ•ด ์ธ๋ฑ์‹ฑ๋œ ์ปฌ๋ ‰์…˜์˜ ์›์†Œ๋กœ๋ถ€ํ„ฐ Map์„ ๋งŒ๋“ค์–ด์ค€๋‹ค. associateBy public inline fun Iterable.associateBy(keySelector: (T) -> K): Map { val capacity = mapCapacity(collectionSizeOrDefault(10)).coerceAtLeast(16) return associateByTo(LinkedHashMap(capacity), keySelector) } ๋งค๊ฐœ๋ณ€์ˆ˜์—๋Š” T๋ฅผ ์ „๋‹ฌํ•˜๊ณ  key๋ฅผ ๋ฆฌํ„ดํ•˜๋Š” ๋žŒ๋‹คํ•จ์ˆ˜ keySelector๋ฅผ ์ธ์ž๋กœ ๋ฐ›๋Š”๋‹ค. ๋งค๊ฐœ๋ณ€์ˆ˜๋กœ ๋ฐ›์€ key..

article thumbnail
Spring WebFlux์˜ Programming Models
BACKEND/Spring 2023. 2. 20. 14:22

Programming Models 1. Annotated Controller Spring MVC์—์„œ ์‚ฌ์šฉํ•˜๋˜ ๋ฐฉ์‹์„ WebFlux ์—์„œ ๊ทธ๋Œ€๋กœ ์‚ฌ์šฉ์ด ๊ฐ€๋Šฅํ•˜๋‹ค. @RequestMapping, @PathVariable, @RestController, @GetMapping ๋“ฑ 2. Functional Endpoints Java8์˜ lambda style routing๊ณผ handling ๋ฐฉ์‹ (ํ•จ์ˆ˜ํ˜• ๋ชจ๋ธ) RouterFunction: ์–ด๋–ค ํ•ธ๋“ค๋Ÿฌ๊ฐ€ ์š”์ฒญ์„ ์ฒ˜๋ฆฌํ•  ์ง€ ๊ฒฐ์ • HandlerFunction: ๋ฐ”์ธ๋”ฉ ๋ถ€ํ„ฐ HTTP ์š”์ฒญ ์‘๋‹ต์ฒ˜๋ฆฌ ServerRequest์™€ ServerResponse๋กœ ์‘๋‹ต์„ ํ•˜๋ฉฐ ์„œ๋ธ”๋ฆฟ ์ œ์•ฝ์ด ์—†๊ณ  ๋ฆฌ์•กํ‹ฐ๋ธŒ ํƒ€์ž…์„ ์ง€์›ํ•œ๋‹ค. Spring WebFlux์˜ ๊ฒฝ์šฐ ๋‹ค์Œ๊ณผ ๊ฐ™์€ 2๊ฐœ์˜ ๊ฐœ๋ฐœ ..

Spring Actuator ์‚ฌ์šฉํ•ด๋ณด๊ธฐ
BACKEND/Spring 2023. 1. 31. 22:45

Spring Actuator๋ž€? ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์˜ ์ƒํƒœ๋ฅผ ๋ชจ๋‹ˆํ„ฐ๋ง, Metric ์ˆ˜์ง‘์„ ์œ„ํ•œ Http Endpoint๋ฅผ ์ œ๊ณตํ•ด์ฃผ๋Š” ๋ชจ๋“ˆ์ด๋‹ค. (์š”์•ฝํ•˜๋ฉด ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์˜ ์ƒํƒœ๋ฅผ ์ „์ฒด์ ์œผ๋กœ ์•Œ ์ˆ˜ ์žˆ๋„๋ก ๋„์™€์ฃผ๋Š” ๊ธฐ๋Šฅ!) // https://mvnrepository.com/artifact/org.springframework.boot/spring-boot-starter-actuator implementation 'org.springframework.boot:spring-boot-starter-actuator:3.0.1' ๋‹ค์Œ๊ณผ ๊ฐ™์ด dependency๋งŒ ์ถ”๊ฐ€ํ•ด์ฃผ๋ฉด ์‚ฌ์šฉ์ด ๊ฐ€๋Šฅํ•˜๋‹ค. Ex) spring ์„ค์ • yaml ํŒŒ์ผ์— ์•„๋ž˜์™€ ๊ฐ™์ด ์–ด๋–ค endpoint๋“ค์„ ํฌํ•จํ• ์ง€ ๋ช…์‹œํ•ด์ฃผ๋ฉด ๋œ๋‹ค. management: endp..

Spring Securirty 6 ์ด์ƒ ๋ฒ„์ „์—์„œ h2-console 403 ์—๋Ÿฌ ๋‚˜๋Š” ๋ฌธ์ œ
BACKEND/Spring 2023. 1. 23. 17:41

๊ธฐ์กด์— ํ•˜๋˜ ๊ฒƒ ์ฒ˜๋Ÿผ http.requestMatchers("/h2-console/**").permitAll() ๋กœ h2-console์— ๋Œ€ํ•œ ์ ‘๊ทผ์„ ํ—ˆ์šฉํ•ด์ฃผ๋ ค๊ณ  ํ–ˆ์ง€๋งŒ ๊ณ„์†ํ•ด์„œ 403(forbidden) ์—๋Ÿฌ๊ฐ€ ๋‚ฌ๋‹ค. ๊ตฌ๊ธ€๋ง์„ ํ†ตํ•ด ํ•ด๊ฒฐํ•œ ๊ฒฐ๊ณผ @Bean public SecurityFilterChain filterChain(HttpSecurity http) throws Exception { http.authorizeHttpRequests() .requestMatchers("/users/**").permitAll() .and() .authorizeHttpRequests(auth -> auth .requestMatchers(AntPathRequestMatcher.antMatcher("/h2-console/..

Kotlin Coroutine Context, Coroutine Builder
Language/Kotlin 2022. 11. 1. 14:30

Coroutine Context ์ฝ”๋ฃจํ‹ด์€ ํ•ญ์ƒ Coroutine Context๋กœ ๊ตฌ์„ฑ๋œ ์ฝ˜ํ…์ŠคํŠธ ์•ˆ์—์„œ ์‹คํ–‰๋˜๋Š”๋ฐ, ์ด ์ฝ˜ํ…์ŠคํŠธ๋Š” Dispatchers์™€ Job์œผ๋กœ ๊ตฌ์„ฑ๋œ๋‹ค. Dispatchers๋Š” ์ฝ”๋ฃจํ‹ด์ด ์‹คํ–‰๋  ์Šค๋ ˆ๋“œ๋ฅผ ์ง€์ •ํ•˜๋Š” ์—ญํ•  Default : CPU์—์„œ ๋งŽ์€ ์—ฐ์‚ฐ์ด ํ•„์š”ํ•œ ์ฒ˜๋ฆฌ ๋™์‹œ์ž‘์—… ๊ฐ€๋Šฅํ•œ ์ตœ๋Œ€ ๊ฐœ์ˆ˜๋Š” CPU ์ฝ”์–ด ์ˆ˜์™€ ๊ฐ™๋‹ค. IO : ํŒŒ์ผ ์ž…์ถœ๋ ฅ, ๋„คํŠธ์›Œํฌ ์ฝœ ๋“ฑ ์˜ค๋ž˜ ๋Œ€๊ธฐํ•˜๋Š” ์ƒํ™ฉ์ผ ๋•Œ Blocking IO์šฉ ๊ณต์œ  ์Šค๋ ˆ๋“œํ’€์—์„œ ๋™์ž‘ Default์™€ ์Šค๋ ˆ๋“œ๋ฅผ ๊ณต์œ ํ•˜๋ฏ€๋กœ withContext์—์„œ Dispatcher ๋ณ€๊ฒฝ ์‹œ, ์ปจํ…์ŠคํŠธ ์Šค์œ„์นญ ํ•˜์ง€ ์•Š๊ณ  ๋™์ผํ•œ ์Šค๋ ˆ๋“œ์—์„œ ์‹คํ–‰๋จ Main: ์ฝ”๋ฃจํ‹ด์—์„œ ์ฒ˜๋ฆฌ๋œ ๊ฐ’์„ UI์— ๋ฐ˜์˜ํ•  ๋•Œ ๋ฉ”์ธ์Šค๋ ˆ๋“œ์—์„œ ๋™์ž‘ UnConfined ๋ฉ”์ธ์Šค๋ ˆ๋“œ์—์„œ ๋™์ž‘ C..

Kotlin inline fun, reified
Language/Kotlin 2022. 10. 28. 13:30

Reified ํ‚ค์›Œ๋“œ๋ฅผ ์‚ฌ์šฉํ•˜๋ฉด ์ œ๋„ค๋ฆญ ํ•จ์ˆ˜์—์„œ Runtime์— ํƒ€์ž… ์ •๋ณด๋ฅผ ์•Œ ์ˆ˜ ์žˆ๋‹ค. (๋ณดํ†ต์€ ์ปดํŒŒ์ผ ์‹œ์—๋งŒ ํƒ€์ž…์„ ์•Œ ์ˆ˜ ์žˆ๊ณ  ๋Ÿฐํƒ€์ž„์—์„œ ํƒ€์ž… ์ •๋ณด๋Š” ์กด์žฌํ•˜์ง€ ์•Š๊ฒŒ ๋œ๋‹ค.) ์ฆ‰, ๋Ÿฐํƒ€์ž„์‹œ์—๋„ ํƒ€์ž… ์ •๋ณด๋ฅผ ๊ฐ€์ง€๊ณ  ์žˆ๊ธฐ ๋•Œ๋ฌธ์— ์ธ์Šคํ„ด์Šค๋ฅผ ์ฐพ๊ธฐ๊ฐ€ ์‰ฝ๋‹ค. reified ๋Š” inline fun๊ณผ ํ•จ๊ป˜ ์‚ฌ์šฉ๋˜๋ฉฐ ํ•จ์ˆ˜์˜ ๋งค๊ฐœ๋ณ€์ˆ˜๋กœ T ํƒ€์ž… ํด๋ž˜์Šค๋ฅผ ๋ฐ›๋Š” ๊ฒƒ์„ ์ƒ๋žตํ•  ์ˆ˜ ์žˆ๋‹ค. ์ถ”๊ฐ€์ ์œผ๋กœ T ํด๋ž˜์Šค๋ฅผ ๋„˜๊ฒจ์ค„ ํ•„์š”๊ฐ€ ์—†๋‹ค๋Š” ์ ์ด ์ข‹์€ ๊ฒƒ ๊ฐ™๋‹ค. ๋‹ค์Œ์€ R2dbcEntityTemplate ์ฟผ๋ฆฌ ์‹คํ–‰์„ ์œ„ํ•œ ํ•จ์ˆ˜์ด๋‹ค. ๊ธฐ์กด ์ฝ”๋“œ) private fun executeQuery(build: Select, entityClass: KClass): Flow = r2dbcEntityTemplate.query( QueryBuil..

Kotlin Kotest @beforeSpec @beforeContainer @beforeTest @beforeEach ์ฐจ์ด
BACKEND/Spring 2022. 9. 19. 16:58

Kotest์—๋Š” ์ „ํ›„์ฒ˜๋ฆฌ๋ฅผ ์œ„ํ•œ ์—ฌ๋Ÿฌ๊ฐœ์˜ ์ธํ„ฐํŽ˜์ด์Šค ํ•จ์ˆ˜๋“ค์ด ์กด์žฌํ•˜๋Š”๋ฐ ๋Œ€ํ‘œ์ ์œผ๋กœ @beforeSpec @beforeContainer @beforeTest @beforeEach .. ๋“ฑ์ด ์กด์žฌํ•œ๋‹ค. ํ…Œ์ŠคํŠธ ์ƒ๋ช…์ฃผ๊ธฐ์— ์–ด๋– ํ•œ ์ „ํ›„ ์„ธํŒ…์„ ํ•ด์ฃผ์–ด์•ผ ํ•˜๋Š”๊ฒฝ์šฐ ์‚ฌ์šฉํ•œ๋‹ค. ์˜ˆ๋ฅผ ๋“ค๋ฉด ํ…Œ์ŠคํŠธ ์ปจํ…Œ์ด๋„ˆ ์‹คํ–‰, ๋ฐ์ดํ„ฐ ์‚ฝ์ž… ๋“ฑ๋“ฑ! ์–ด๋–ค function์„ ์‚ฌ์šฉํ•˜๋ƒ์— ๋”ฐ๋ผ ํ…Œ์ŠคํŠธ ๊ณผ์ •๊ณผ ๊ฒฐ๊ณผ๊ฐ€ ๋‹ฌ๋ผ์งˆ ์ˆ˜ ์žˆ๊ธฐ ๋•Œ๋ฌธ์— ํ•„์š”์— ๋งž๊ฒŒ ๊ณจ๋ผ ์‚ฌ์šฉํ•˜๋ฉด ๋  ๊ฒƒ ๊ฐ™๋‹ค. Function Description @beforeEach ๊ฐ testcase ๋งˆ๋‹ค ํ˜ธ์ถœ๋œ๋‹ค. @beforeTest ๊ฐ testcase ๋งˆ๋‹ค ํ˜ธ์ถœ๋œ๋‹ค. @beforeContainer ๊ฑฑ context๋งˆ๋‹ค ํ˜ธ์ถœ๋œ๋‹ค. @beforeSpec ํ•˜๋‚˜์˜ ํ…Œ์ŠคํŠธ spec (FunS..

FetchJoin ๊ณผ EntityGraph
BACKEND/Spring 2022. 8. 21. 15:52

์—ฐ๊ด€๋œ ์—”ํ‹ฐํ‹ฐ์— ๋Œ€ํ•ด ์ง€์—ฐ๋กœ๋”ฉ์œผ๋กœ ์„ค์ •์„ ํ•ด์ฃผ๋ฉด ์ผ๋ฐ˜์ ์ธ ์กฐํšŒ ์ฟผ๋ฆฌ์—์„œ๋Š” ์—ฐ๊ด€๋œ ์—”ํ‹ฐํ‹ฐ๊นŒ์ง€ ์กฐํšŒํ•ด์˜ค์ง€ ์•Š๊ณ  ์—ฐ๊ด€๋œ ์—”ํ‹ฐํ‹ฐ๋Š” ๊ฐ€์งœ ํ”„๋ก์‹œ ๊ฐ์ฒด๋กœ ์„ค์ •์ด ๋œ๋‹ค. ์ด๋ ‡๊ฒŒ ๋˜๋ฉด ์—ฐ๊ด€๋œ ์—”ํ‹ฐํ‹ฐ์˜ ๊ฐ’์— ์ ‘๊ทผํ•ด์•ผํ•  ๋•Œ ๋ฐ์ดํ„ฐ๋งˆ๋‹ค ์ฟผ๋ฆฌ๊ฐ€ ํ•œ๋ฒˆ์”ฉ ๋” ์‹คํ–‰๋˜์–ด N+1 ๋ฌธ์ œ๊ฐ€ ๋ฐœ์ƒํ•˜๊ฒŒ ๋œ๋‹ค. ์ด๋ฅผ ํ•ด๊ฒฐํ•˜๊ธฐ ์œ„ํ•œ ๊ฒƒ์ด Fetch Join ์ด๋‹ค. ์—ฐ๊ด€๋œ ๊ฒƒ๋“ค์„ ํ•œ๋ฒˆ์— ๋‹ค ๊ฐ€์ ธ์˜ค๋Š” ๊ฒƒ์œผ๋กœ ๊ฐ€์งœ ํ”„๋ก์‹œ ๊ฐ์ฒด๊ฐ€ ์•„๋‹ˆ๋ผ ์—ฐ๊ด€๋œ ์—”ํ‹ฐํ‹ฐ๊นŒ์ง€ ์‹ค์ œ ๊ฐ’์œผ๋กœ ์ „๋ถ€ ์ฑ„์›Œ์ค€๋‹ค. (์ฆ‰, ์กฐ์ธ๋งŒ ํ•˜๋Š” ๊ฒƒ์ด ์•„๋‹ˆ๋ผ select ์ ˆ์— ์žˆ๋Š” ๊ฐ’๋“ค๋„ ์ „๋ถ€ ๋„ฃ์–ด์ฃผ๋Š” ๊ฒƒ) EntityGraph - data jpa๋ฅผ ์‚ฌ์šฉํ•  ๊ฒฝ์šฐ fetch join ์„ jpql ์—†์ด ๊ฐ„๋‹จํ•˜๊ฒŒ ์‚ฌ์šฉํ•˜๋Š” ๋ฐฉ๋ฒ•์ด๋‹ค. JpaRepository๋ฅผ ์ƒ์†๋ฐ›๋Š” repository๊ฐ€ ์žˆ์„ ๋•Œ @..

Spring Mockito when().thenReturn ๊ณผ doReturn.when()์˜ ์ฐจ์ด
BACKEND/Spring 2022. 8. 1. 16:29

Typically, stubbing argument mismatch indicates user mistake when writing tests. Mockito fails early so that you can debug potential problem easily. However, there are legit scenarios when this exception generates false negative signal: - stubbing the same method multiple times using 'given().will()' or 'when().then()' API Please use 'will().given()' or 'doReturn().when()' API for stubbing. - st..