Files
portfolio-hub/docs/discovery/dcy-009_20260627_user-read-asset-catalog-and-daemons.md
T
genichinandClaude Opus 4.8 d43ff430c2 docs(dcy-009): 사용자용 read 엔드포인트 discovery confirmed + REQ-044/045 approved
- dcy-009: GET /v1/assets require_read 완화 + 사용자 가용 데몬 목록 신규 (trex-web 포트폴리오 관리 발원)
- REQ-044(assets 권한 완화) / REQ-045(사용자 데몬 목록) — Approved
- 전부 read 추가(쓰기·데몬관리 제외)

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01VHtM5Ws1HKCKQ4JGi6GRb5
2026-06-27 10:16:23 +09:00

11 KiB

0. 문서 상태

이 문서의 현재 상태와 식별 정보를 기록한다. 문서 추적과 승인 흐름에 필요한 최소 메타데이터를 적는다.

  • 상태: confirmed
  • 문서 ID: dcy-009_20260627_user-read-asset-catalog-and-daemons
  • 이슈명: 사용자용 read 엔드포인트 2종 — asset 카탈로그 조회 권한 완화(require_read) + 사용자 가용 데몬 목록 신규
  • 작성 시각(KST): 2026-06-27 10:07
  • 마지막 갱신 시각(KST): 2026-06-27 10:30
  • 대체됨: 없음
  • 후속 Discovery 참조: 없음
  • 교차 서비스 발원(driver): trex-web 포트폴리오 관리(예정 dcy-007) — 사용자가 자신의 포트폴리오를 생성/변경할 때 ① asset 리스트에서 종목을 고르고 ② 자신이 사용 가능한 데몬을 선택해야 한다. 두 선택 UI에 필요한 read API가 portfolio-hub에 없다(asset 목록은 admin 전용, 사용자 데몬 목록은 라우트 미노출). 본 Discovery는 그 의존을 portfolio-hub측 변경 단위로 정식화한다. (trex-web 포트폴리오 관리 UI는 별도 trex-web dcy-007.)
  • 생성된 REQ 참조: REQ-044, REQ-045

1. 계획 상태 요약

  • 연계 문서 현황:
    • 관련 점수 파일: 없음
    • 관련 TODO/메모: 워크스페이스 GitHub 보드 #7 trex-web 항목. 발원 = trex-web 포트폴리오 관리.
  • 해석:
    • trex-web에서 "각 사용자가 자기 포트폴리오를 관리(생성/변경)"하려면 asset 선택·가용 데몬 선택이 필요한데, portfolio-hub의 해당 read 경로가 사용자에게 막혀 있다.
    • 사장님 결정(2026-06-27): GET /v1/assets를 require_read로 완화, 사용자 가용 데몬 목록 read 엔드포인트 신규. 백엔드를 먼저 만들고 trex-web UI를 얹는다.

2. 요구사항 판정 결과

  • 판정: 신규
  • 근거
    • asset 카탈로그 조회 권한 완화는 기존 REQ(자산 카탈로그, admin 전용)의 접근 정책 변경 + 신규 사용자 데몬 목록 엔드포인트는 신규 인터페이스다.
    • 포트폴리오 관리(생성/변경 시 선택 UI 공급)라는 새 소비 맥락에서 발생한 read 표면 확장이다.

3. 문제점의 요약

  • 현재 상태
    • GET /v1/assets(app/api/v1_assets.py:75 list_catalog_assets)는 require_admin — 일반 사용자가 asset 카탈로그를 읽을 수 없다. (생성/비활성/태그 등 쓰기도 require_admin.)
    • 사용자 가용 데몬을 조회하는 HTTP 엔드포인트가 없다. 도메인 Daemon(id·owner_user_id·daemon_slug·display_name·is_active) 존재 + 서비스/리포지토리에 list_daemons_for_user(user_id)·find_candidate_daemons_for_user(user_id)가 있으나 라우트로 노출되지 않음.
    • 포트폴리오 CRUD(POST/PATCH/DELETE /v1/portfolios)는 이미 owner-scoped require_read로 존재(이번 변경 대상 아님). 포트폴리오는 managed_by_daemon_id로 데몬에 바인딩됨(PATCH로 설정 가능).
  • 기대 상태
    • 일반 사용자(require_read)가 active asset 카탈로그를 조회할 수 있다(쓰기 권한은 admin 유지).
    • 일반 사용자가 자신이 사용 가능한 데몬 목록(자기 소유 active 데몬)을 조회할 수 있다 — 포트폴리오의 managed_by_daemon_id로 선택할 후보.
  • 이해관계자
    • 사장님 — 접근 정책(카탈로그 공개 범위)·우선순위 결정
    • 팀장(Claude) — Discovery/거버넌스 게이트
    • portfolio-hub-dev — delivery(백엔드)
    • trex-web(소비자) / 일반 사용자
  • 제약사항
    • asset 쓰기(생성/비활성/태그 적용)는 admin 유지(완화는 읽기에 한정).
    • 데몬 목록은 caller 본인(user_id) 스코프(타 사용자 데몬 노출 금지).
    • 기존 admin asset 관리·서비스 토큰 daemon 바인딩 동작에 회귀 없어야 함.

주요 사용자 시나리오

  • 사용자가 trex-web에서 포트폴리오를 추가할 때, asset 선택 드롭다운/검색이 GET /v1/assets(read)로 active 카탈로그를 불러온다.
  • 사용자가 포트폴리오의 관리 데몬을 고를 때, "내 가용 데몬" 목록을 신규 엔드포인트로 불러와 선택한다.
  • admin은 기존대로 asset 카탈로그를 생성/수정/비활성(쓰기)한다(권한 불변).

4. 이번에 정의할 변경

  • 변경 1 — GET /v1/assets 권한 완화: require_admin → require_read. status 필터(기본 active)·market 필터 동작 유지. 쓰기 엔드포인트(POST/PATCH/DELETE assets, 태그)는 require_admin 유지.
  • 변경 2 — 사용자 가용 데몬 목록 read 엔드포인트 신규: caller(user_id) 소유 active 데몬을 반환(id·daemon_slug·display_name·is_active). require_read, caller 스코프. 기존 서비스 메서드(list_daemons_for_user) 활용.

영향 범위

  • 코드 영향: app/api/v1_assets.py(GET 권한 완화), 데몬 목록 라우트 신규(app/api/—경로 design), app/services/auth_service.py(기존 list_daemons_for_user 노출용 wiring), 응답 스키마(DaemonResponse 신규 가능).
  • 문서 영향: docs/srs/(REQ), docs/discovery/index.md. API 계약 문서.
  • 운영 영향: asset 카탈로그가 전 인증 사용자에게 read 공개됨(쓰기 불변). 배포 시 계약 변경 고지.

5. 요구사항 목록

기능 요구사항

  • FR-1: GET /v1/assets를 require_read로 완화해 일반 사용자가 active asset 카탈로그를 조회할 수 있다. 기존 status/market 필터·응답 스키마 유지. asset 쓰기(생성/비활성/태그)는 require_admin 유지.
  • FR-2: 사용자 가용 데몬 목록 read 엔드포인트를 추가한다 — require_read, caller(user_id) 소유 데몬(active) 반환. 응답 필드 id·daemon_slug·display_name·is_active.

비기능 요구사항

  • NFR-1: 기존 admin asset 관리(쓰기)·서비스 토큰 daemon 바인딩 동작에 회귀 0.
  • NFR-2: 데몬 목록은 caller 본인 데몬만 반환(타 사용자 데몬 비노출) — 권한/스코프 정확.

범위 경계

  • In Scope
    • GET /v1/assets require_read 완화
    • 사용자 가용 데몬 목록 read 엔드포인트 신규
  • Out of Scope
    • asset 카탈로그 쓰기(생성/수정/비활성/태그) 권한 변경(admin 유지)
    • 데몬 생성/수정/삭제 등 데몬 관리(이번엔 read 목록만)
    • 포트폴리오 CRUD 자체(기존 존재) 및 trex-web UI(별도 trex-web dcy-007)

6. 리스크/가정 목록

리스크

  • R-1 (Low): asset 카탈로그를 전 사용자 read 공개 — 민감 정보 노출 우려.
    • 완화 방안: 카탈로그는 거래 가능 종목 메타(민감도 낮음). 쓰기는 admin 유지. 필요 시 status=active만 기본 노출.
  • R-2 (Low): 데몬 목록 스코프 오류로 타 사용자 데몬 노출.
    • 완화 방안: caller user_id 스코프 강제(list_daemons_for_user(auth.user_id)), 테스트로 타 사용자 비노출 검증.

가정

  • A-1: 도메인 Daemon(owner_user_id)·list_daemons_for_user가 사용자 소유 데몬을 정확히 반환한다.
  • A-2: asset 카탈로그(거래 종목 메타)는 전 인증 사용자에게 read 공개해도 무방하다(사장님 승인).
  • A-3: 포트폴리오의 managed_by_daemon_id에 넣을 후보 = 사용자 소유 데몬(이 목록).

오픈 질문

  • OQ-1: GET /v1/assets require_read 완화 — 승인 여부.
    • 상태: Answered (2026-06-27, 사장님) — require_read로 완화 확정(쓰기는 admin 유지). FR-1 반영.
  • OQ-2: 데몬 목록 엔드포인트 경로·형태 — 예: GET /v1/daemons(caller 스코프) vs GET /v1/users/me/daemons. 응답 스키마(DaemonResponse) 형태.
    • 상태: Deferred
    • 처리 방안: draft-batch-design에서 기존 라우팅 컨벤션에 맞춰 확정.
    • 종료 조건: design에서 경로·스키마 확정 시 Answered.
  • OQ-3: "가용 데몬" 정의 — 사용자 소유 active 데몬(list_daemons_for_user)으로 충분한지, 아니면 미바인딩 후보(find_candidate_daemons_for_user) 의미가 필요한지.
    • 상태: Deferred
    • 처리 방안: design에서 trex-web 포트폴리오 배정 요구(managed_by_daemon_id 후보)에 맞는 의미 1개 확정. 기본안 = 사용자 소유 active 데몬 전체.
    • 종료 조건: design에서 의미 확정 시 Answered.

오픈 질문 처리 기준

  • Open/Answered/Deferred/Dropped 표준 처리.

7. 초기 성공 기준

  • S-1: 일반 사용자(read) 세션으로 GET /v1/assets 호출 시 200 + active 카탈로그 반환(admin 아님).
  • S-2: 일반 사용자가 asset 쓰기(POST/PATCH/DELETE) 시 여전히 403(admin 전용 유지).
  • S-3: 사용자 가용 데몬 목록 엔드포인트가 caller 소유 데몬만 반환(타 사용자 데몬 비노출).
  • S-4: 기존 admin asset 관리·토큰 daemon 바인딩 회귀 0.

측정 방식 및 데이터 출처

  • S-1/S-2: read·admin·다른권한 토큰별 통합 테스트(권한 매트릭스) / 데이터 출처: pytest.
  • S-3: 2명 사용자 데몬 fixture로 스코프 테스트 / pytest.
  • S-4: 기존 v1_assets·auth 테스트 회귀 / pytest.

8. REQ로 넘기기 전 확인 체크

  • 범위(In/Out) 확정 — read 2종 In, 쓰기·데몬관리·UI Out (사장님 합의)
  • 성공 지표 측정 방식 — 권한 매트릭스·스코프 테스트
  • High 리스크 없음(R-1/R-2 Low)
  • OQ-2/OQ-3(엔드포인트 경로·가용데몬 의미) design 인계
  • Freeze 담당자(CONFIRMED_BY) — 팀장

9. 파일 처리 결과

  • 처리 결과: 생성
  • 생성 경로: docs/discovery/dcy-009_20260627_user-read-asset-catalog-and-daemons.md
  • 참조 문서:
    • .github/templates/discovery/discovery.md (템플릿)
    • app/api/v1_assets.py(GET /v1/assets — 완화 대상), app/domain/models.py(Daemon), app/services/auth_service.py(list_daemons_for_user)
    • 발원: trex-web 포트폴리오 관리(예정 trex-web dcy-007)

10. 사용자 결정 필요 항목 요약

DECIDE

  • (해소됨, 2026-06-27) GET /v1/assets require_read 완화 — 승인.

CONFIRM

  • (해소됨, 2026-06-27) 백엔드 read 2종(asset 완화 + 사용자 데몬 목록) 단위 채택 — 쓰기·데몬관리·trex-web UI 제외. 백엔드 우선 진행.

DATA

  • (확인됨) Daemon 필드 id·owner_user_id·daemon_slug·display_name·is_active. asset GET 응답 = AssetCatalogListResponse.

11. Discovery Freeze

섹션 참조

Freeze 플래그

  • Handoff Decision: REQ Drafting 진행 가능
  • Handoff Rationale: 범위·asset 완화 승인 완료(사장님). OQ-2(엔드포인트 경로)·OQ-3(가용데몬 의미)만 design Deferred — REQ 인계 가능.
  • Ready for REQ Drafting: true
  • Confirmed By: 팀장 (Claude)
  • Confirmed At (KST): 2026-06-27 10:07
  • 비고: 본 Discovery는 사장님이 백엔드 변경(asset 완화 + 데몬 목록 read)을 명시 승인했으므로 작성과 동시에 confirm 처리. 상태는 confirm-discovery 게이트에서 confirmed로 전환.

12. 작성 가이드

  • portfolio-hub .github/templates discovery 기반. trex-web dcy-007(UI)이 이 엔드포인트를 소비한다. design에서 OQ-2/3 확정.