다크모드
민원(complaint) 게시판 — BE 참고 매뉴얼
독자: BE 개발자/AI. board seam 계약 · 멤버 FK · 영속 · 실 fetch 교체점 · ERP 교차링크. 정본 spec:
docs/superpowers/specs/2026-06-27-complaint-member-integration.md. as-built 2026-06-27.
1. 아키텍처 (seam 레이어)
BoardListOrg/BoardDetailOrg (view) → useBoard(boardKey) (흐름·state) → boardApi (데이터 seam) → boardFixtures (데모)- boardApi = 통합 경계(the seam). 실 BE는
lib/board/api.js만 fetch/axios로 교체 → 상위 무변경(seam 주석). - boardKey:
'notice'(공지·무상태) |'complaint'(민원·상태워크플로·ERP 연결).
2. 민원 데이터 모델
post = { id, no, category, title, body, date, views, comments, hasAttachment, isNew, isPrivate, status,
memberCode, // demoSeed member FK (작성자=입주민)
unitCode, // demoSeed unit FK (대상 호·교차링크 키)
assignee } // 담당자(관리소장/직원 문자열) | null- category: facility/noise/parking/suggestion/etc. status: pending→progress→done/rejected.
- 표시 식별은 FK에서 파생(평문 author/unit은 fallback):
residentName = member(memberCode).name,unitLabel = unit(unitCode).name.
3. ERP 코어 연결 (★핵심)
- 민원 작성자 = 입주민(demoSeed member).
boardApi.resolvePost가 memberCode/unitCode로 공유 멤버/유닛 SSOT(buildSeed)에서 실명·라벨 join. → 빌링과 동일 디렉터리. - 교차링크: 민원 상세 →
/service-charge/actual/console/account/{unitCode}(세대 계정 허브). configresidentAccountBase+ unitCode. unitCode는 라우트account/:unitKey와 동일 키. - 불변식: 모든 민원 memberCode/unitCode는 demoSeed에 존재(dangling FK 0 — 테스트 T2). 빌링코어(charges/lines) 무편집(민원은 read-only 참조).
4. 영속 (데모 seam)
complaintStore= fixtures 1회 복제(in-memory).listPosts/getPost는 store에서 read(clone 반환·원본 보호),setStatus/setAssignee는 store mutate → 목록·상세 일관(데모 영속)._resetComplaintStore()— 테스트/리셋용 fixtures 원복(상태 누수 방지).- notice는 무상태 경로 유지(store/resolve 미적용 — 회귀 0).
5. BE 배선 대상 (현재 FE 데모)
- 실 BE: boardApi 메서드를 fetch/persist로 교체.
setStatus/setAssignee/addComment영속,createPost(입주민 제출) 실 발급. - 민원 FK(memberCode/unitCode)는 입주민 디렉터리 PK와 정합 필요(빌링과 단일 멤버 마스터 공유).
- 첨부 업로드/다운로드·알림·SLA·통계 = 미구현.
6. 불변식 테스트
lib/board/__tests__/complaintIntegration.spec.js(T1 resolve·T2 FK유효·T3 영속·T3b 리셋·T4 notice격리·T5 교차링크경로) · components/board/__tests__/BoardComplaintRender.spec.js(실명/담당 컬럼 렌더·notice 격리).