300 lines
11 KiB
Python
300 lines
11 KiB
Python
"""
|
|
Comprehensive Demo Data Seeder for Elmeg
|
|
Creates 12 diverse user personas and populates with Goose data
|
|
"""
|
|
import sys
|
|
from datetime import datetime, timedelta
|
|
from sqlmodel import Session, select
|
|
from passlib.context import CryptContext
|
|
from database import engine
|
|
from models import (
|
|
User, Vertical, Venue, Tour, Show, Song, Performance, Artist,
|
|
Attendance, Comment, Rating, Review, Group, GroupMember, GroupPost,
|
|
PerformanceNickname, UserPreferences, Badge, UserBadge, Tag, EntityTag
|
|
)
|
|
|
|
pwd_context = CryptContext(schemes=["bcrypt"], deprecated="auto")
|
|
|
|
# User Personas
|
|
USERS = [
|
|
{"email": "archivist@demo.com", "username": "TheArchivist", "role": "user", "wiki_mode": True, "bio": "Pure data, no noise"},
|
|
{"email": "statnerd@demo.com", "username": "StatNerd420", "role": "user", "wiki_mode": False, "bio": "Gap charts are life"},
|
|
{"email": "reviewer@demo.com", "username": "CriticalListener", "role": "user", "wiki_mode": False, "bio": "Every show deserves analysis"},
|
|
{"email": "casual@demo.com", "username": "CasualFan", "role": "user", "wiki_mode": False, "bio": "Just here for the vibes"},
|
|
{"email": "groupleader@demo.com", "username": "NortheastHonkers", "role": "user", "wiki_mode": False, "bio": "NYC/Boston crew organizer"},
|
|
{"email": "mod@demo.com", "username": "ModGoose", "role": "moderator", "wiki_mode": False, "bio": "Keeping it clean"},
|
|
{"email": "admin@demo.com", "username": "AdminBird", "role": "admin", "wiki_mode": False, "bio": "Platform steward"},
|
|
{"email": "newbie@demo.com", "username": "NewToGoose", "role": "user", "wiki_mode": False, "bio": "Just discovered them!"},
|
|
{"email": "taper@demo.com", "username": "TaperTom", "role": "user", "wiki_mode": False, "bio": "Recording quality matters"},
|
|
{"email": "tourfollower@demo.com", "username": "RoadWarrior", "role": "user", "wiki_mode": False, "bio": "50+ shows and counting"},
|
|
{"email": "lurker@demo.com", "username": "SilentHonker", "role": "user", "wiki_mode": True, "bio": "Observer mode"},
|
|
{"email": "hype@demo.com", "username": "HypeGoose", "role": "user", "wiki_mode": False, "bio": "EVERYTHING IS FIRE 🔥"},
|
|
]
|
|
|
|
def create_users(session: Session):
|
|
"""Create 12 diverse user personas"""
|
|
print("Creating users...")
|
|
users = []
|
|
for user_data in USERS:
|
|
user = User(
|
|
email=user_data["email"],
|
|
hashed_password=pwd_context.hash("demo123"),
|
|
is_active=True,
|
|
is_superuser=(user_data["role"] == "admin"),
|
|
role=user_data["role"]
|
|
)
|
|
session.add(user)
|
|
session.commit()
|
|
session.refresh(user)
|
|
|
|
# Set preferences
|
|
prefs = UserPreferences(
|
|
user_id=user.id,
|
|
wiki_mode=user_data["wiki_mode"],
|
|
show_ratings=not user_data["wiki_mode"],
|
|
show_comments=not user_data["wiki_mode"]
|
|
)
|
|
session.add(prefs)
|
|
|
|
users.append(user)
|
|
|
|
session.commit()
|
|
print(f"✓ Created {len(users)} users")
|
|
return users
|
|
|
|
def create_vertical(session: Session):
|
|
"""Create Goose vertical"""
|
|
print("Creating Goose vertical...")
|
|
vertical = Vertical(
|
|
name="Goose",
|
|
slug="goose",
|
|
description="Goose is a jam band from Connecticut"
|
|
)
|
|
session.add(vertical)
|
|
session.commit()
|
|
session.refresh(vertical)
|
|
print("✓ Created Goose vertical")
|
|
return vertical
|
|
|
|
def create_sample_data(session: Session, vertical: Vertical, users: list):
|
|
"""Create comprehensive sample data"""
|
|
print("Creating sample venues, tours, and shows...")
|
|
|
|
# Venues
|
|
venues = [
|
|
Venue(name="Red Rocks Amphitheatre", city="Morrison", state="CO", country="USA", capacity=9525),
|
|
Venue(name="The Capitol Theatre", city="Port Chester", state="NY", country="USA", capacity=1800),
|
|
Venue(name="Radio City Music Hall", city="New York", state="NY", country="USA", capacity=6015),
|
|
Venue(name="The Gorge Amphitheatre", city="George", state="WA", country="USA", capacity=27500),
|
|
Venue(name="Brooklyn Bowl", city="Brooklyn", state="NY", country="USA", capacity=600),
|
|
]
|
|
for v in venues:
|
|
session.add(v)
|
|
session.commit()
|
|
|
|
# Tours
|
|
tours = [
|
|
Tour(name="Fall 2023 Tour", start_date=datetime(2023, 10, 1), end_date=datetime(2023, 11, 15)),
|
|
Tour(name="Summer 2024 Tour", start_date=datetime(2024, 6, 1), end_date=datetime(2024, 8, 31)),
|
|
]
|
|
for t in tours:
|
|
session.add(t)
|
|
session.commit()
|
|
|
|
# Songs
|
|
songs = [
|
|
Song(title="Hungersite", vertical_id=vertical.id, original_artist=None),
|
|
Song(title="Arcadia", vertical_id=vertical.id, original_artist=None),
|
|
Song(title="Hot Tea", vertical_id=vertical.id, original_artist=None),
|
|
Song(title="Tumble", vertical_id=vertical.id, original_artist=None),
|
|
Song(title="Seekers on the Ridge", vertical_id=vertical.id, original_artist=None),
|
|
Song(title="Arrow", vertical_id=vertical.id, original_artist=None),
|
|
Song(title="Empress of Organos", vertical_id=vertical.id, original_artist=None),
|
|
Song(title="Rockdale", vertical_id=vertical.id, original_artist=None),
|
|
]
|
|
for s in songs:
|
|
session.add(s)
|
|
session.commit()
|
|
|
|
# Shows
|
|
shows = []
|
|
for i in range(10):
|
|
show = Show(
|
|
date=datetime(2024, 1, 1) + timedelta(days=i*30),
|
|
vertical_id=vertical.id,
|
|
venue_id=venues[i % len(venues)].id,
|
|
tour_id=tours[i % len(tours)].id if i < 8 else None,
|
|
notes=f"Night {i+1} of tour" if i < 5 else None
|
|
)
|
|
session.add(show)
|
|
shows.append(show)
|
|
session.commit()
|
|
|
|
# Performances (setlists)
|
|
for show in shows:
|
|
for pos, song in enumerate(songs[:5], 1):
|
|
perf = Performance(
|
|
show_id=show.id,
|
|
song_id=song.id,
|
|
position=pos,
|
|
set_name="Set 1" if pos <= 3 else "Set 2",
|
|
segue=(pos % 2 == 0),
|
|
notes="Extended jam" if pos == 3 else None
|
|
)
|
|
session.add(perf)
|
|
session.commit()
|
|
|
|
print(f"✓ Created {len(venues)} venues, {len(tours)} tours, {len(songs)} songs, {len(shows)} shows")
|
|
return venues, tours, songs, shows
|
|
|
|
def seed_user_activity(session: Session, users: list, shows: list, songs: list):
|
|
"""Seed diverse user activity based on personas"""
|
|
print("Seeding user activity...")
|
|
|
|
# Archivist - No social activity
|
|
# StatNerd - Attendance tracking
|
|
stat_nerd = users[1]
|
|
for show in shows[:8]:
|
|
att = Attendance(user_id=stat_nerd.id, show_id=show.id, notes="Stats logged")
|
|
session.add(att)
|
|
|
|
# Reviewer - Detailed reviews
|
|
reviewer = users[2]
|
|
for show in shows[:3]:
|
|
review = Review(
|
|
user_id=reviewer.id,
|
|
show_id=show.id,
|
|
blurb="A masterclass in improvisation",
|
|
content="The Hungersite opener set the tone perfectly. The segue into Arcadia was seamless...",
|
|
score=9,
|
|
created_at=show.date + timedelta(days=1)
|
|
)
|
|
session.add(review)
|
|
|
|
# Casual Fan - Occasional comments
|
|
casual = users[3]
|
|
perfs = session.exec(select(Performance).limit(5)).all()
|
|
for perf in perfs[:2]:
|
|
comment = Comment(
|
|
user_id=casual.id,
|
|
show_id=perf.show_id,
|
|
content="This was so good live!",
|
|
created_at=datetime.utcnow() - timedelta(days=10)
|
|
)
|
|
session.add(comment)
|
|
|
|
# Group Leader - Creates group
|
|
leader = users[4]
|
|
group = Group(
|
|
name="Northeast Honkers",
|
|
description="Goose fans from NYC and Boston area",
|
|
privacy="public",
|
|
created_by=leader.id
|
|
)
|
|
session.add(group)
|
|
session.commit()
|
|
|
|
# Add members
|
|
for user in users[:6]:
|
|
member = GroupMember(group_id=group.id, user_id=user.id, role="admin" if user.id == leader.id else "member")
|
|
session.add(member)
|
|
|
|
# Group posts
|
|
post = GroupPost(
|
|
group_id=group.id,
|
|
user_id=leader.id,
|
|
content="Who's going to the Capitol show next month?"
|
|
)
|
|
session.add(post)
|
|
|
|
# Taper - Notes on recording quality
|
|
taper = users[8]
|
|
for show in shows[:4]:
|
|
comment = Comment(
|
|
user_id=taper.id,
|
|
show_id=show.id,
|
|
content="AUD recording available - great soundboard quality",
|
|
created_at=show.date + timedelta(hours=12)
|
|
)
|
|
session.add(comment)
|
|
|
|
# Road Warrior - Massive attendance
|
|
warrior = users[9]
|
|
for show in shows:
|
|
att = Attendance(user_id=warrior.id, show_id=show.id, notes="On the road!")
|
|
session.add(att)
|
|
|
|
# Hype Person - Rates everything 10/10
|
|
hype = users[11]
|
|
for show in shows[:5]:
|
|
rating = Rating(user_id=hype.id, show_id=show.id, score=10)
|
|
review = Review(
|
|
user_id=hype.id,
|
|
show_id=show.id,
|
|
blurb="ABSOLUTE HEATER 🔥🔥🔥",
|
|
content="This show SLAPPED. Every song was FIRE. Best show ever!!!",
|
|
score=10,
|
|
created_at=show.date + timedelta(hours=6)
|
|
)
|
|
session.add(rating)
|
|
session.add(review)
|
|
|
|
# Performance Nicknames
|
|
mod = users[5]
|
|
perfs = session.exec(select(Performance).limit(3)).all()
|
|
for perf in perfs:
|
|
nick = PerformanceNickname(
|
|
performance_id=perf.id,
|
|
nickname="Red Rocks Hungersite" if perf.position == 1 else "Epic Jam",
|
|
description="Legendary version",
|
|
status="approved",
|
|
suggested_by=mod.id
|
|
)
|
|
session.add(nick)
|
|
|
|
session.commit()
|
|
print("✓ Seeded comprehensive user activity")
|
|
|
|
def main():
|
|
print("=" * 60)
|
|
print("ELMEG DEMO DATA SEEDER")
|
|
print("=" * 60)
|
|
|
|
with Session(engine) as session:
|
|
# Check if already seeded
|
|
existing = session.exec(select(User)).first()
|
|
if existing:
|
|
print("⚠ Database already contains data!")
|
|
response = input("Clear and reseed? (yes/no): ")
|
|
if response.lower() != "yes":
|
|
print("Aborted.")
|
|
return
|
|
|
|
# Clear all data (in reverse dependency order)
|
|
from sqlalchemy import text
|
|
for model in [GroupPost, GroupMember, Group, UserBadge, Badge,
|
|
PerformanceNickname, EntityTag, Tag, Attendance,
|
|
Comment, Rating, Review, Performance, Show, Tour,
|
|
Song, Venue, Artist, UserPreferences, User, Vertical]:
|
|
session.exec(text(f"DELETE FROM {model.__tablename__}"))
|
|
session.commit()
|
|
print("✓ Cleared existing data")
|
|
|
|
# Seed
|
|
users = create_users(session)
|
|
vertical = create_vertical(session)
|
|
venues, tours, songs, shows = create_sample_data(session, vertical, users)
|
|
seed_user_activity(session, users, shows, songs)
|
|
|
|
print("=" * 60)
|
|
print("✓ DEMO DATA SEEDED SUCCESSFULLY!")
|
|
print("=" * 60)
|
|
print("\nLogin credentials (all passwords: demo123):")
|
|
for user_data in USERS:
|
|
print(f" {user_data['email']:30} ({user_data['username']})")
|
|
print("\nStart the demo server:")
|
|
print(" cd /Users/ten/ANTIGRAVITY/elmeg-demo/backend")
|
|
print(" DATABASE_URL='sqlite:///./elmeg-demo.db' uvicorn main:app --reload --port 8001")
|
|
|
|
if __name__ == "__main__":
|
|
main()
|