Skip to content

Screen: DisclosureDetail (공시 상세)

특정 공시 한 건의 상세 화면. AI 분석 카드 (lazy reveal) + 메타 + 이전 공시 list (App).

💡 시각 미리보기:

진입 경로

  • App: dashboard 의 DisclosureItem 탭 / push 알림 / company detail 의 PreviousDisclosuresList 탭
  • Web: dashboard (/) 의 DisclosureItem 링크 / 공시 SNS 공유 링크 / 검색 엔진

URL: /disclosures/[rceptNo]

플랫폼별 차이

항목App (Flutter)Web (Next.js)
인증로그인 시 풀기능, 비로그인은 requireAuth 게이트비로그인 한정 (로그인 UI 없음)
AnalysisCard풀버전 — reveal / 광고 / 피드백 mechanicsmeta only — 요약만 (일부 마스킹)
Quota 표시QuotaIndicator (HP bar) 하위없음
AuthGaterequireAuth 흐름 (reveal / feedback 트리거 시)없음
보상형 광고광고 시청 시 quota 1회 회복없음
이전 공시 listPreviousDisclosuresList (같은 종목 N건)없음
AppCTA없음"전체 분석은 앱에서" 모달
DART 원문in-app browser sheettarget=_blank 외부 링크
Renderingclient-side (Riverpod)SSR + ISR (revalidate=300)

App — 화면 구성

영역컴포넌트조건
AppBar← back + "공시 상세"항상
HeaderCardcorp 칩 + report name + meta list + DART 원문 보기 CTA항상
AnalysisCardAI 분석 (M1~M9 / W1~W5 상태 분기)항상
QuotaIndicatorHP bar항상
PreviousDisclosuresList같은 종목 이전 공시 list데이터 있을 때

App — 상태 분기 (전체 화면)

  • D1. 로딩 — spinner + "공시 정보를 불러오는 중..."
  • D2. 에러 — 메시지 (error ?? '공시를 찾을 수 없습니다.')
  • D3. 정상 — Header + AnalysisCard + Quota + PreviousList

App — AnalysisCard 상태 (M1~M9 / W1~W5)

AnalysisCard 컴포넌트 자체 spec: components/analysis-card.html. 화면 단위에서는 다음 흐름:

  • M1. 분석 안 됨 (PENDING) — "AI가 곧 분석할 예정이에요"
  • M2. 분석 중 (PROCESSING) — spinner + "AI 가 분석 중이에요"
  • M3. 분석 완료, 미 reveal — Summary 줄 (이미 동봉) + "본문 분석 보기" CTA → reveal flow
  • M4. Reveal 완료 — 본문 분석 풀 노출 + feedback 인라인
  • M5. Quota 소진 — Summary + "이번 주 분석 한도 소진" + 광고 시청 CTA
  • M6. Reveal 사용 — quota 1회 차감 → POST /api/v1/ai/analyze/{rceptNo}/reveal
  • M7. 광고 시청 (보상형)RewardedAdController.showAd() → quota 1회 회복
  • M8. 짧은 공시 (isShort) — reveal 안 함, summary 자체가 본문 역할
  • M9. 분석 불가 (UNAVAILABLE) — "AI 가 분석하기 어려운 공시예요"
  • W1~W5: AuthGate / 네트워크 에러 / 재시도 등 — flow-auth-gate spec 참조

App — 진입 시 API 호출

GET /api/v1/disclosures/{rceptNo}        → DisclosureDetail (corp / report_name / meta / previous)
GET /api/v1/ai/analyze/{rceptNo}         → AnalyzeMeta (status / isShort / alreadyRevealed)
GET /api/v1/quota                        → QuotaStatus (HP bar)

App — 액션

Reveal (본문 분석 보기)

  1. AnalysisCard CTA 탭 → requireAuth 통과 시
  2. POST /api/v1/ai/analyze/{rceptNo}/reveal
  3. 성공: analysis 본문 노출 + alreadyRevealed=true + quota 1 차감
  4. 실패 (quota 소진): M5 상태로 → 광고 시청 옵션
  5. 실패 (인증 만료): flow-auth-gate → 재시도

광고 시청 (Rewarded Ad)

  1. M5 상태 CTA 탭 → RewardedAdController.showAd()
  2. 시청 완료 → quota +1 (음수 weeklyUsed 가능, M5 → M3 회복)
  3. 시청 중간 종료 → 회복 없음, M5 유지
  4. 자동으로 retryAfterAd() 호출 → analyze meta refetch

피드백 (Reveal 후)

  1. 별점 (1~5) + 태그 (다중) 선택 → requireAuth 통과 시
  2. PUT /api/v1/ai/analyze/{rceptNo}/feedback {rating, tags} (upsert)
  3. UI 인라인 토스트 ("피드백 감사합니다")

피드백 삭제

  1. 본인이 남긴 피드백 영역의 X 탭
  2. DELETE /api/v1/ai/analyze/{rceptNo}/feedback

DART 원문 보기

App 내 in-app browser sheet (InAppBrowserSheet) 로 DART 공식 URL 오픈.

이전 공시 탭

PreviousDisclosuresList 의 item 탭 → context.push('/disclosures/{otherRceptNo}') (라우터 재진입).


Web — 화면 구성

영역컴포넌트조건
AppBar← back to / + "공시 상세"항상
HeaderCardcorp Link (/?corp={corpCode} — 대시보드 종목 필터) + report name + meta list + DART 원문 외부 링크항상
AnalysisCardmeta 기반 (요약만, 본문 마스킹)항상
AppCTA인라인 "전체 분석은 앱에서" + App Store / Play disabled 버튼 (준비 중) — 모달 X항상

Web — 상태 분기

비로그인 한정 단일 상태:

  • D1. 404fetchDisclosure null → Next.js notFound() → 404 페이지
  • D2. 정상 — Header + AnalysisCard (요약만) + AppCTA

Web — AnalysisCard 상태 (Web 전용 subset)

  • W-M1. 분석 안 됨 — "AI가 곧 분석할 예정이에요" (App 과 동일 카피)
  • W-M2. 분석 중 — spinner + 카피
  • W-M3. 분석 완료 — Summary 줄만 노출, "본문 분석은 앱에서" 안내 (reveal 없음)
  • W-M8. 짧은 공시 — summary 풀 노출 (App 과 동일)
  • W-M9. 분석 불가 — 카피만

Web — 진입 시 API 호출

SSR + ISR (revalidate=300):

GET /api/v1/disclosures/{rceptNo}        → Disclosure
GET /api/v1/ai/analyze/{rceptNo}         → AnalyzeMeta (요약만 사용)

Web — 액션

DART 원문 보기

<a target=_blank> 외부 링크 (https://dart.fss.or.kr/dsaf001/main.do?rcpNo={rceptNo}).

AppCTA (인라인)

<AppCTA /> 가 본문 하단에 인라인 렌더 — "전체 분석은 앱에서" + App Store / Play disabled 버튼 (준비 중). 모달/핸들러 없음, 단순 표시.

공시 카드 SNS 공유

generateMetadata 가 OpenGraph 채움 → {corp_name} - {report_name} | 공시한입 으로 카카오톡 / 트위터 미리보기.


액션 카탈로그 (전체)

액션endpointmethodrequestresponseAppWeb
공시 메타 조회/api/v1/disclosures/{rceptNo}GETDisclosureDetail
분석 메타 조회/api/v1/ai/analyze/{rceptNo}GETAnalyzeMeta✅ (요약만)
Reveal 본문 분석/api/v1/ai/analyze/{rceptNo}/revealPOSTAnalysis
피드백 제출 (upsert)/api/v1/ai/analyze/{rceptNo}/feedbackPUT{rating, tags}204
피드백 삭제/api/v1/ai/analyze/{rceptNo}/feedbackDELETE204
광고 보상/api/v1/quota/ad-rewardPOSTQuotaStatus
Quota 조회/api/v1/quotaGETQuotaStatus

Edge cases

App

  • 인증 만료 (401) — reveal/feedback 시점: requireAuth 가 AuthGate 모달 띄움 (자세히 flow-auth-gate.md — 예정, 아직 미작성)
  • 광고 SDK 미로드: Rewarded button disabled, 자동 재시도
  • 광고 중간 종료: quota 회복 X, M5 유지
  • race — reveal 중 quota 소진 통보 (다른 디바이스): BE 가 reveal 실패 응답 → M5 로 전환
  • PreviousDisclosuresList 빈 결과: 섹션 자체 hide (헤더 X)

Web

  • 공시 not found (rceptNo 잘못됨): notFound() → Next.js 404
  • 백엔드 403 (CF Worker secret 없음): getJSONSoft null 삼킴, AnalysisCard 빈 상태
  • OpenGraph metadata 빈 응답: title 만 "공시 상세 | 공시한입" 으로 fallback
  • ISR cache stale: 5분(300s) 후 revalidate, 그 사이는 stale-while-revalidate

관련 docs

Status

  • ✅ App — 모든 상태 / API / 액션 구현 일치
  • ✅ Web — meta only 모드 + AppCTA 구현 일치
  • 📋 광고 보상 시 quota 회복 UI 깜빡임 — 별도 backlog