Skip to content

[Fix/#41] UseCase 수정, 16KB 페이지 대응, 마이 뷰모델 로직 수정#43

Merged
BeomBeom2 merged 5 commits intodevelopfrom
fix/#41-login-dialog
Mar 16, 2026
Merged

[Fix/#41] UseCase 수정, 16KB 페이지 대응, 마이 뷰모델 로직 수정#43
BeomBeom2 merged 5 commits intodevelopfrom
fix/#41-login-dialog

Conversation

@BeomBeom2
Copy link
Collaborator

@BeomBeom2 BeomBeom2 commented Mar 16, 2026

개요

#41

PR 유형

해당하는 항목에 체크해주세요.

  • Add — 리소스/코드/컴포넌트 추가 (기능 변화 없음)
  • Feat — 사용자에게 보이는 새로운 기능 추가
  • Fix — 버그 수정
  • Refactor — 기능 변경 없는 코드 구조 개선
  • Docs / Comment — 문서, 주석 수정
  • Test — 테스트 추가 또는 리팩토링
  • Build / Config — 빌드, 의존성, 설정 변경
  • File — 파일 / 폴더 구조 변경

변경 사항

  • 건너뛰기 UseCase 수정
  • 파키부 라이브러리 관련 16kb 페이지 대응
  • 마이 뷰모델에서 init 블럭으로 로그인 확인하는 로직을 뷰로 이동

📸 화면 / 영상 (선택)

Before

After


리뷰어에게 전달할 사항

  • 의존성을 확인해보니 io.github.onseok:peekaboo-ui:0.5.2가 CameraX 1.3.2을 가져오고 libimage_processing_util_jni.so가 16KB page size 비호환으로 잡혀서 이를 16KB 페이지로 대응가능한 라이브러리로 추가하였습니다.
  • navigation 구조가 변경되면서 마이 뷰모델에서 init 블럭에서 로그인이 되어있는지 확인하면 의도한 대로 동작하지 않습니다. 따라서 Myscreen에서 LaunchedEffect를 사용하여 My 탭에 들어올 때마다 다이얼로그가 나오도록 하였습니다.
  • 마지막으로 기존에는 오버레이 방식으로 다이얼로그를 보여줬는데 이를 다이얼로그로 수정하였습니다. 어제 회의했던 바텀바와 시스템바 모두 클릭 가능한 영역으로 만들었습니다.

Summary by CodeRabbit

릴리스 노트

  • 새로운 기능

    • 카메라 기능 지원 추가
  • 개선 사항

    • 로그인 안내 UI가 오버레이에서 모달 대화상자로 개선되어 닫기 동작이 더 자연스러워짐
    • 로그인 건너뛰기 시 사용자 토큰이 정확히 삭제되도록 변경
    • 로그인 흐름이 이벤트 기반으로 업데이트되어, 로그인 후 또는 건너뛰기 시 홈으로 자동 이동함
    • 마이페이지 진입 시 자동 로그인 확인을 실행하도록 변경

@coderabbitai
Copy link

coderabbitai bot commented Mar 16, 2026

📝 Walkthrough

Walkthrough

이 변경은 로그인/토큰 처리 흐름과 UI/DI 일부를 재구성합니다. LoginRequiredOverlay를 Dialog 기반의 LoginRequiredDialog로 교체하고 시그니처에 onDismissRequest를 추가했습니다. Koin 모듈 변수명 DrawDataModule을 drawDataModule로 변경해 initKoin에 반영했습니다. DeleteUserTokensUseCase를 추가하고 LoginViewModel에서 이를 사용하도록 교체했으며, Login 이벤트 흐름을 SharedFlow 기반으로 변경해 NavigateToHome 이벤트를 발행합니다. MyScreen은 ViewModel init 대신 컴포지션에서 requireLogin()을 호출하도록 이동했고, CameraX 의존성이 evaluate 기능에 추가되었습니다.

Sequence Diagram(s)

sequenceDiagram
  autonumber
  participant MyScreen
  participant MyViewModel
  participant AppDialog as App/Dialog
  participant LoginRoute
  participant LoginVM as LoginViewModel
  participant DeleteUseCase as DeleteUserTokensUseCase
  participant TokenStore as AuthTokenStore
  participant Nav as Navigation

  MyScreen->>MyViewModel: requireLogin()
  MyViewModel->>AppDialog: emit(loginRequiredState)
  AppDialog->>MyScreen: show LoginRequiredDialog

  alt User taps "로그인"
    MyScreen->>Nav: navigateTo(LoginRoute)
    Nav->>LoginRoute: open
    LoginRoute->>LoginVM: user logs in
    LoginVM->>LoginVM: update auth state
    LoginVM->>Nav: emit NavigateToHome
    Nav->>Nav: navigate Home
  else User taps "나중에 하기"
    AppDialog->>LoginVM: onSkipLoginClick()
    LoginVM->>DeleteUseCase: invoke()
    DeleteUseCase->>TokenStore: clear()
    DeleteUseCase-->>LoginVM: result true
    LoginVM->>Nav: emit NavigateToHome
    Nav->>Nav: navigate Home
  end
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~25 minutes

Possibly related PRs

  • kustaurant/Android-CMP PR 35: 동일 파일(App.kt)에서 LoginRequiredOverlay → LoginRequiredDialog 전환과 관련된 UI 컴포넌트 변경을 다룹니다.
  • kustaurant/Android-CMP PR 21: composeApp의 initKoin.kt에서 DI 모듈 임포트/등록명 변경(DrawDataModule → drawDataModule)과 직접적으로 겹칩니다.
  • kustaurant/Android-CMP PR 32: evaluate 기능 추가/연결 및 androidxCamera 의존성 추가와 관련해 evaluate 모듈·DI 연동 변경과 코드 수준 연관성이 있습니다.
🚥 Pre-merge checks | ✅ 2 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (2 passed)
Check name Status Explanation
Title check ✅ Passed PR 제목이 주요 변경 사항들(UseCase 수정, 16KB 페이지 대응, 뷰모델 로직 이동)을 포괄적으로 요약하고 있으며, 변경 사항과 관련된 이슈(#41)도 명시되어 있습니다.
Description check ✅ Passed PR 설명이 템플릿의 주요 섹션(개요, PR 유형, 변경 사항, 리뷰어 전달 사항)을 포함하고 있으며, 각 변경 사항에 대한 명확한 설명과 이유를 제공하고 있습니다.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
  • 📝 Generate docstrings (stacked PR)
  • 📝 Generate docstrings (commit on current branch)
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch fix/#41-login-dialog
📝 Coding Plan
  • Generate coding plan for human review comments

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@BeomBeom2 BeomBeom2 added Add 신규 기능 / 화면 / 컴포넌트 추가 AI Review Request coderabbitai 리뷰 요청 labels Mar 16, 2026
@BeomBeom2 BeomBeom2 self-assigned this Mar 16, 2026
Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
shared/core/designSystem/src/commonMain/kotlin/com/kus/designsystem/component/LoginRequiredDialog.kt (1)

23-29: ⚠️ Potential issue | 🟡 Minor

KDoc 주석이 실제 구현과 일치하지 않습니다.

Line 24의 주석에서 "오버레이"라고 언급하고 있지만, 실제 구현은 Dialog로 변경되었습니다. 주석을 업데이트해주세요.

📝 수정 제안
 /**
- * 미로그인시 기능제한 안내 오버레이
+ * 미로그인시 기능제한 안내 다이얼로그
  *
  * `@param` modifier 다이얼로그 수정자
  * `@param` onLoginButtonClick 로그인 버튼 클릭 시 호출되는 콜백
  * `@param` onDismissRequest 취소 버튼 및 외부 영역 터치 시 호출되는 콜백
  */
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In
`@shared/core/designSystem/src/commonMain/kotlin/com/kus/designsystem/component/LoginRequiredDialog.kt`
around lines 23 - 29, KDoc for LoginRequiredDialog.kt incorrectly describes the
UI as an "오버레이" while the implementation uses a Dialog; update the KDoc above
the LoginRequiredDialog composable to reflect that it displays a Dialog
prompting login, and ensure parameter docs (modifier, onLoginButtonClick,
onDismissRequest) match the function signature and behavior (e.g., dialog
dismissal vs overlay touch). Locate the KDoc near the LoginRequiredDialog
declaration and replace "오버레이" wording with "Dialog" and adjust any parameter
descriptions to accurately describe Dialog-specific interactions.
🧹 Nitpick comments (1)
shared/domain/auth/src/commonMain/kotlin/com/kus/domain/auth/usecase/DeleteUserTokensUseCase.kt (1)

8-10: Boolean 반환값을 사용하지 않으므로 Unit으로 변경하세요.

호출부에서 반환값을 사용하지 않으며, 함수가 항상 true를 반환하는 현재 구현에서는 Unit으로 단순화하는 것이 의도를 더 명확하게 표현합니다.

♻️ 제안 diff
 class DeleteUserTokensUseCase(
     private val tokenStore: AuthTokenStore,
 ) {
-    suspend operator fun invoke(): Boolean {
+    suspend operator fun invoke() {
         tokenStore.clear()
-        return true
     }
 }
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In
`@shared/domain/auth/src/commonMain/kotlin/com/kus/domain/auth/usecase/DeleteUserTokensUseCase.kt`
around lines 8 - 10, Change the operator function suspend operator fun invoke()
in DeleteUserTokensUseCase to return Unit instead of Boolean: remove the Boolean
return type and the trailing return true, leaving the function to call
tokenStore.clear() and complete with no return value; update the function
signature (or omit explicit return type) and remove any now-unnecessary return
statements in DeleteUserTokensUseCase.invoke, and adjust any callers if they
relied on the Boolean (they should not).
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In
`@shared/feature/login/src/commonMain/kotlin/com/kus/feature/login/ui/LoginViewModel.kt`:
- Around line 54-57: deleteUserTokens() currently launches
deleteUserTokensUseCase() asynchronously and returns immediately, causing
navigation (onNavigateToHome()) to race with token deletion; change the flow so
navigation waits for deletion to complete and handles failures: make
deleteUserTokens either suspend or return a Result/Boolean from
deleteUserTokensUseCase, call it from a coroutine (viewModelScope.launch) and
only call onNavigateToHome() after successful completion, and wrap the call in
try/catch (or handle error Result) to surface failures (e.g., show error state
or retry) instead of navigating immediately.

---

Outside diff comments:
In
`@shared/core/designSystem/src/commonMain/kotlin/com/kus/designsystem/component/LoginRequiredDialog.kt`:
- Around line 23-29: KDoc for LoginRequiredDialog.kt incorrectly describes the
UI as an "오버레이" while the implementation uses a Dialog; update the KDoc above
the LoginRequiredDialog composable to reflect that it displays a Dialog
prompting login, and ensure parameter docs (modifier, onLoginButtonClick,
onDismissRequest) match the function signature and behavior (e.g., dialog
dismissal vs overlay touch). Locate the KDoc near the LoginRequiredDialog
declaration and replace "오버레이" wording with "Dialog" and adjust any parameter
descriptions to accurately describe Dialog-specific interactions.

---

Nitpick comments:
In
`@shared/domain/auth/src/commonMain/kotlin/com/kus/domain/auth/usecase/DeleteUserTokensUseCase.kt`:
- Around line 8-10: Change the operator function suspend operator fun invoke()
in DeleteUserTokensUseCase to return Unit instead of Boolean: remove the Boolean
return type and the trailing return true, leaving the function to call
tokenStore.clear() and complete with no return value; update the function
signature (or omit explicit return type) and remove any now-unnecessary return
statements in DeleteUserTokensUseCase.invoke, and adjust any callers if they
relied on the Boolean (they should not).

ℹ️ Review info
⚙️ Run configuration

Configuration used: Repository UI

Review profile: CHILL

Plan: Pro

Run ID: c3ce254d-b6fb-465c-916b-812d3328815b

📥 Commits

Reviewing files that changed from the base of the PR and between 56392b2 and 0c31851.

📒 Files selected for processing (16)
  • composeApp/src/commonMain/kotlin/com/kus/kustaurant/App.kt
  • composeApp/src/commonMain/kotlin/com/kus/kustaurant/di/initKoin.kt
  • gradle/libs.versions.toml
  • shared/core/designSystem/src/commonMain/kotlin/com/kus/designsystem/component/LoginRequiredDialog.kt
  • shared/data/draw/src/commonMain/kotlin/com/kus/data/draw/di/drawDataModule.kt
  • shared/domain/auth/src/commonMain/kotlin/com/kus/domain/auth/di/authDomainModule.kt
  • shared/domain/auth/src/commonMain/kotlin/com/kus/domain/auth/usecase/DeleteUserTokensUseCase.kt
  • shared/domain/my/src/androidMain/kotlin/com/kus/shared/domain/my/Platform.android.kt
  • shared/domain/my/src/commonMain/kotlin/com/kus/shared/domain/my/Platform.kt
  • shared/domain/my/src/iosMain/kotlin/com/kus/domain/my/Platform.ios.kt
  • shared/feature/evaluate/build.gradle.kts
  • shared/feature/login/src/androidMain/kotlin/com/kus/feature/login/navigation/LoginRoute.android.kt
  • shared/feature/login/src/commonMain/kotlin/com/kus/feature/login/ui/LoginViewModel.kt
  • shared/feature/login/src/iosMain/kotlin/com/kus/feature/login/navigation/LoginRoute.ios.kt
  • shared/feature/my/src/commonMain/kotlin/com/kus/feature/my/ui/MyScreen.kt
  • shared/feature/my/src/commonMain/kotlin/com/kus/feature/my/ui/MyViewModel.kt
💤 Files with no reviewable changes (4)
  • shared/feature/my/src/commonMain/kotlin/com/kus/feature/my/ui/MyViewModel.kt
  • shared/domain/my/src/iosMain/kotlin/com/kus/domain/my/Platform.ios.kt
  • shared/domain/my/src/commonMain/kotlin/com/kus/shared/domain/my/Platform.kt
  • shared/domain/my/src/androidMain/kotlin/com/kus/shared/domain/my/Platform.android.kt

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In
`@shared/feature/login/src/commonMain/kotlin/com/kus/feature/login/ui/LoginViewModel.kt`:
- Around line 59-63: onSkipLoginClick currently launches viewModelScope.launch
and calls deleteUserTokensUseCase without checking its Boolean result or
catching exceptions; update onSkipLoginClick to await and capture the result of
deleteUserTokensUseCase, wrap the call in try/catch, and only call
_event.emit(LoginUiEvent.NavigateToHome) when deletion succeeds; on failure or
exception emit a failure/feedback event (e.g., LoginUiEvent.ShowError or
similar) and/or log the error so the UI can notify the user instead of blindly
navigating; reference functions/fields: onSkipLoginClick,
deleteUserTokensUseCase, viewModelScope.launch, and
_event.emit(LoginUiEvent.NavigateToHome).

In
`@shared/feature/login/src/iosMain/kotlin/com/kus/feature/login/navigation/LoginRoute.ios.kt`:
- Line 69: The skip button handler currently calls both onSkipLogin (which calls
viewModel.onSkipLoginClick()) and onNavigateToHome, causing duplicate
navigation; remove the direct call to onNavigateToHome from LoginScreen's skip
handler so that only viewModel.onSkipLoginClick() is invoked and navigation is
performed solely in response to the ViewModel's LoginUiEvent.NavigateToHome
event.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Repository UI

Review profile: CHILL

Plan: Pro

Run ID: 8043a91c-adac-41f0-95f9-dde14e342dc4

📥 Commits

Reviewing files that changed from the base of the PR and between 0c31851 and 7c102f9.

📒 Files selected for processing (4)
  • shared/feature/login/src/androidMain/kotlin/com/kus/feature/login/navigation/LoginRoute.android.kt
  • shared/feature/login/src/commonMain/kotlin/com/kus/feature/login/ui/LoginUiEvent.kt
  • shared/feature/login/src/commonMain/kotlin/com/kus/feature/login/ui/LoginViewModel.kt
  • shared/feature/login/src/iosMain/kotlin/com/kus/feature/login/navigation/LoginRoute.ios.kt
🚧 Files skipped from review as they are similar to previous changes (1)
  • shared/feature/login/src/androidMain/kotlin/com/kus/feature/login/navigation/LoginRoute.android.kt

Comment on lines +59 to 63
fun onSkipLoginClick() {
viewModelScope.launch {
deleteUserInfoUseCase()
deleteUserTokensUseCase()
_event.emit(LoginUiEvent.NavigateToHome)
}
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

스킵 처리 실패/예외를 핸들링하지 않아 안정성이 떨어집니다.

Line 61의 결과(Boolean)를 무시하고, 예외 처리 없이 바로 진행합니다. 토큰 삭제 실패 시 사용자에게 알림 없이 흐름이 어긋나거나 예외 전파로 불안정해질 수 있습니다.

🔧 제안 수정
 fun onSkipLoginClick() {
     viewModelScope.launch {
-        deleteUserTokensUseCase()
-        _event.emit(LoginUiEvent.NavigateToHome)
+        runCatching { deleteUserTokensUseCase() }
+            .onSuccess { deleted ->
+                if (deleted) {
+                    _event.emit(LoginUiEvent.NavigateToHome)
+                } else {
+                    _uiState.update {
+                        it.copy(authState = UiState.Failure(UiError.Message("토큰 삭제에 실패했어요.")))
+                    }
+                }
+            }
+            .onFailure { e ->
+                _uiState.update {
+                    it.copy(
+                        authState = UiState.Failure(
+                            e.message?.let { msg -> UiError.Message(msg) }
+                                ?: UiError.Message("토큰 삭제 중 오류가 발생했어요.")
+                        )
+                    )
+                }
+            }
     }
 }
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
fun onSkipLoginClick() {
viewModelScope.launch {
deleteUserInfoUseCase()
deleteUserTokensUseCase()
_event.emit(LoginUiEvent.NavigateToHome)
}
fun onSkipLoginClick() {
viewModelScope.launch {
runCatching { deleteUserTokensUseCase() }
.onSuccess { deleted ->
if (deleted) {
_event.emit(LoginUiEvent.NavigateToHome)
} else {
_uiState.update {
it.copy(authState = UiState.Failure(UiError.Message("토큰 삭제에 실패했어요.")))
}
}
}
.onFailure { e ->
_uiState.update {
it.copy(
authState = UiState.Failure(
e.message?.let { msg -> UiError.Message(msg) }
?: UiError.Message("토큰 삭제 중 오류가 발생했어요.")
)
)
}
}
}
}
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In
`@shared/feature/login/src/commonMain/kotlin/com/kus/feature/login/ui/LoginViewModel.kt`
around lines 59 - 63, onSkipLoginClick currently launches viewModelScope.launch
and calls deleteUserTokensUseCase without checking its Boolean result or
catching exceptions; update onSkipLoginClick to await and capture the result of
deleteUserTokensUseCase, wrap the call in try/catch, and only call
_event.emit(LoginUiEvent.NavigateToHome) when deletion succeeds; on failure or
exception emit a failure/feedback event (e.g., LoginUiEvent.ShowError or
similar) and/or log the error so the UI can notify the user instead of blindly
navigating; reference functions/fields: onSkipLoginClick,
deleteUserTokensUseCase, viewModelScope.launch, and
_event.emit(LoginUiEvent.NavigateToHome).

},
onNavigateToHome = navigateToHome,
onSkipLogin = { viewModel.deleteUserInfo() }
onSkipLogin = { viewModel.onSkipLoginClick() }
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🔴 Critical

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
# LoginScreen 내부에서 skip 시 직접 onNavigateToHome를 호출하는지 확인
rg -n -C5 'fun LoginScreen|onSkipLogin|onNavigateToHome' shared/feature/login/src/commonMain/kotlin/com/kus/feature/login/ui/LoginScreen.kt

# 각 플랫폼 Route에서 skip 처리 경로 확인
rg -n -C4 'onSkipLogin\s*=|onNavigateToHome\s*=' \
  shared/feature/login/src/androidMain/kotlin/com/kus/feature/login/navigation/LoginRoute.android.kt \
  shared/feature/login/src/iosMain/kotlin/com/kus/feature/login/navigation/LoginRoute.ios.kt

Repository: kustaurant/Android-CMP

Length of output: 2955


🏁 Script executed:

# Verify what viewModel.onSkipLoginClick() does to confirm it also triggers navigation
rg -n 'fun onSkipLoginClick|onSkipLoginClick' shared/feature/login/src/commonMain/kotlin/com/kus/feature/login/viewmodel/LoginViewModel.kt

Repository: kustaurant/Android-CMP

Length of output: 198


🏁 Script executed:

# Find LoginViewModel file
fd -i loginviewmodel shared/feature/login/src/

# Also check the directory structure
find shared/feature/login/src -type f -name "*.kt" | grep -i viewmodel | head -20

Repository: kustaurant/Android-CMP

Length of output: 237


🏁 Script executed:

# Check onSkipLoginClick implementation in LoginViewModel
rg -n 'fun onSkipLoginClick' shared/feature/login/src/commonMain/kotlin/com/kus/feature/login/ui/LoginViewModel.kt -A 10

Repository: kustaurant/Android-CMP

Length of output: 458


LoginScreen의 스킵 버튼 핸들러에서 중복 네비게이션 발생 확인됨

LoginScreen 내부 스킵 버튼 클릭 핸들러(line 122-123)에서 onSkipLogin()onNavigateToHome()을 순차적으로 호출하고 있습니다.

ViewModel 이벤트 기반으로 변경된 이후에도:

  • onSkipLogin()viewModel.onSkipLoginClick()LoginUiEvent.NavigateToHome 이벤트 발생
  • onNavigateToHome() → 직접 네비게이션 수행

두 경로가 모두 실행되어 이중 이동이 발생합니다. LoginScreen에서 스킵 클릭 시 onNavigateToHome() 직접 호출을 제거하고, ViewModel 이벤트 처리만 사용하도록 수정이 필요합니다.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In
`@shared/feature/login/src/iosMain/kotlin/com/kus/feature/login/navigation/LoginRoute.ios.kt`
at line 69, The skip button handler currently calls both onSkipLogin (which
calls viewModel.onSkipLoginClick()) and onNavigateToHome, causing duplicate
navigation; remove the direct call to onNavigateToHome from LoginScreen's skip
handler so that only viewModel.onSkipLoginClick() is invoked and navigation is
performed solely in response to the ViewModel's LoginUiEvent.NavigateToHome
event.

@BeomBeom2 BeomBeom2 merged commit 7e555fa into develop Mar 16, 2026
1 check passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Add 신규 기능 / 화면 / 컴포넌트 추가 AI Review Request coderabbitai 리뷰 요청

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant