# Copyright 2024 Heinrich Krupp
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
#     http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.

"""
Backup management endpoints for MCP Memory Service.

Provides status monitoring, manual backup triggering, and backup listing.
"""

from typing import List, Optional

from fastapi import APIRouter, HTTPException, Depends
from pydantic import BaseModel

from mcp_memory_service.config import OAUTH_ENABLED

# OAuth authentication imports
from ..oauth.middleware import require_read_access, require_write_access, AuthenticationResult

router = APIRouter()


class BackupStatusResponse(BaseModel):
    """Backup status response model."""
    enabled: bool
    interval: str
    retention_days: int
    max_count: int
    backup_count: int
    total_size_bytes: int
    last_backup_time: Optional[float]
    time_since_last_seconds: Optional[float]
    next_backup_at: Optional[str]
    scheduler_running: bool
    backup_directory: Optional[str] = None


class BackupCreateResponse(BaseModel):
    """Backup creation response model."""
    success: bool
    filename: Optional[str] = None
    size_bytes: Optional[int] = None
    created_at: Optional[str] = None
    duration_seconds: Optional[float] = None
    error: Optional[str] = None


class BackupInfo(BaseModel):
    """Backup information model."""
    filename: str
    size_bytes: int
    created_at: str
    age_days: int


class BackupListResponse(BaseModel):
    """Backup list response model."""
    backups: List[BackupInfo]
    total_count: int
    total_size_bytes: int


@router.get("/backup/status", response_model=BackupStatusResponse)
async def get_backup_status(
    user: AuthenticationResult = Depends(require_read_access)
):
    """
    Get current backup service status.

    Returns backup configuration, last backup time, and next scheduled backup.
    """
    try:
        from mcp_memory_service.backup.scheduler import get_backup_scheduler
        scheduler = get_backup_scheduler()
        status = scheduler.get_status()

        return BackupStatusResponse(
            enabled=status.get('enabled', False),
            interval=status.get('interval', 'daily'),
            retention_days=status.get('retention_days', 7),
            max_count=status.get('max_count', 10),
            backup_count=status.get('backup_count', 0),
            total_size_bytes=status.get('total_size_bytes', 0),
            last_backup_time=status.get('last_backup_time'),
            time_since_last_seconds=status.get('time_since_last_seconds'),
            next_backup_at=status.get('next_backup_at'),
            scheduler_running=status.get('scheduler_running', False),
            backup_directory=status.get('backups_dir'),
        )

    except Exception as e:
        raise HTTPException(status_code=500, detail=f"Failed to get backup status: {str(e)}")


@router.post("/backup/now", response_model=BackupCreateResponse)
async def trigger_backup(
    user: AuthenticationResult = Depends(require_write_access)
):
    """
    Manually trigger an immediate backup.

    Creates a new backup of the database regardless of the schedule.
    """
    try:
        from mcp_memory_service.backup.scheduler import get_backup_service
        backup_service = get_backup_service()
        result = await backup_service.create_backup(description="Manual backup from dashboard")

        if result.get('success'):
            return BackupCreateResponse(
                success=True,
                filename=result.get('filename'),
                size_bytes=result.get('size_bytes'),
                created_at=result.get('created_at'),
                duration_seconds=result.get('duration_seconds')
            )
        else:
            return BackupCreateResponse(
                success=False,
                error=result.get('error', 'Unknown error')
            )

    except Exception as e:
        raise HTTPException(status_code=500, detail=f"Failed to create backup: {str(e)}")


@router.get("/backup/list", response_model=BackupListResponse)
async def list_backups(
    user: AuthenticationResult = Depends(require_read_access)
):
    """
    List all available backups.

    Returns list of backups sorted by date (newest first).
    """
    try:
        from mcp_memory_service.backup.scheduler import get_backup_service
        backup_service = get_backup_service()
        backups = backup_service.list_backups()

        backup_infos = [
            BackupInfo(
                filename=b['filename'],
                size_bytes=b['size_bytes'],
                created_at=b['created_at'],
                age_days=b['age_days']
            )
            for b in backups
        ]

        total_size = sum(b['size_bytes'] for b in backups)

        return BackupListResponse(
            backups=backup_infos,
            total_count=len(backup_infos),
            total_size_bytes=total_size
        )

    except Exception as e:
        raise HTTPException(status_code=500, detail=f"Failed to list backups: {str(e)}")
