콘텐츠로 이동

attendance_requests 스키마 (근로자 출퇴근 요청)

현장 근로자의 출퇴근 승인 요청을 담는 컬렉션. 근로자가 앱에서 출근/퇴근 버튼을 누르면 여기에 pending 문서가 생성되고, 관리자가 승인/거절하면 문서가 업데이트됩니다. 승인된 출근 요청은 attendance_logs에 새 로그를 만들고, 승인된 퇴근 요청은 기존 출근 로그를 페어링하는 방식입니다.

저장 위치

companies/{company_id}/sites/{site_id}/attendance_requests/{request_id}
  • request_id: Firestore 자동 생성 ID
  • 하나의 근로자는 같은 현장에 동시에 하나의 pending 요청만 가질 수 있습니다 (코드에서 선검사).

상태 흐름

[근로자 요청]     status=pending
      ↓ (관리자 승인)               ↓ (관리자 거절)           ↓ (근로자 취소)
 status=approved                status=rejected          status=rejected
 + attendance_logs 문서 생성/페어링
  • pending: 근로자가 출/퇴근 요청한 상태 (승인 대기 중)
  • approved: 관리자가 승인한 상태. 출근이면 attendance_logs에 새 문서 생성, 퇴근이면 기존 link=False인 로그가 페어링(link=True)됨
  • rejected: 관리자가 거절했거나 요청자(근로자)가 취소한 상태

승인/거절/취소 후에도 문서 자체는 보존됩니다 (감사 이력). 다만 승인된 check_in 요청의 경우 실제 출근 기록은 별도의 attendance_logs 문서에 저장됩니다.

문서 필드

공통 필드

필드 타입 설명
UID string 요청자(근로자) UID
name string 근로자 이름 (당시 스냅샷)
type string "check_in" | "check_out"
company_id string 회사 ID
site_id string 현장 ID
created_at timestamp 요청 생성 시각 (= 버튼 누른 시각)
check_at timestamp 출/퇴근 체크 시각 (created_at과 동일, 승인 시 attendance_logs.check_in_at / check_out_at에 복사됨)
status string "pending" | "approved" | "rejected"
approvalUID string | null 승인/거절 처리자 UID (pending 상태에서는 null)
approval_at timestamp | null 승인/거절 시각 (pending 상태에서는 null)

check_in 타입에서만 저장되는 필드

_site_check_in_request 호출 시 현장 멤버 스냅샷이 함께 복사됩니다. 승인 시 attendance_logs에 그대로 복사되어 당시 직종/직급이 보존됩니다.

필드 타입 설명
member_type string "site" (고정, 회사 출근과 구분)
position string 직급 (당시 스냅샷)
field string 공종 (당시 스냅샷)
labor_supplier string 인력 공급처 (당시 스냅샷)
memo string 메모 (기본 "")

check_out 타입에서만 저장되는 필드

퇴근 요청 문서는 공통 필드만 저장합니다 (멤버 정보는 페어링 대상인 출근 로그에서 이미 보존됨).

관련 컬렉션

생성/수정 경로

  • _site_check_in_request → 새 pending 문서 생성 (type=check_in)
  • _site_check_out_request → 새 pending 문서 생성 (type=check_out)
  • _site_check_in_request_approvalstatus 업데이트(approved/rejected) + check_in 승인 시 attendance_logs 생성
  • _site_check_out_request_approvalstatus 업데이트(approved/rejected) + check_out 승인 시 기존 attendance_logs 페어링
  • _site_attendance_request_cancel → 근로자가 자체 취소 (status=rejected)

예시 문서

출근 요청 (pending)

{
  "UID": "uid_worker",
  "name": "홍길동",
  "type": "check_in",
  "member_type": "site",
  "company_id": "company_abc",
  "site_id": "site_001",
  "created_at": "2026-04-23T08:00:00Z",
  "check_at": "2026-04-23T08:00:00Z",
  "position": "작업반장",
  "field": "철근",
  "labor_supplier": "대한인력",
  "memo": "",
  "status": "pending",
  "approvalUID": null,
  "approval_at": null
}

퇴근 요청 (approved)

{
  "UID": "uid_worker",
  "name": "홍길동",
  "type": "check_out",
  "company_id": "company_abc",
  "site_id": "site_001",
  "created_at": "2026-04-23T17:30:00Z",
  "check_at": "2026-04-23T17:30:00Z",
  "status": "approved",
  "approvalUID": "uid_admin",
  "approval_at": "2026-04-23T17:35:00Z"
}

거절된 요청

{
  "UID": "uid_worker",
  "name": "홍길동",
  "type": "check_in",
  "member_type": "site",
  "company_id": "company_abc",
  "site_id": "site_001",
  "created_at": "2026-04-23T08:00:00Z",
  "check_at": "2026-04-23T08:00:00Z",
  "position": "작업반장",
  "field": "철근",
  "labor_supplier": "대한인력",
  "memo": "",
  "status": "rejected",
  "approvalUID": "uid_admin",
  "approval_at": "2026-04-23T08:10:00Z"
}