hale-api / deploy_spaces.py
Raunak211006's picture
Deploy v3.2 to Hugging Face (excluding binaries)
c50a873
Raw
History Blame Contribute Delete
4.89 kB
"""
Direct HF Spaces deploy script — creates space, uploads all files.
"""
import os
import json
import shutil
import tempfile
from pathlib import Path
from huggingface_hub import HfApi, upload_folder
api = HfApi()
SPACE_ID = "Raunak211006/hale-api"
PROJECT_DIR = os.path.dirname(os.path.abspath(__file__))
print("=" * 60)
print("HALE API -> Hugging Face Spaces Deploy")
print("=" * 60)
# 1. Create Space
print("\n[1/4] Creating Space...")
try:
api.create_repo(
repo_id=SPACE_ID,
repo_type="space",
space_sdk="docker",
private=False,
exist_ok=True,
)
print(f" > Space ready: https://huggingface.co/spaces/{SPACE_ID}")
except Exception as e:
print(f" Space: {e}")
# 2. Prepare deploy directory
print("\n[2/4] Preparing deploy files...")
deploy_dir = os.path.join(tempfile.gettempdir(), "hale-deploy")
if os.path.exists(deploy_dir):
shutil.rmtree(deploy_dir)
os.makedirs(deploy_dir)
# Files/dirs to SKIP
SKIP = {
'.git', '__pycache__', '.pytest_cache', 'hale-frontend',
'node_modules', '.env', 'data', 'logs', '.planning',
'Dockerfile.spaces', 'deploy_hf.py', 'deploy_spaces.py',
'.github', '.gitattributes', '.dockerignore',
'docker-compose.yml', 'alembic', 'alembic.ini',
'debug_hale_db.py', 'migrate_db.py', 'seed_test_data.py',
'simulate_e2e.py', '.antigravityignore',
}
for item in os.listdir(PROJECT_DIR):
if item in SKIP:
continue
src = os.path.join(PROJECT_DIR, item)
dst = os.path.join(deploy_dir, item)
try:
if os.path.isdir(src):
shutil.copytree(src, dst, dirs_exist_ok=True,
ignore=shutil.ignore_patterns('__pycache__', '*.pyc', '.pytest_cache'))
else:
shutil.copy2(src, dst)
except Exception as e:
print(f" Skip {item}: {e}")
# Copy Dockerfile.spaces as Dockerfile
spaces_dockerfile = os.path.join(PROJECT_DIR, "Dockerfile.spaces")
if os.path.exists(spaces_dockerfile):
shutil.copy2(spaces_dockerfile, os.path.join(deploy_dir, "Dockerfile"))
print(" > Dockerfile.spaces -> Dockerfile")
# Create .env for spaces
env_content = f"""APP_ENV=production
DATABASE_URL=sqlite:///./data/hale.db
CORS_ORIGINS=*
LOG_LEVEL=INFO
GEMINI_API_KEYS={os.environ.get('GEMINI_API_KEYS', '')}
SECRET_KEY=hale-production-key-change-me-to-random-64-chars-in-settings
"""
# Read GEMINI keys from local .env
local_env = os.path.join(PROJECT_DIR, ".env")
if os.path.exists(local_env):
with open(local_env) as f:
for line in f:
line = line.strip()
if line.startswith("GEMINI_API_KEYS="):
gemini_keys = line.split("=", 1)[1]
env_content = env_content.replace(
f"GEMINI_API_KEYS=",
f"GEMINI_API_KEYS={gemini_keys}"
)
break
with open(os.path.join(deploy_dir, ".env"), "w", encoding="utf-8") as f:
f.write(env_content)
print(" > .env created")
# Create README.md with HF Spaces metadata
readme = "---\ntitle: HALE - Adaptive Learning Engine API\nemoji: \U0001F9E0\ncolorFrom: purple\ncolorTo: blue\nsdk: docker\napp_port: 7860\npinned: true\n---\n\n# HALE - Adaptive Learning Engine\n\nAI-powered adaptive learning API with Reinforcement Learning behavioral engine.\n\n**API Docs**: [Open Swagger UI](/docs)\n\n## Quick Start\n1. POST /api/auth/register - Register user\n2. POST /api/auth/login - Get JWT token\n3. POST /api/goals/ - Create a learning goal\n4. GET /api/plan - Get todays adaptive plan\n5. POST /api/complete-task - Mark task done\n6. GET /api/stats - View analytics\n\n## Features\n- Contextual Multi-Armed Bandit RL engine (Thompson Sampling)\n- AI-generated curriculum via Gemini\n- Behavioral adaptation (mood, fatigue, stress, sleep)\n- Multi-goal support with priority-weighted scheduling\n- Streak tracking, XP, and leveling system\n- Auto-close at 2 AM IST with next-day preparation\n"
with open(os.path.join(deploy_dir, "README.md"), "w", encoding="utf-8") as f:
f.write(readme)
print(" > README.md created")
# Count files
file_count = sum(len(files) for _, _, files in os.walk(deploy_dir))
print(f" > {file_count} files ready")
# 3. Upload
print(f"\n[3/4] Uploading to HF Spaces ({SPACE_ID})...")
try:
api.upload_folder(
folder_path=deploy_dir,
repo_id=SPACE_ID,
repo_type="space",
commit_message="Deploy HALE API v3.1",
)
print(" > Upload complete!")
except Exception as e:
print(f" Upload failed: {e}")
raise
# 4. Done
print("")
print("=" * 60)
print("DEPLOYMENT COMPLETE!")
print("")
print("API: https://raunak211006-hale-api.hf.space")
print("Docs: https://raunak211006-hale-api.hf.space/docs")
print(f"Space: https://huggingface.co/spaces/{SPACE_ID}")
print("")
print("Building may take 2-3 minutes. Check the Space page for status.")
print("=" * 60)