Organization
docs/domain/organization.md
Organization
개요
조직(Organization) 생성, 멤버 관리, 물류(ARGO) 연동을 관리하는 도메인. Seller가 Shop을 운영하기 위한 상위 단위이며, 멤버 초대/역할 관리와 ARGO 물류 시스템 통합을 담당한다.
서버 패키지: com.makitt.core.domain.organization
DynamoDB Entity
Organization
Organization의 메타데이터 엔티티.
키 구조:
| 키 | 패턴 | 예시 |
|---|---|---|
| PK | ORGANIZATION#{organizationId} | ORGANIZATION#abc123 |
| SK | METADATA | METADATA |
필드:
| 필드 | DynamoDB Attribute | 타입 | 필수 | 설명 |
|---|---|---|---|---|
| pk | PK | String | O | Partition Key |
| sk | SK | String | O | Sort Key |
| entityType | entity_type | String | O | "ORGANIZATION" 고정 |
| organizationId | organization_id | String | O | 조직 고유 ID (UUID) |
| name | name | String | O | 조직명 |
| description | description | String | X | 조직 설명 |
| logoUrl | logo_url | String | X | 로고 URL |
| ownerId | owner_id | String | O | 생성자 User ID |
| integrationInfo | integration_info | IntegrationInfo | O | ARGO 연동 정보 (nested) |
| businessInfo | business_info | BusinessInfo | X | 사업자 정보 (nested) |
| createdAt | created_at | Instant | O | 생성 시각 |
| updatedAt | updated_at | Instant | O | 수정 시각 |
Factory Methods:
Organization.create(organizationId, name, description, ownerId)— 조직 생성, integrationInfo 초기화 (NONE)
Business Methods:
updateInfo(name, description, logoUrl)— 기본 정보 수정activateLogistics(vendorId, argoLoginId, businessInfo)— ARGO 물류 활성화hasActiveLogistics()— ARGO 연동 활성화 여부suspendLogistics()— ARGO 일시 중지deactivateLogistics()— ARGO 연동 해제 (모든 연동 데이터 초기화)
Nested Objects
IntegrationInfo
ARGO 물류 시스템 연동 상태 정보.
| 필드 | DynamoDB Attribute | 타입 | 설명 |
|---|---|---|---|
| vendorId | vendor_id | Long | ARGO Vendor ID |
| vendorStatus | vendor_status | VendorStatus | 연동 상태 |
| argoLoginId | argo_login_id | String | ARGO 공유 로그인 ID (예: org_xxx@makitt.argo) |
Methods:
IntegrationInfo.initial()— vendorStatus=NONE 으로 초기화activateArgo(vendorId, argoLoginId)— 연동 활성화 (status=ACTIVE)hasActiveArgo()— status==ACTIVE && vendorId!=nullsuspendArgo()— 일시 중지 (status=SUSPENDED)deactivateArgo()— 연동 해제 (모든 필드 초기화, status=NONE)
BusinessInfo
사업자 등록 정보. 물류 연동 시 필요.
| 필드 | DynamoDB Attribute | 타입 | 설명 |
|---|---|---|---|
| businessNumber | business_number | String | 사업자등록번호 |
| businessName | business_name | String | 상호명 |
| representative | representative | String | 대표자명 |
| address | address | String | 사업장 주소 |
| addressDetail | address_detail | String | 상세주소 |
| postalCode | postal_code | String | 우편번호 |
| managerName | manager_name | String | 담당자명 |
| managerPhone | manager_phone | String | 담당자 연락처 |
| managerEmail | manager_email | String | 담당자 이메일 |
OrganizationMember
조직-사용자 간 멤버십 엔티티. 역할 기반 접근 제어 및 초대 관리.
키 구조:
| 키 | 패턴 | 예시 |
|---|---|---|
| PK | ORGANIZATION#{organizationId} | ORGANIZATION#abc123 |
| SK | MEMBER#{userId} | MEMBER#user456 |
필드:
| 필드 | DynamoDB Attribute | 타입 | 필수 | 설명 |
|---|---|---|---|---|
| pk | PK | String | O | Partition Key |
| sk | SK | String | O | Sort Key |
| entityType | entity_type | String | O | "ORGANIZATION_MEMBER" 고정 |
| organizationId | organization_id | String | O | 조직 ID |
| userId | user_id | String | O | 사용자 ID |
| role | role | OrganizationRole | O | 멤버 역할 |
| status | status | MemberStatus | O | 멤버 상태 |
| invitedBy | invited_by | String | X | 초대한 사용자 ID |
| invitedAt | invited_at | Instant | X | 초대 시각 |
| joinedAt | joined_at | Instant | X | 참여 시각 |
| createdAt | created_at | Instant | O | 생성 시각 |
| updatedAt | updated_at | Instant | O | 수정 시각 |
Factory Methods:
createOwner(organizationId, userId)— OWNER 역할, ACTIVE 상태createInvited(organizationId, userId, role, invitedBy)— INVITED 상태
Business Methods:
acceptInvitation()— INVITED → ACTIVE 전환, joinedAt 설정updateRole(newRole)— 역할 변경deactivate()— INACTIVE 전환
ArgoVendorMapping
ARGO vendorId → MAKITT organizationId 역방향 매핑. Kafka Consumer에서 ARGO 이벤트를 MAKITT 조직으로 라우팅할 때 사용.
키 구조:
| 키 | 패턴 | 예시 |
|---|---|---|
| PK | ARGO_VENDOR#{vendorId} | ARGO_VENDOR#12345 |
| SK | MAPPING | MAPPING |
필드:
| 필드 | DynamoDB Attribute | 타입 | 필수 | 설명 |
|---|---|---|---|---|
| vendorId | vendor_id | Long | O | ARGO Vendor ID |
| organizationId | organization_id | String | O | MAKITT 조직 ID |
| createdAt | created_at | Instant | O | 생성 시각 |
Enums
OrganizationRole
멤버 역할. ordinal 기반 권한 계층 (OWNER > ADMIN > MEMBER).
| 값 | 설명 |
|---|---|
OWNER | 조직 소유자 (모든 권한) |
ADMIN | 관리자 (멤버/Shop 관리) |
MEMBER | 일반 멤버 (제한된 접근) |
MemberStatus
멤버 상태.
| 값 | 설명 |
|---|---|
ACTIVE | 활성 멤버 |
INVITED | 초대됨 (수락 대기) |
INACTIVE | 비활성 (탈퇴/제거) |
VendorStatus
ARGO 물류 연동 상태.
| 값 | 설명 |
|---|---|
NONE | 물류 서비스 미연동 |
PENDING | 물류 서비스 연동 중 |
ACTIVE | 물류 서비스 활성화 |
SUSPENDED | 물류 서비스 일시 중지 |
VendorType
사업자 유형. 물류 활성화 시 사용.
| 값 | 설명 | businessInfo 필수 |
|---|---|---|
INDIVIDUAL | 개인 | X |
SOLE_PROPRIETOR | 개인사업자 | O |
CORPORATION | 법인사업자 | O |
GSI (Global Secondary Index)
| GSI | PK 패턴 | SK 패턴 | 용도 |
|---|---|---|---|
| EntityLookupIndex | USER#{userId} | ORGANIZATION#{organizationId} | 사용자별 조직 목록 조회 |
OrganizationMember의
gsi1_pk,gsi1_sk필드로 구성. KEYS_ONLY 프로젝션 후 BatchGetItem으로 전체 데이터 조회.
Key Builder
OrganizationKey
클래스: com.makitt.core.common.dynamodb.key.OrganizationKey
OrganizationKey.pk(organizationId) → "ORGANIZATION#{organizationId}"
OrganizationKey.sk() → "METADATA"
OrganizationKey.extractOrganizationId(pk) → organizationId (PK에서 추출)
OrganizationMemberKey
클래스: com.makitt.core.common.dynamodb.key.OrganizationMemberKey
// Primary Keys
OrganizationMemberKey.pk(organizationId) → "ORGANIZATION#{organizationId}"
OrganizationMemberKey.sk(userId) → "MEMBER#{userId}"
OrganizationMemberKey.skPrefix() → "MEMBER#" (begins-with 쿼리용)
// GSI1: EntityLookupIndex
OrganizationMemberKey.gsi1Pk(userId) → "USER#{userId}"
OrganizationMemberKey.gsi1Sk(organizationId) → "ORGANIZATION#{organizationId}"
OrganizationMemberKey.gsi1SkPrefix() → "ORGANIZATION#"
// Helper
OrganizationMemberKey.extractOrganizationId(pk) → organizationId
OrganizationMemberKey.extractUserId(sk) → userId
관련 도메인
| 도메인 | 관계 | 설명 |
|---|---|---|
| User | N:M (via OrganizationMember) | 사용자는 여러 조직에 소속, 조직은 여러 멤버 보유 |
| Shop | 1:N | 조직 하위에 여러 Shop 존재 (Shop.organizationId) |
| UserOnboarding | trigger | 조직 생성/물류 연동 시 온보딩 sub-step 완료 트리거 |
온보딩 연동
UserOnboardingStep.ORGANIZATION_COMPLETION의 sub-step:
| Sub-Step | 필수 | 트리거 시점 |
|---|---|---|
ORG_INFO_SET | O | 조직 생성 시 (OrganizationApplication.createOrganization) |
BUSINESS_INFO_SET | O | 물류 활성화 시 (LogisticsApplication.activateLogistics) |
LOGISTICS_CONNECTED | X | 물류 활성화 시 (LogisticsApplication.activateLogistics) |
필수 sub-step(ORG_INFO_SET + BUSINESS_INFO_SET) 모두 완료 시 ORGANIZATION_COMPLETION 자동 완료. 이 단계는
FIRST_SHOP_CREATED의 선행 조건.