# [Flow] 사용자 동의 내역 조회 및 동기화 흐름

이 문서는 DevFront(개발자 포털)에서 클라이언트별 사용자 동의 내역을 조회하는 기능의 전체적인 데이터 흐름과 백엔드 로직을 설명합니다. 이 기능의 핵심은 Ory Hydra의 API 제약을 우회하고 멀티 테넌트 환경에서 데이터를 격리하기 위해 Baron SSO 자체 DB를 활용하는 것입니다.

## 1. 데이터 동기화 (자체 DB에 저장)

사용자의 동의 상태가 변경될 때마다 Baron SSO의 `client_consents` 테이블에 실시간으로 데이터가 동기화됩니다.

### 1.1. 사용자가 최초로 동의할 때

-   **시작점**: 사용자가 로그인 후 동의 화면에서 "허용" 버튼을 클릭합니다.
-   **파일**: `backend/internal/handler/auth_handler.go`
-   **함수**: `AcceptConsentRequest`
-   **로직**:
    1.  프론트엔드로부터 `consent_challenge`와 사용자가 선택한 `scopes`를 전달받습니다.
    2.  `h.Hydra.AcceptConsentRequest`를 호출하여 Ory Hydra에 동의를 최종 승인합니다.
    3.  Hydra 요청이 성공하면, `domain.ClientConsent` 모델 객체를 생성합니다.
    4.  `h.ConsentRepo.Upsert` 함수를 호출하여 `client_consents` 테이블에 해당 동의 내역을 저장(INSERT 또는 UPDATE)합니다.

### 1.2. 사용자가 이미 동의하여 자동으로 승인될 때

-   **시작점**: 이미 동의한 사용자가 다시 로그인을 시도하여 동의 화면이 생략(`skip: true`)될 때.
-   **파일**: `backend/internal/handler/auth_handler.go`
-   **함수**: `GetConsentRequest`
-   **로직**:
    1.  Ory Hydra로부터 `skip: true` 응답을 받습니다.
    2.  백엔드는 이 요청을 자동으로 수락하기 위해 `h.Hydra.AcceptConsentRequest`를 내부적으로 호출합니다.
    3.  자동 승인이 성공하면, **마찬가지로 `h.ConsentRepo.Upsert`를 호출하여 `client_consents` 테이블의 데이터를 최신 상태로 동기화합니다.** 이는 동의 내역의 일관성을 보장합니다.

## 2. 데이터 조회 (DevFront 목록 표시)

관리자가 DevFront에서 동의 내역을 조회할 때의 흐름입니다.

-   **시작점**: 관리자가 DevFront의 `Consent & Users` 페이지에 진입합니다.
-   **파일**: `devfront/src/features/clients/ClientConsentsPage.tsx`
-   **로직**:
    1.  React Query의 `useQuery` 훅이 실행되면서 백엔드 API `GET /api/v1/dev/consents?client_id=<ID>`를 호출합니다.
    2.  (보안) 이때 axios interceptor 등을 통해 현재 관리자의 **테넌트 ID가 담긴 `X-Tenant-ID` 헤더**를 함께 전송합니다.

-   **파일**: `backend/internal/handler/dev_handler.go`
-   **함수**: `ListConsents`
-   **로직**:
    1.  `client_id`와 `X-Tenant-ID` 헤더 값을 파라미터로 받습니다.
    2.  **테넌트 ID 유무에 따라 분기합니다**:
        -   `X-Tenant-ID`가 있으면, `h.ConsentRepo.ListByTenant`를 호출합니다.
        -   `X-Tenant-ID`가 없으면 (e.g., 슈퍼 관리자), `h.ConsentRepo.List`를 호출합니다.

-   **파일**: `backend/internal/repository/client_consent_repository.go`
-   **함수**: `ListByTenant`
-   **로직**:
    1.  **가장 핵심적인 데이터 격리 로직이 실행됩니다.**
    2.  GORM을 사용하여 `client_consents` 테이블과 `users` 테이블을 `JOIN`합니다.
    3.  `WHERE` 절을 통해 `client_id`와 **관리자의 `tenant_id`**를 동시에 조건으로 사용하여, 해당 테넌트에 속한 사용자들의 동의 내역만 안전하게 필터링합니다.
    4.  조회된 결과를 `DevHandler`로 반환합니다.

-   **파일**: `backend/internal/handler/dev_handler.go`
-   **함수**: `ListConsents` (계속)
-   **로직**:
    1.  Repository로부터 필터링된 동의 목록을 전달받습니다.
    2.  목록의 각 항목(사용자 `subject`)에 대해 `h.KratosAdmin.GetIdentity`를 호출하여 Kratos로부터 사용자 이름, 이메일 등 추가 정보를 가져와 응답 데이터를 보강합니다.
    3.  최종적으로 보강된 데이터를 JSON 형태로 프론트엔드에 반환합니다.

-   **파일**: `devfront/src/features/clients/ClientConsentsPage.tsx` (계속)
-   **로직**:
    1.  `useQuery`가 성공적으로 데이터를 받아오면, 상태가 업데이트되고 화면에 테이블 형태로 동의 내역이 렌더링됩니다.

## 3. 데이터 철회 (동의 취소)

-   **시작점**: 관리자가 DevFront의 동의 목록에서 "Revoke" 버튼을 클릭합니다.
-   **파일**: `backend/internal/handler/dev_handler.go`
-   **함수**: `RevokeConsents`
-   **로직**:
    1.  `h.Hydra.RevokeConsentSessions`를 호출하여 Ory Hydra에서 실제 OIDC 세션을 무효화합니다.
    2.  성공 시, `h.ConsentRepo.Delete`를 호출하여 `client_consents` 테이블에서도 해당 동의 내역을 삭제하여 상태를 일치시킵니다.
