rules_version = '2'; // TriplePick Firestore 보안 규칙 // 모델: 공개 데이터(경기/AI예측/집계)는 읽기 허용, 모든 쓰기는 서버(Admin SDK·Cloud Functions)만. // 유저 예측/구독/참여는 클라이언트 직접 접근 금지 → 콜러블 함수로만 처리(검증·집계·PII 보호). service cloud.firestore { match /databases/{database}/documents { // ---- 공개 읽기 전용 (쓰기는 Admin SDK가 규칙 우회) ---- match /matches/{matchId} { allow read: if true; allow write: if false; } match /ai_predictions/{docId} { allow read: if true; allow write: if false; } match /crowd_stats/{matchId} { allow read: if true; // 군중 분포(퍼센트, PII 없음) allow write: if false; // submitPrediction 함수가 트랜잭션으로 증분 } // ---- 비공개: 함수/Admin 전용 (클라이언트 직접 접근 전면 금지) ---- match /user_predictions/{docId} { allow read, write: if false; // 제출/조회는 콜러블 함수로만, 이메일 등 PII 보호 } match /notify_subscriptions/{docId} { allow read, write: if false; // 결과 알림 구독 (Resend 발송용) } match /event_participation/{deviceId} { allow read, write: if false; // R2 — 상금 챌린지 누적/자격 } // 그 외 전부 차단 match /{document=**} { allow read, write: if false; } } } // 참고: 클라이언트 직접 쓰기 방식을 택할 경우(함수 없이), user_predictions에 // create 검증 규칙(opens_at ≤ now < lock_at[=킥오프 정각], outcome ∈ {TEAM_A_WIN,DRAW,TEAM_B_WIN}, // score 0~9 정수, nickname 2~16자, docId == matchId+"_"+deviceId)을 넣어야 한다. // 단 crowd_stats 원자적 증분과 PII 보호 때문에 콜러블 함수 방식을 권장한다(docs/BACKEND.md).