| |
|
|
| |
| ALTER TABLE matches ADD COLUMN IF NOT EXISTS competition TEXT; |
| ALTER TABLE matches ADD COLUMN IF NOT EXISTS created_by UUID REFERENCES users(id) ON DELETE SET NULL; |
|
|
| |
| CREATE TABLE IF NOT EXISTS match_stat_uploads ( |
| id UUID PRIMARY KEY DEFAULT uuid_generate_v4(), |
| match_id UUID NOT NULL REFERENCES matches(id) ON DELETE CASCADE, |
| organization_id UUID NOT NULL REFERENCES organizations(id) ON DELETE CASCADE, |
| uploaded_by UUID NOT NULL REFERENCES users(id) ON DELETE SET NULL, |
| storage_path TEXT NOT NULL, |
| file_type TEXT CHECK (file_type IN ('image', 'pdf')), |
| extract_status TEXT DEFAULT 'queued' CHECK (extract_status IN ('queued', 'extracting', 'needs_review', 'confirmed', 'failed')), |
| extracted_json JSONB, |
| confidence NUMERIC, |
| created_at TIMESTAMPTZ DEFAULT NOW(), |
| updated_at TIMESTAMPTZ DEFAULT NOW() |
| ); |
|
|
| CREATE INDEX IF NOT EXISTS idx_match_stat_uploads_match ON match_stat_uploads(match_id); |
| CREATE INDEX IF NOT EXISTS idx_match_stat_uploads_org ON match_stat_uploads(organization_id); |
|
|
| |
| CREATE TABLE IF NOT EXISTS match_player_stats ( |
| id UUID PRIMARY KEY DEFAULT uuid_generate_v4(), |
| match_id UUID NOT NULL REFERENCES matches(id) ON DELETE CASCADE, |
| organization_id UUID NOT NULL REFERENCES organizations(id) ON DELETE CASCADE, |
| player_profile_id UUID NOT NULL REFERENCES players(id) ON DELETE CASCADE, |
| source TEXT DEFAULT 'official_upload' CHECK (source IN ('official_upload', 'manual')), |
| |
| mins TEXT, |
| pts INTEGER DEFAULT 0, |
| fgm INTEGER DEFAULT 0, |
| fga INTEGER DEFAULT 0, |
| tp_m INTEGER DEFAULT 0, |
| tp_a INTEGER DEFAULT 0, |
| thp_m INTEGER DEFAULT 0, |
| thp_a INTEGER DEFAULT 0, |
| ft_m INTEGER DEFAULT 0, |
| ft_a INTEGER DEFAULT 0, |
| off_reb INTEGER DEFAULT 0, |
| def_reb INTEGER DEFAULT 0, |
| reb INTEGER DEFAULT 0, |
| ast INTEGER DEFAULT 0, |
| to_cnt INTEGER DEFAULT 0, |
| stl INTEGER DEFAULT 0, |
| blk INTEGER DEFAULT 0, |
| pf INTEGER DEFAULT 0, |
| plus_minus INTEGER, |
| index_rating INTEGER, |
| row_confidence NUMERIC, |
| created_at TIMESTAMPTZ DEFAULT NOW(), |
| updated_at TIMESTAMPTZ DEFAULT NOW(), |
| UNIQUE(match_id, player_profile_id) |
| ); |
|
|
| CREATE INDEX IF NOT EXISTS idx_match_player_stats_match ON match_player_stats(match_id); |
| CREATE INDEX IF NOT EXISTS idx_match_player_stats_player ON match_player_stats(player_profile_id); |
|
|
| |
| ALTER TABLE match_stat_uploads ENABLE ROW LEVEL SECURITY; |
| ALTER TABLE match_player_stats ENABLE ROW LEVEL SECURITY; |
|
|
| |
| |
| CREATE POLICY "Users can view org match stat uploads" ON match_stat_uploads |
| FOR SELECT USING ( |
| organization_id IN ( |
| SELECT id FROM organizations WHERE owner_id::text = (SELECT auth.uid())::text |
| UNION |
| SELECT organization_id FROM users WHERE id::text = (SELECT auth.uid())::text |
| UNION |
| SELECT organization_id FROM players WHERE user_id::text = (SELECT auth.uid())::text |
| ) |
| ); |
|
|
| |
| CREATE POLICY "Owners and Staff can manage match stat uploads" ON match_stat_uploads |
| FOR ALL WITH CHECK ( |
| organization_id IN ( |
| SELECT id FROM organizations WHERE owner_id::text = (SELECT auth.uid())::text |
| UNION |
| SELECT organization_id FROM users WHERE id::text = (SELECT auth.uid())::text AND (account_type = 'team' OR account_type = 'coach') |
| ) |
| ); |
|
|
| |
| |
| CREATE POLICY "Users can view match player stats" ON match_player_stats |
| FOR SELECT USING ( |
| organization_id IN ( |
| SELECT id FROM organizations WHERE owner_id::text = (SELECT auth.uid())::text |
| UNION |
| SELECT organization_id FROM users WHERE id::text = (SELECT auth.uid())::text |
| UNION |
| SELECT organization_id FROM players WHERE user_id::text = (SELECT auth.uid())::text |
| ) |
| OR player_profile_id IN ( |
| SELECT id FROM players WHERE user_id::text = (SELECT auth.uid())::text |
| ) |
| ); |
|
|
| |
| CREATE POLICY "Owners and Staff can manage match player stats" ON match_player_stats |
| FOR ALL WITH CHECK ( |
| organization_id IN ( |
| SELECT id FROM organizations WHERE owner_id::text = (SELECT auth.uid())::text |
| UNION |
| SELECT organization_id FROM users WHERE id::text = (SELECT auth.uid())::text AND (account_type = 'team' OR account_type = 'coach') |
| ) |
| ); |
|
|
| |
| CREATE TRIGGER update_match_stat_uploads_updated_at |
| BEFORE UPDATE ON match_stat_uploads |
| FOR EACH ROW EXECUTE FUNCTION update_updated_at(); |
|
|
| CREATE TRIGGER update_match_player_stats_updated_at |
| BEFORE UPDATE ON match_player_stats |
| FOR EACH ROW EXECUTE FUNCTION update_updated_at(); |
|
|
| |
| NOTIFY pgrst, 'reload schema'; |
|
|