Skip to content

[WTH-237] 애플 로그인 수정 및 로그인 시 유저 정보 반환#44

Merged
hyxklee merged 6 commits intodevfrom
refactor/WTH-237-로그인-시-유저-정보-반환
Apr 1, 2026

Hidden character warning

The head ref may contain hidden characters: "refactor/WTH-237-\ub85c\uadf8\uc778-\uc2dc-\uc720\uc800-\uc815\ubcf4-\ubc18\ud658"
Merged

[WTH-237] 애플 로그인 수정 및 로그인 시 유저 정보 반환#44
hyxklee merged 6 commits intodevfrom
refactor/WTH-237-로그인-시-유저-정보-반환

Conversation

@hyxklee
Copy link
Copy Markdown
Contributor

@hyxklee hyxklee commented Mar 31, 2026

📌 Summary

어떤 작업인지 한 줄 요약해 주세요.

애플 로그인을 Web Flow에 맞게 수정했습니다
소셜 로그인시 유저 이름을 반환하도록 수정했습니다.

📝 Changes

변경사항을 what, why, how로 구분해 작성해 주세요.

What

""

Why

애플 로그인이 Web 방식의 경우는 서버 리다이렉트를 하는 방식으로 구현해야 하기 때문

How

카카오 소셜 로그인 응답 dto에 유저 이름 추가
애플 로그인 call back api 추가

  • 애플 로그인의 경우는 카카오와 달리 프론트에서 authCode를 보내주지 않고, 리다이렉트 하는 방식으로 동작
  • 애플 로그인 성공시 302 리다이렉트 및 쿠키 설정, 쿼리 파라미터로 registerd, name 반환
  • 이 방식의 경우 쿠키 설정이 서버 도메인 기준으로 되기 때문에 로컬에서는 쿠키 동작을 확인하기 어려움. 쿠키 설정만 확인하고 실제 동작 여부는 도메인 설정된 후 개발 배포에서 확인 가능 (x.weeth.kr로 다 바꿔야함)

📸 Screenshots / Logs

필요시 스크린샷 or 로그를 첨부해주세요.

💡 Reviewer 참고사항

리뷰에 참고할 내용을 작성해주세요.

✅ Checklist

  • PR 제목 설정 완료 (WTH-123 인증 필터 설정)
  • 테스트 구현 완료
  • 리뷰어 등록 완료
  • 자체 코드 리뷰 완료

Summary by CodeRabbit

  • 새로운 기능
    • Apple Sign In 콜백 엔드포인트 추가 및 ID 토큰 직접 인증 지원
    • 소셜 로그인 응답에 사용자 이름(name) 포함 — 리디렉트 시 이름/등록 여부 및 인증 쿠키 전달
  • 문서화
    • 여러 관리자·사용자 API를 OpenAPI 문서에서 숨김 처리
  • 설정
    • Apple 프론트엔드 리디렉션 URI 설정 추가 및 Apple 도메인 허용 강화

@hyxklee hyxklee requested review from dalzzy and soo0711 March 31, 2026 03:37
@hyxklee hyxklee self-assigned this Mar 31, 2026
@hyxklee hyxklee added the 🐞 BugFix 버그 수정 label Mar 31, 2026
@coderabbitai
Copy link
Copy Markdown

coderabbitai bot commented Mar 31, 2026

📝 Walkthrough

Walkthrough

Apple 소셜 로그인 콜백 처리 기능이 추가되었습니다. Apple ID 토큰을 직접 인증하는 포트/어댑터 확장, 콜백 컨트롤러, 이름 파싱, DTO에 사용자 이름 필드 추가 및 관련 매퍼·유스케이스 변경이 포함됩니다.

Changes

Cohort / File(s) Summary
DTO 및 매퍼
src/main/kotlin/com/weeth/domain/user/application/dto/response/SocialLoginResponse.kt, src/main/kotlin/com/weeth/domain/user/application/mapper/UserMapper.kt
SocialLoginResponsename: String 필드 추가. UserMapper.toSocialLoginResponse 시그니처가 userName: String 인자를 받도록 변경되어 name을 설정.
유스케이스
src/main/kotlin/com/weeth/domain/user/application/usecase/command/SocialLoginUseCase.kt
socialLoginByAppleCallback(idToken, userJson?) 공개 메서드 추가. 공통 로그인 흐름을 processLogin으로 추출, ObjectMapper 주입, Apple userJson에서 이름 파싱 및 인증 결과에 따른 이름 대체 로직 추가.
소셜 인증 포트 및 어댑터
src/main/kotlin/com/weeth/domain/user/domain/port/SocialAuthPort.kt, src/main/kotlin/com/weeth/domain/user/infrastructure/AppleSocialAuthAdapter.kt
authenticateWithIdToken(idToken) 인터페이스 메서드(기본 구현 포함) 추가. AppleSocialAuthAdapter에 해당 메서드 오버라이드와 내부 변환 헬퍼 도입.
콜백 컨트롤러
src/main/kotlin/com/weeth/domain/user/presentation/SocialCallbackController.kt
POST /api/v4/users/social/apple/callback 엔드포인트 추가(폼-urlencoded 수신). 에러/빈 토큰 처리, 유스케이스 호출, 리다이렉트 및 토큰 쿠키 설정, 쿼리로 registered·name 전달.
보안 및 설정
src/main/kotlin/com/weeth/global/config/SecurityConfig.kt, src/main/kotlin/com/weeth/global/config/properties/OAuthProperties.kt, src/main/resources/application.yml
Apple 콜백 경로를 permit, CORS에 https://appleid.apple.com 추가, auth.providers.apple.frontend_redirect_uri 프로퍼티 및 application.yml 환경변수 바인딩 추가.
OpenAPI/문서 주석 정리
여러 컨트롤러들 (Account*, AttendanceController, ReceiptAdminController, Penalty*)
여러 컨트롤러의 @Operation 주석에서 hidden = true 또는 deprecated = true 등 문서 속성 변경(핸들러 로직 변경 없음).
테스트
src/test/kotlin/com/weeth/domain/user/application/usecase/command/SocialLoginUseCaseTest.kt
테스트에 ObjectMapper 목 주입 추가(유스케이스 생성자 변경 반영).
기타
src/main/kotlin/com/weeth/global/common/controller/ExceptionDocController.kt
불필요한 TODO 주석 제거(런타임 영향 없음).

Sequence Diagram(s)

sequenceDiagram
    participant Client as Apple Sign In Client
    participant Controller as SocialCallbackController
    participant UseCase as SocialLoginUseCase
    participant AuthPort as SocialAuthPort
    participant Adapter as AppleSocialAuthAdapter
    participant Mapper as UserMapper
    participant CookieProv as TokenCookieProvider

    Client->>Controller: POST /api/v4/users/social/apple/callback (id_token, user)
    alt error or missing id_token
        Controller->>Client: 302 Redirect (error)
    else valid id_token
        Controller->>Controller: parse userJson -> userName?
        Controller->>UseCase: socialLoginByAppleCallback(idToken, userJson)
        UseCase->>AuthPort: authenticateWithIdToken(idToken)
        AuthPort->>Adapter: authenticateWithIdToken(idToken)
        Adapter->>Adapter: decode id_token, build SocialAuthResult
        Adapter-->>UseCase: SocialAuthResult
        UseCase->>UseCase: override name if parsed non-blank
        UseCase->>UseCase: processLogin(authResult) -> JwtDto, isRegistered
        UseCase->>Mapper: toSocialLoginResponse(user.name, token, isRegistered)
        Mapper-->>UseCase: SocialLoginResponse
        UseCase-->>Controller: SocialLoginResponse
        Controller->>CookieProv: create access/refresh cookies
        Controller-->>Client: 302 Redirect (registered, name) + Set-Cookie
    end
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~25 minutes

Possibly related PRs

Suggested labels

✨ Feature

Suggested reviewers

  • dalzzy
  • soo0711

Poem

🐰 사과빛 콜백이 도착했네,
토큰 풀고 이름을 살짝 훔쳐,
쿠키 한 줌 품에 안겨 돌아가네.
폴짝폴짝 새 길을 밟는 토끼,
로그인 축하의 깡총 춤을 춥니다.

🚥 Pre-merge checks | ✅ 2 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 6.06% 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 제목은 두 가지 주요 변경사항(애플 로그인 수정, 유저 정보 반환)을 명확하게 요약하고 있으며, 이는 변경사항과 일치합니다.
Description check ✅ Passed PR 설명은 템플릿의 필수 섹션(Summary, Changes의 What/Why/How, Reviewer 참고사항, Checklist)을 대부분 포함하고 있으며, 변경사항을 충분히 상세히 설명하고 있습니다.

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

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch refactor/WTH-237-로그인-시-유저-정보-반환

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.

Copy link
Copy Markdown

@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

🧹 Nitpick comments (3)
src/main/kotlin/com/weeth/global/config/SecurityConfig.kt (1)

91-91: CORS 설정 확인이 필요합니다.

Apple의 form_post 방식은 서버 리다이렉트(302)가 아닌 폼 POST로 브라우저가 직접 요청을 보내므로, CORS preflight가 발생하지 않습니다. 이 CORS 항목이 실제로 필요한지 확인해 주세요. 불필요하더라도 해가 되지는 않지만, 불필요한 설정은 제거하는 것이 좋습니다.

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

In `@src/main/kotlin/com/weeth/global/config/SecurityConfig.kt` at line 91, Review
the CORS origin entry "https://appleid.apple.com" in SecurityConfig and confirm
whether the application actually needs it for cross-origin requests (Apple's
form_post uses direct browser POSTs without CORS preflight); if it's unnecessary
remove it from the allowed origins list (e.g., the origins collection used in
the CORS configuration/bean such as the corsConfiguration or allowedOrigins
variable in SecurityConfig) otherwise leave it but add a comment explaining why
it's required for clarity. Ensure you update any related tests or documentation
that reference the CORS origins.
src/main/kotlin/com/weeth/domain/user/application/usecase/command/SocialLoginUseCase.kt (1)

42-45: TODO 주석: Apple 계정 연결 해제 구현 필요.

탈퇴 기능 구현 시 Apple Revoke Tokens API를 호출하기 위해 refresh token 저장이 필요하다는 점이 명시되어 있습니다. 이 작업을 추적하기 위한 이슈를 생성할까요?

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

In
`@src/main/kotlin/com/weeth/domain/user/application/usecase/command/SocialLoginUseCase.kt`
around lines 42 - 45, Add a tracked task and implement storing Apple refresh
tokens when handling the Apple OAuth callback in SocialLoginUseCase: exchange
the callback code at Apple’s token endpoint, persist the returned refresh_token
to the user/Auth entity (so it’s available for future revocation), and ensure
the revoke flow uses that stored refresh_token when calling the Apple Revoke
Tokens API; create an issue to track this work and link it from the TODO in
SocialLoginUseCase.
src/main/kotlin/com/weeth/domain/user/presentation/SocialCallbackController.kt (1)

72-80: 광범위한 Exception catch는 디버깅을 어렵게 할 수 있습니다.

콜백 핸들러에서 graceful degradation을 위해 모든 예외를 잡는 것은 합리적이나, 특정 예외 타입(예: JsonProcessingException, AuthenticationException)을 먼저 처리하고 로그 레벨을 다르게 하면 운영 시 문제 파악이 더 용이합니다.

♻️ 선택적 리팩토링 제안
-        } catch (e: Exception) {
-            log.error("Apple 콜백 처리 중 오류 발생", e)
+        } catch (e: com.fasterxml.jackson.core.JsonProcessingException) {
+            log.warn("Apple 콜백 JSON 파싱 오류", e)
+            redirect(
+                UriComponentsBuilder
+                    .fromUriString(frontendRedirectUri)
+                    .queryParam("error", "invalid_user_data")
+                    .toUriString(),
+            )
+        } catch (e: Exception) {
+            log.error("Apple 콜백 처리 중 예기치 않은 오류 발생", e)
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In
`@src/main/kotlin/com/weeth/domain/user/presentation/SocialCallbackController.kt`
around lines 72 - 80, In SocialCallbackController's Apple callback handler,
replace the broad catch(Exception e) with targeted catches for likely issues
first (e.g., catch com.fasterxml.jackson.core.JsonProcessingException and
org.springframework.security.core.AuthenticationException) to log more specific
messages and appropriate log levels, handle each case (return the same redirect
with specific error query param like "invalid_payload" or "auth_failed"), and
keep a final catch(Exception e) as a fallback that logs the generic error and
performs the existing redirect; update log messages to include the exception
message/stack as appropriate.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In
`@src/main/kotlin/com/weeth/domain/user/presentation/SocialCallbackController.kt`:
- Around line 55-60: redirectUri 생성 시 response.name에 한글·공백 등 특수문자가 포함될 경우 제대로
인코딩되지 않으므로 UriComponentsBuilder를 통해 쿼리 파라미터를 설정한 뒤 build()와 encode()를 호출해 모든
특수문자를 인코딩한 후 toUriString()으로 변환하도록 변경하세요; 즉 현재
UriComponentsBuilder.fromUriString(frontendRedirectUri).queryParam("registered",
response.registered).queryParam("name", response.name).toUriString() 흐름을 build()
-> encode() -> toUriString() 순서로 바꾸어 redirectUri를 생성하도록 수정하면 됩니다 (참조:
UriComponentsBuilder, frontendRedirectUri, response.name, redirectUri).
- Around line 62-71: Apple's form_post callback is dropping cookies due to
SameSite=Lax; update the cookie creation for the Apple callback in
SocialCallbackController to use SameSite=None and Secure. Add a dedicated method
on TokenCookieProvider (e.g., createAppleAccessTokenCookie and
createAppleRefreshTokenCookie or a buildCookie variant with a sameSiteOverride
param) that constructs cookies using CookieProperties or buildCookie with
sameSite="None" and secure=true, then call those methods instead of
createAccessTokenCookie/createRefreshTokenCookie in the Apple callback response
construction so the headers set HttpHeaders.SET_COOKIE include SameSite=None;
Secure.

---

Nitpick comments:
In
`@src/main/kotlin/com/weeth/domain/user/application/usecase/command/SocialLoginUseCase.kt`:
- Around line 42-45: Add a tracked task and implement storing Apple refresh
tokens when handling the Apple OAuth callback in SocialLoginUseCase: exchange
the callback code at Apple’s token endpoint, persist the returned refresh_token
to the user/Auth entity (so it’s available for future revocation), and ensure
the revoke flow uses that stored refresh_token when calling the Apple Revoke
Tokens API; create an issue to track this work and link it from the TODO in
SocialLoginUseCase.

In
`@src/main/kotlin/com/weeth/domain/user/presentation/SocialCallbackController.kt`:
- Around line 72-80: In SocialCallbackController's Apple callback handler,
replace the broad catch(Exception e) with targeted catches for likely issues
first (e.g., catch com.fasterxml.jackson.core.JsonProcessingException and
org.springframework.security.core.AuthenticationException) to log more specific
messages and appropriate log levels, handle each case (return the same redirect
with specific error query param like "invalid_payload" or "auth_failed"), and
keep a final catch(Exception e) as a fallback that logs the generic error and
performs the existing redirect; update log messages to include the exception
message/stack as appropriate.

In `@src/main/kotlin/com/weeth/global/config/SecurityConfig.kt`:
- Line 91: Review the CORS origin entry "https://appleid.apple.com" in
SecurityConfig and confirm whether the application actually needs it for
cross-origin requests (Apple's form_post uses direct browser POSTs without CORS
preflight); if it's unnecessary remove it from the allowed origins list (e.g.,
the origins collection used in the CORS configuration/bean such as the
corsConfiguration or allowedOrigins variable in SecurityConfig) otherwise leave
it but add a comment explaining why it's required for clarity. Ensure you update
any related tests or documentation that reference the CORS origins.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 018f8452-7701-4b01-b25e-d83fc24884bd

📥 Commits

Reviewing files that changed from the base of the PR and between 784ac94 and c0419ed.

📒 Files selected for processing (9)
  • src/main/kotlin/com/weeth/domain/user/application/dto/response/SocialLoginResponse.kt
  • src/main/kotlin/com/weeth/domain/user/application/mapper/UserMapper.kt
  • src/main/kotlin/com/weeth/domain/user/application/usecase/command/SocialLoginUseCase.kt
  • src/main/kotlin/com/weeth/domain/user/domain/port/SocialAuthPort.kt
  • src/main/kotlin/com/weeth/domain/user/infrastructure/AppleSocialAuthAdapter.kt
  • src/main/kotlin/com/weeth/domain/user/presentation/SocialCallbackController.kt
  • src/main/kotlin/com/weeth/global/config/SecurityConfig.kt
  • src/main/kotlin/com/weeth/global/config/properties/OAuthProperties.kt
  • src/main/resources/application.yml

Comment on lines +62 to +71
ResponseEntity
.status(HttpStatus.FOUND)
.header(HttpHeaders.LOCATION, redirectUri)
.header(
HttpHeaders.SET_COOKIE,
tokenCookieProvider.createAccessTokenCookie(response.accessToken).toString(),
).header(
HttpHeaders.SET_COOKIE,
tokenCookieProvider.createRefreshTokenCookie(response.refreshToken).toString(),
).build()
Copy link
Copy Markdown

@coderabbitai coderabbitai bot Mar 31, 2026

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟠 Major

🧩 Analysis chain

🌐 Web query:

SameSite cookie behavior on cross-origin POST redirect 302 response

💡 Result:

SameSite cookie behavior on a cross-origin POST request followed by a 302 redirect depends on the SameSite attribute value (Strict, Lax, or None) and whether the subsequent redirect request is classified as "same-site" or "cross-site". Cookies set in the 302 response are always stored by the browser before following the redirect (result 1), but whether existing cookies (including those just set) are sent on the follow-up request depends on SameSite rules. Key concepts from specs (results 9,10,13,14,18): - A request is "cross-site" if the initiator site (top-level browsing context) differs from the request URL's site (scheme+registrable domain). - For redirects: HTTP 302 redirects preserve the initiator context, so a cross-site POST keeps the chain cross-site for follow-up requests (results 3,4,22). Sec-Fetch-Site remains "cross-site". - SameSite=Strict: Cookie sent ONLY on same-site requests, never cross-site (results 3,4,9,13). - SameSite=Lax: Sent on same-site requests + cross-site top-level navigations with "safe" methods (GET, HEAD). Cross-site POST or unsafe methods: not sent. Lax-allowing-unsafe mode (some browsers) sends on cross-site top-level regardless of method, but POST after cross-origin POST redirect typically blocked (results 2,5,6,9). - SameSite=None (requires Secure): Sent on all requests, cross-site included (results 9,11). Scenario example (OAuth/login flow, results 5,6): 1. Cross-origin POST to /login (cross-site, initiator from other site). 2. Server responds 302 Location: /dashboard + Set-Cookie (session). 3. Browser stores cookie, follows with GET /dashboard. - If chain cross-site: Strict=None sent; Lax=not sent (not safe method exception); None=sent. - Common breakage with Strict/Lax leads to workarounds like meta-refresh 200 (changes to same-site navigation, result 6). For cross-origin POST 302 specifically: Cookies with Lax/Strict typically NOT sent on redirect leg if chain cross-site; use None for cross-site compatibility.

Citations:


🏁 Script executed:

# TokenCookieProvider와 쿠키 설정 관련 파일 찾기
fd -t f "TokenCookieProvider\|CookieProperties" --case-sensitive

Repository: Team-Weeth/weeth-server

Length of output: 49


🏁 Script executed:

# SocialCallbackController 전체 내용 확인
cat -n src/main/kotlin/com/weeth/domain/user/presentation/SocialCallbackController.kt

Repository: Team-Weeth/weeth-server

Length of output: 4817


🏁 Script executed:

# cookieProperties 또는 Cookie 관련 설정 파일 찾기
fd -t f -i "cookie" | grep -i "properties\|config"

Repository: Team-Weeth/weeth-server

Length of output: 137


🏁 Script executed:

# TokenCookieProvider 파일 찾기
fd -t f "TokenCookieProvider"

Repository: Team-Weeth/weeth-server

Length of output: 240


🏁 Script executed:

# CookieProperties 내용 확인
cat -n src/main/kotlin/com/weeth/global/config/properties/CookieProperties.kt

Repository: Team-Weeth/weeth-server

Length of output: 850


🏁 Script executed:

# TokenCookieProvider 내용 확인
cat -n src/main/kotlin/com/weeth/global/auth/jwt/application/service/TokenCookieProvider.kt

Repository: Team-Weeth/weeth-server

Length of output: 1994


🏁 Script executed:

# Verify if there are any alternative token handling methods or other Apple callback implementations
rg -i "apple|samesite" --type kt -A 3 -B 3 | head -80

Repository: Team-Weeth/weeth-server

Length of output: 93


🏁 Script executed:

# Check if there's any frontend token handling via query params or other methods
rg "accessToken|refreshToken" src/main/kotlin/com/weeth/domain/user/presentation/ --type kt

Repository: Team-Weeth/weeth-server

Length of output: 93


🏁 Script executed:

# Verify the scenario more directly
rg "apple" -i --max-count=20

Repository: Team-Weeth/weeth-server

Length of output: 13812


Apple 콜백의 SameSite 쿠키 이슈로 인해 토큰이 프론트엔드에 전달되지 않습니다.

Apple의 form_post 방식은 appleid.apple.com에서 크로스 오리진 POST 요청을 보내므로, 이 엔드포인트의 302 응답에 포함된 SameSite=Lax 쿠키는 브라우저가 무시합니다. 현재 CookieProperties의 기본값이 sameSite = "Lax"이고, TokenCookieProvider.buildCookie()가 이 값을 사용하기 때문에 액세스/리프레시 토큰 쿠키가 프론트엔드에 전달되지 않아 Apple 로그인이 실패합니다.

해결 방안:

  1. Apple 콜백 전용으로 SameSite=None; Secure 쿠키를 생성하는 별도 메서드 제공
  2. 또는 토큰을 쿠키 대신 리다이렉트 URL fragment(#) 또는 localStorage 스크립트로 전달하고 프론트엔드에서 처리
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In
`@src/main/kotlin/com/weeth/domain/user/presentation/SocialCallbackController.kt`
around lines 62 - 71, Apple's form_post callback is dropping cookies due to
SameSite=Lax; update the cookie creation for the Apple callback in
SocialCallbackController to use SameSite=None and Secure. Add a dedicated method
on TokenCookieProvider (e.g., createAppleAccessTokenCookie and
createAppleRefreshTokenCookie or a buildCookie variant with a sameSiteOverride
param) that constructs cookies using CookieProperties or buildCookie with
sameSite="None" and secure=true, then call those methods instead of
createAccessTokenCookie/createRefreshTokenCookie in the Apple callback response
construction so the headers set HttpHeaders.SET_COOKIE include SameSite=None;
Secure.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

백엔드와 프론트 도메인이 맞으면 문제 없지 않아?

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

@hyxklee, 맞습니다. 제 분석에 보완이 필요합니다.

Set-Cookie 헤더는 응답에서 쿠키를 저장하는 역할이고, SameSite 속성은 쿠키를 요청에 포함해 전송할 때만 적용됩니다. 즉, Apple에서 크로스 오리진 POST로 들어와도 302 응답의 Set-Cookie는 브라우저에 정상적으로 저장됩니다.

이후 백엔드와 프론트엔드가 동일한 registrable domain(e.g., api.weeth.krx.weeth.kr → 둘 다 weeth.kr)을 공유하고, 쿠키의 Domain 속성이 .weeth.kr로 설정되어 있다면, SameSite=Lax 쿠키는 same-site 요청으로 간주되어 정상적으로 전송됩니다.

따라서 두 도메인이 같은 eTLD+1을 공유한다면 제가 지적한 SameSite=Lax 이슈는 해당되지 않습니다. 지적이 맞습니다.


✏️ Learnings added
Learnt from: hyxklee
Repo: Team-Weeth/weeth-server PR: 44
File: src/main/kotlin/com/weeth/domain/user/presentation/SocialCallbackController.kt:62-71
Timestamp: 2026-03-31T06:54:59.595Z
Learning: In the weeth-server project (Kotlin/Spring), the Apple Sign In callback (SocialCallbackController) sets SameSite=Lax cookies in the 302 redirect response. This is acceptable as long as the backend and frontend share the same registrable domain (e.g., both under weeth.kr), because Set-Cookie stores cookies regardless of SameSite, and SameSite=Lax allows same-site requests. The SameSite=None concern would only apply if backend and frontend are on completely different domains.

Note: Learnings are effective only in the context of similar code segments. To apply general coding guidelines, please configure review instructions. You can manage existing learnings in the app.

Copy link
Copy Markdown
Collaborator

@soo0711 soo0711 left a comment

Choose a reason for hiding this comment

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

수고하셨습니다!! 리뷰 하나 확인부탁드려용

.header(HttpHeaders.LOCATION, uri)
.build()

private fun parseAppleUserName(userJson: String?): String? {
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

컨트롤러는 요청/응답과 흐름 제어를 담당하는데
해당 매서드(파싱, 추출)은 도메인로직에 가까워보입니당
유스케이스로 책임을 이동하는 건 어떨까요?? 아니면 별도의 추출클래스로 만들어도 괜찮을 것 같아욤

Copy link
Copy Markdown

@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.

Caution

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

⚠️ Outside diff range comments (1)
src/test/kotlin/com/weeth/domain/user/application/usecase/command/SocialLoginUseCaseTest.kt (1)

38-47: ⚠️ Potential issue | 🟠 Major

Apple callback 핵심 경로 테스트가 빠져 있습니다.

ObjectMapper 의존성이 추가됐지만, 현재 케이스는 socialLoginByApple 중심이라 socialLoginByAppleCallback의 이름 파싱(정상 JSON/비정상 JSON/null user) 경로 회귀를 잡기 어렵습니다. 이번 PR 목표(로그인 시 이름 반환)를 직접 검증하는 테스트를 보강해 주세요.

테스트 보강 예시
+        describe("socialLoginByAppleCallback") {
+            it("user JSON에서 이름을 파싱해 반환한다") {
+                // given
+                // when
+                // then: result.name shouldBe "홍길동"
+            }
+
+            it("user JSON이 없거나 파싱 실패 시 name은 null로 처리된다") {
+                // given malformed/null user json
+                // when
+                // then: result.name shouldBe null
+            }
+        }
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In
`@src/test/kotlin/com/weeth/domain/user/application/usecase/command/SocialLoginUseCaseTest.kt`
around lines 38 - 47, Add unit tests covering the Apple callback parsing paths
for SocialLoginUseCase: specifically exercise the socialLoginByAppleCallback
flow using the injected ObjectMapper to simulate (1) valid JSON with a name, (2)
invalid/malformed JSON, and (3) JSON that yields a null user; assert that when
valid JSON is provided the returned login result includes the user's name (per
PR goal), and for invalid or null cases the use case handles errors or nulls as
expected. Locate and extend SocialLoginUseCaseTest to mock
ObjectMapper.deserialize behavior (or readTree) for those three scenarios,
invoke SocialLoginUseCase.socialLoginByAppleCallback (or the method that
delegates to it) and verify interactions with
userRepository/userSocialAccountRepository and the jwtManageUseCase as
appropriate. Ensure tests assert both successful name propagation and proper
fallback/error handling.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Outside diff comments:
In
`@src/test/kotlin/com/weeth/domain/user/application/usecase/command/SocialLoginUseCaseTest.kt`:
- Around line 38-47: Add unit tests covering the Apple callback parsing paths
for SocialLoginUseCase: specifically exercise the socialLoginByAppleCallback
flow using the injected ObjectMapper to simulate (1) valid JSON with a name, (2)
invalid/malformed JSON, and (3) JSON that yields a null user; assert that when
valid JSON is provided the returned login result includes the user's name (per
PR goal), and for invalid or null cases the use case handles errors or nulls as
expected. Locate and extend SocialLoginUseCaseTest to mock
ObjectMapper.deserialize behavior (or readTree) for those three scenarios,
invoke SocialLoginUseCase.socialLoginByAppleCallback (or the method that
delegates to it) and verify interactions with
userRepository/userSocialAccountRepository and the jwtManageUseCase as
appropriate. Ensure tests assert both successful name propagation and proper
fallback/error handling.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 27be175f-2a32-4fc2-9adf-326f5ddce34b

📥 Commits

Reviewing files that changed from the base of the PR and between c780891 and 5f1ad28.

📒 Files selected for processing (1)
  • src/test/kotlin/com/weeth/domain/user/application/usecase/command/SocialLoginUseCaseTest.kt

@hyxklee hyxklee merged commit 60f941c into dev Apr 1, 2026
2 checks passed
@hyxklee hyxklee deleted the refactor/WTH-237-로그인-시-유저-정보-반환 branch April 1, 2026 06:11
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

🐞 BugFix 버그 수정

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants