# File and media management # app/api/v1/vendor/media.py """ Vendor media and file management endpoints. Vendor Context: Uses token_vendor_id from JWT token (authenticated vendor API pattern) """ import logging from fastapi import APIRouter, Depends, File, Query, UploadFile from sqlalchemy.orm import Session from app.api.deps import get_current_vendor_api from app.core.database import get_db from app.exceptions import InvalidTokenException from app.services.vendor_service import vendor_service from models.database.user import User router = APIRouter(prefix="/media") logger = logging.getLogger(__name__) def _get_vendor_from_token(current_user: User, db: Session): """Helper to get vendor from JWT token.""" if not hasattr(current_user, "token_vendor_id"): raise InvalidTokenException("Token missing vendor information. Please login again.") return vendor_service.get_vendor_by_id(db, current_user.token_vendor_id) @router.get("") def get_media_library( skip: int = Query(0, ge=0), limit: int = Query(100, ge=1, le=1000), media_type: str | None = Query(None, description="image, video, document"), search: str | None = Query(None), current_user: User = Depends(get_current_vendor_api), db: Session = Depends(get_db), ): """ Get vendor media library. TODO: Implement in Slice 3 - Get all media files for vendor - Filter by type (image, video, document) - Search by filename - Support pagination - Return file URLs, sizes, metadata """ vendor = _get_vendor_from_token(current_user, db) # noqa: F841 - vendor will be used when implemented return { "media": [], "total": 0, "skip": skip, "limit": limit, "message": "Media library coming in Slice 3", } @router.post("/upload") async def upload_media( file: UploadFile = File(...), folder: str | None = Query(None, description="products, general, etc."), current_user: User = Depends(get_current_vendor_api), db: Session = Depends(get_db), ): """ Upload media file. TODO: Implement in Slice 3 - Accept file upload - Validate file type and size - Store file (local or cloud storage) - Generate thumbnails for images - Save metadata to database - Return file URL """ vendor = _get_vendor_from_token(current_user, db) # noqa: F841 - vendor will be used when implemented return { "file_url": None, "thumbnail_url": None, "message": "Media upload coming in Slice 3", } @router.post("/upload/multiple") async def upload_multiple_media( files: list[UploadFile] = File(...), folder: str | None = Query(None), current_user: User = Depends(get_current_vendor_api), db: Session = Depends(get_db), ): """ Upload multiple media files at once. TODO: Implement in Slice 3 - Accept multiple files - Process each file - Return list of uploaded file URLs - Handle errors gracefully """ vendor = _get_vendor_from_token(current_user, db) # noqa: F841 - vendor will be used when implemented return { "uploaded_files": [], "failed_files": [], "message": "Multiple upload coming in Slice 3", } @router.get("/{media_id}") def get_media_details( media_id: int, current_user: User = Depends(get_current_vendor_api), db: Session = Depends(get_db), ): """ Get media file details. TODO: Implement in Slice 3 - Get file metadata - Return file URL - Return usage information (which products use this file) """ vendor = _get_vendor_from_token(current_user, db) # noqa: F841 - vendor will be used when implemented return {"message": "Media details coming in Slice 3"} @router.put("/{media_id}") def update_media_metadata( media_id: int, metadata: dict, current_user: User = Depends(get_current_vendor_api), db: Session = Depends(get_db), ): """ Update media file metadata. TODO: Implement in Slice 3 - Update filename - Update alt text - Update tags/categories - Update description """ vendor = _get_vendor_from_token(current_user, db) # noqa: F841 - vendor will be used when implemented return {"message": "Media update coming in Slice 3"} @router.delete("/{media_id}") def delete_media( media_id: int, current_user: User = Depends(get_current_vendor_api), db: Session = Depends(get_db), ): """ Delete media file. TODO: Implement in Slice 3 - Verify file belongs to vendor - Check if file is in use by products - Delete file from storage - Delete database record - Return success/error """ vendor = _get_vendor_from_token(current_user, db) # noqa: F841 - vendor will be used when implemented return {"message": "Media deletion coming in Slice 3"} @router.get("/{media_id}/usage") def get_media_usage( media_id: int, current_user: User = Depends(get_current_vendor_api), db: Session = Depends(get_db), ): """ Get where this media file is being used. TODO: Implement in Slice 3 - Check products using this media - Check other entities using this media - Return list of usage """ vendor = _get_vendor_from_token(current_user, db) # noqa: F841 - vendor will be used when implemented return { "products": [], "other_usage": [], "message": "Media usage tracking coming in Slice 3", } @router.post("/optimize/{media_id}") def optimize_media( media_id: int, current_user: User = Depends(get_current_vendor_api), db: Session = Depends(get_db), ): """ Optimize media file (compress, resize, etc.). TODO: Implement in Slice 3 - Optimize image (compress, resize) - Generate multiple sizes - Keep original - Update database with new versions """ vendor = _get_vendor_from_token(current_user, db) # noqa: F841 - vendor will be used when implemented return {"message": "Media optimization coming in Slice 3"}