import os import hashlib import asyncpg from fastapi import HTTPException from pydantic import BaseModel import app_part1 from app_part1 import app SECRET_KEY = os.environ.get("DOLOR3V_SECRET_KEY", "dev-secret-change-me") IN_MEMORY_USERS = {} def hash_password(password: str) -> str: return hashlib.sha256((password + SECRET_KEY).encode()).hexdigest() class UserCreateRequest(BaseModel): email: str password: str name: str class UserLoginRequest(BaseModel): email: str password: str USERS_TABLE_SQL = "CREATE TABLE IF NOT EXISTS dolor3v_users (id SERIAL PRIMARY KEY, email TEXT UNIQUE NOT NULL, password_hash TEXT NOT NULL, name TEXT NOT NULL, created_at TIMESTAMPTZ NOT NULL DEFAULT now())" @app.post("/v1/auth/register") async def register_user(req: UserCreateRequest): password_hash = hash_password(req.password) if app_part1.db_pool is not None: try: async with app_part1.db_pool.acquire() as conn: await conn.execute(USERS_TABLE_SQL) row = await conn.fetchrow( "INSERT INTO dolor3v_users (email, password_hash, name) VALUES ($1, $2, $3) RETURNING id, email, name", req.email, password_hash, req.name ) return {"user": dict(row), "token": f"user_{row['id']}"} except asyncpg.UniqueViolationError: raise HTTPException(status_code=400, detail="Email already exists") if req.email in IN_MEMORY_USERS: raise HTTPException(status_code=400, detail="Email already exists") user_id = len(IN_MEMORY_USERS) + 1 IN_MEMORY_USERS[req.email] = {"id": user_id, "email": req.email, "password_hash": password_hash, "name": req.name} return {"user": {"id": user_id, "email": req.email, "name": req.name}, "token": f"user_{user_id}"} @app.post("/v1/auth/login") async def login_user(req: UserLoginRequest): password_hash = hash_password(req.password) if app_part1.db_pool is not None: async with app_part1.db_pool.acquire() as conn: row = await conn.fetchrow("SELECT id, email, name FROM dolor3v_users WHERE email = $1 AND password_hash = $2", req.email, password_hash) if not row: raise HTTPException(status_code=401, detail="Invalid credentials") return {"user": dict(row), "token": f"user_{row['id']}"} user = IN_MEMORY_USERS.get(req.email) if not user or user["password_hash"] != password_hash: raise HTTPException(status_code=401, detail="Invalid credentials") return {"user": {"id": user["id"], "email": user["email"], "name": user["name"]}, "token": f"user_{user['id']}"}