Architecture
League Database Quick Start

Source: data_layer/docs/QUICKSTART.md

League Database Quick Start Guide

πŸš€ Get Started in 5 Minutes

Step 1: Set Up Supabase (2 minutes)

  1. Go to https://supabase.com (opens in a new tab) and create a free account
  2. Create a new project
  3. Go to SQL Editor and run:
    # Copy and paste the SQL from:
    database/schemas/supabase_migration_001_prospective_leagues.sql
  4. Go to Settings β†’ API to get your credentials:
    • Project URL β†’ SUPABASE_URL
    • anon public key β†’ SUPABASE_ANON_KEY
    • service_role key β†’ SUPABASE_SERVICE_KEY

Step 2: Configure Environment Variables (1 minute)

Add to your .env file:

# Supabase
SUPABASE_URL=https://your-project.supabase.co
SUPABASE_ANON_KEY=your-anon-key-here
SUPABASE_SERVICE_KEY=your-service-key-here
 
# Frontend
NEXT_PUBLIC_SUPABASE_URL=https://your-project.supabase.co
NEXT_PUBLIC_SUPABASE_ANON_KEY=your-anon-key-here
NEXT_PUBLIC_BACKEND_URL=http://localhost:8000
 
# Firebase (optional for now)
FIREBASE_SERVICE_ACCOUNT_PATH=/path/to/service-account.json

Step 3: Test the Backend (1 minute)

cd apps/backend
python -m services.unified_league_database

You should see:

βœ… Supabase adapter initialized (MOCK MODE)
βœ… Firebase adapter initialized (MOCK MODE)
βœ… Initialized Unified League Database

=== Test 1: Scraped League ===
βœ… Mock upserted league: International Basketball League (ID: 1)
...

Step 4: Test the Frontend (1 minute)

cd clients/frontend-001-nextjs-ui-grok-chat-polymarket-micro-betting-altsport-opportunities
npm install
npm run dev

Navigate to the league query interface and try:

  • "Show me all basketball leagues"
  • "Find high-potential soccer leagues"

🎯 Common Use Cases

Use Case 1: Add a Scraped League

from apps.backend.services.unified_league_database import upsert_scraped_league
 
result = await upsert_scraped_league({
    "name": "New Basketball League",
    "sport_name": "Basketball",
    "sport_tier": "TIER2",
    "source_url": "https://example.com/nbl",
    "opportunity_score": 75
})
 
print(result)
# {
#   "supabase": {"success": True, "id": "..."},
#   "firebase": {"status": "skipped"}
# }

What happens:

  • βœ… Added to Supabase with source_type: 'web_scrape' and verification_status: 'unverified'
  • ❌ NOT added to Firebase (only verified leagues go there)

Use Case 2: Add a Verified League (Both Databases)

from apps.backend.services.unified_league_database import upsert_verified_league
 
result = await upsert_verified_league(
    {
        "name": "Premier Volleyball League",
        "sport_name": "Volleyball",
        "contact_info": {"email": "info@pvl.com"}
    },
    user_context={"email": "partner@altsportsdata.com"}
)
 
print(result)
# {
#   "supabase": {"success": True, "id": "..."},
#   "firebase": {"success": True, "id": "premier_volleyball_league"}
# }

What happens:

  • βœ… Added to Supabase with source_type: 'human_verified' and verification_status: 'human_verified'
  • βœ… ALSO added to Firebase (human-verified leagues get promoted automatically)

Use Case 3: Query from Frontend

import { getLeagueDatabaseClient } from '@/lib/league-database-client'
 
const client = getLeagueDatabaseClient()
 
// Natural language query
const result = await client.query(
  "Show me high-potential basketball leagues we haven't contacted"
)
 
console.log(result.leagues)
// [
//   {
//     name: "International Basketball League",
//     sport_name: "Basketball",
//     source_type: "web_scrape",
//     verification_status: "unverified",
//     opportunity_score: 75
//   }
// ]

Use Case 4: Promote Scraped β†’ Verified

from apps.backend.services.unified_league_database import UnifiedLeagueDatabase
 
db = UnifiedLeagueDatabase()
 
# After human contact confirms legitimacy
result = await db.promote_to_firebase(
    supabase_league_id="abc-123",
    user_context={"email": "sales@altsportsdata.com"}
)
 
print(result)
# {
#   "success": True,
#   "league_id": "abc-123",
#   "firebase_id": "international_basketball_league"
# }

What happens:

  1. Updates Supabase: verification_status β†’ 'human_verified', promoted_to_firebase β†’ true
  2. Adds to Firebase: Creates document in verified_leagues collection

πŸ” Query Examples

Frontend (TypeScript)

const client = getLeagueDatabaseClient()
 
// 1. Get all basketball leagues
const basketball = await client.executeQuery({ sport: "Basketball" })
 
// 2. Get high-potential opportunities (score > 80)
const highPotential = await client.getHighPotentialOpportunities(80)
 
// 3. Get verified partnerships only
const verified = await client.getVerifiedPartnerships()
 
// 4. Get leagues needing contact (score > 70, unverified)
const needsContact = await client.getLeaguesNeedingContact(70)
 
// 5. Search by name
const search = await client.searchByName("Premier")
 
// 6. Get analytics
const analytics = await client.getAnalytics()
console.log(`Total: ${analytics.total_leagues}`)
console.log(`Verified: ${analytics.verified_count}`)
console.log(`Scraped: ${analytics.scraped_count}`)

Backend (Python)

from apps.backend.services.unified_league_database import (
    query_all_leagues,
    query_verified_leagues_only,
    query_scraped_leagues_only
)
 
# Get all leagues
all_leagues = await query_all_leagues()
 
# Get only verified
verified = await query_verified_leagues_only()
 
# Get only scraped
scraped = await query_scraped_leagues_only()
 
# Filter by sport
basketball = await query_all_leagues({"sport_name": "Basketball"})

πŸ“Š Understanding the Data Flow

β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”
β”‚                WEB SCRAPING                      β”‚
β”‚            (Discovers Leagues)                   β”‚
β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜
                  β”‚
                  ↓
         β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”
         β”‚ Supabase Database  β”‚ ← ALL LEAGUES
         β”‚  (prospective_     β”‚   β€’ Scraped (unverified)
         β”‚   leagues)         β”‚   β€’ Verified (human contact)
         β””β”€β”€β”€β”€β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜
                  β”‚
        β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”΄β”€β”€β”€β”€β”€β”€β”€β”€β”€β”
        β”‚                   β”‚
        ↓                   ↓
  UNVERIFIED          VERIFIED
  (Scraped)           (Human Contact)
        β”‚                   β”‚
        β”‚                   ↓
        β”‚          β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”
        β”‚          β”‚ Firebase Database  β”‚
        β”‚          β”‚  (verified_        β”‚
        β”‚          β”‚   leagues)         β”‚
        └───────────                    β”‚
                   β”‚ ONLY VERIFIED      β”‚
                   β”‚ PARTNERSHIPS       β”‚
                   β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜

🎨 Frontend Integration

Add the query interface to any page:

import { LeagueQueryInterface } from '@/components/league-query-interface'
 
export default function LeagueDashboard() {
  return (
    <div className="container mx-auto p-6">
      <h1 className="text-3xl font-bold mb-6">League Database</h1>
      <LeagueQueryInterface />
    </div>
  )
}

πŸ” Access Control

Supabase (Public + Authenticated)

  • βœ… Public read access (for discovery)
  • βœ… Authenticated write (for data entry)
  • βœ… Service role full access (for backend)

Firebase (Restricted)

  • ❌ No public access
  • βœ… Authenticated users only
  • βœ… League owners can edit their own data
  • βœ… Internal team has full access

πŸ“ˆ Monitoring

Check database health:

from apps.backend.services.unified_league_database import UnifiedLeagueDatabase
 
db = UnifiedLeagueDatabase()
analytics = await db.get_league_analytics()
 
print(f"Supabase: {analytics['supabase']['total_leagues']} leagues")
print(f"Firebase: {analytics['firebase']['total_leagues']} verified")
print(f"Promotion rate: {analytics['promotion_rate']:.1%}")

πŸ› Troubleshooting

"Supabase client not initialized"

  • Check .env file has correct Supabase credentials
  • Verify project URL and keys from Supabase dashboard

"Firebase adapter in mock mode"

  • Normal during development
  • Add FIREBASE_SERVICE_ACCOUNT_PATH to use real Firebase

"Query returns no results"

  • Run the sample data INSERT from the migration SQL
  • Or add leagues manually using the backend service

Frontend can't connect

  • Check NEXT_PUBLIC_SUPABASE_URL and NEXT_PUBLIC_SUPABASE_ANON_KEY
  • Verify Supabase project is running
  • Check CORS settings in Supabase dashboard

πŸŽ“ Next Steps

  1. Build a web scraper to populate Supabase with leagues
  2. Create an onboarding portal for league owners to register
  3. Add email integration to auto-classify incoming league inquiries
  4. Build analytics dashboard to track promotion rates
  5. Add Neo4j integration for relationship mapping (optional)

πŸ“š Further Reading

Platform

Documentation

Community

Support

partnership@altsportsdata.comdev@altsportsleagues.ai

2025 Β© AltSportsLeagues.ai. Powered by AI-driven sports business intelligence.

πŸ€– AI-Enhancedβ€’πŸ“Š Data-Drivenβ€’βš‘ Real-Time