diff options
Diffstat (limited to 'backend')
| -rw-r--r-- | backend/app/auth/models.py | 5 | ||||
| -rw-r--r-- | backend/app/auth/routes.py | 47 |
2 files changed, 51 insertions, 1 deletions
diff --git a/backend/app/auth/models.py b/backend/app/auth/models.py index 76c33fa..8477ba2 100644 --- a/backend/app/auth/models.py +++ b/backend/app/auth/models.py @@ -1,5 +1,5 @@ import os -from sqlalchemy import Column, Integer, String, DateTime, create_engine +from sqlalchemy import Column, Integer, String, DateTime, Text, create_engine from sqlalchemy.ext.declarative import declarative_base from sqlalchemy.orm import sessionmaker from datetime import datetime @@ -23,6 +23,9 @@ class User(Base): hashed_password = Column(String(255), nullable=False) created_at = Column(DateTime, default=datetime.utcnow) is_active = Column(Integer, default=1) + # API Keys (stored encrypted in production, plain for simplicity here) + openai_api_key = Column(Text, nullable=True) + gemini_api_key = Column(Text, nullable=True) def init_db(): diff --git a/backend/app/auth/routes.py b/backend/app/auth/routes.py index 7f07c2a..3c906b5 100644 --- a/backend/app/auth/routes.py +++ b/backend/app/auth/routes.py @@ -2,6 +2,7 @@ from fastapi import APIRouter, Depends, HTTPException, status from fastapi.security import OAuth2PasswordBearer, OAuth2PasswordRequestForm from sqlalchemy.orm import Session from typing import Optional +from pydantic import BaseModel from .models import User, get_db from .utils import ( @@ -212,6 +213,52 @@ async def get_me(current_user: User = Depends(get_current_user)): return current_user +@router.get("/api-keys") +async def get_api_keys(current_user: User = Depends(get_current_user)): + """ + Get current user's API keys (masked for security). + """ + def mask_key(key: str | None) -> str: + if not key: + return "" + if len(key) <= 8: + return "*" * len(key) + return key[:4] + "*" * (len(key) - 8) + key[-4:] + + return { + "openai_api_key": mask_key(current_user.openai_api_key), + "gemini_api_key": mask_key(current_user.gemini_api_key), + "has_openai_key": bool(current_user.openai_api_key), + "has_gemini_key": bool(current_user.gemini_api_key), + } + + +class ApiKeysUpdate(BaseModel): + openai_api_key: Optional[str] = None + gemini_api_key: Optional[str] = None + + +@router.post("/api-keys") +async def update_api_keys( + keys: ApiKeysUpdate, + current_user: User = Depends(get_current_user), + db: Session = Depends(get_db) +): + """ + Update current user's API keys. + Pass empty string to clear a key, or omit to keep unchanged. + """ + if keys.openai_api_key is not None: + current_user.openai_api_key = keys.openai_api_key if keys.openai_api_key else None + + if keys.gemini_api_key is not None: + current_user.gemini_api_key = keys.gemini_api_key if keys.gemini_api_key else None + + db.commit() + + return {"message": "API keys updated successfully"} + + @router.post("/logout") async def logout(): """ |
