from fastapi import FastAPI, UploadFile, Form, Request
from fastapi.responses import JSONResponse
from datetime import datetime
from pathlib import Path
import os
import shutil
import logging

app = FastAPI()

# Ścieżki
TARGET_BASE_DIR = Path("/root/jar/userFiles/files/public/styles/polca/S01")
TEMP_DIR = Path("tempUploads")
LOG_DIR = Path("logs")

# Tworzenie katalogów
for folder in [TEMP_DIR, LOG_DIR]:
    folder.mkdir(parents=True, exist_ok=True)

# Logowanie
logging.basicConfig(
    level=logging.INFO,
    format="%(asctime)s [%(levelname)s] %(message)s",
    handlers=[
        logging.FileHandler(LOG_DIR / "server.log"),
        logging.StreamHandler()
    ]
)

def create_next_subfolder(parent_folder: Path) -> Path:
    logging.info(f"🔧 Tworzenie nowego podkatalogu w: {parent_folder}")
    try:
        parent_folder.mkdir(parents=True, exist_ok=True)

        max_number = 0
        for entry in parent_folder.iterdir():
            if entry.is_dir():
                try:
                    number = int(entry.name)
                    max_number = max(max_number, number)
                except ValueError:
                    continue  # pomiń foldery typu "recordings", "temp" itd.

        next_number = max_number + 1
        if next_number > 999:
            raise Exception("⚠️ Przekroczono maksymalną liczbę folderów (999)")

        new_folder = parent_folder / f"{next_number:02d}"
        new_folder.mkdir()
        logging.info(f"📁 Utworzono folder: {new_folder.resolve()}")
        return new_folder

    except Exception as e:
        logging.error(f"❌ Błąd przy tworzeniu folderu: {e}")
        raise

def save_temp_audio(audio: UploadFile) -> Path:
    timestamp = datetime.now().strftime("%Y%m%d_%H%M%S")
    temp_path = TEMP_DIR / f"audio_{timestamp}.webm"
    content = audio.file.read()
    with open(temp_path, "wb") as f:
        f.write(content)
    logging.info(f"💾 Zapisano tymczasowy plik audio: {temp_path.resolve()}")
    return temp_path

def move_to_final_destination(temp_path: Path, target_dir: Path) -> Path:
    final_path = target_dir / "recording.webm"
    shutil.move(str(temp_path), final_path)
    logging.info(f"🚚 Przeniesiono audio z {temp_path.resolve()} → {final_path.resolve()}")
    return final_path

def save_xpath_if_provided(xpath: str, target_dir: Path):
    if xpath and xpath.strip() != '//*[@id="recordBtn"]':
        xpath_file = target_dir / "xpath.txt"
        with open(xpath_file, "w", encoding="utf-8") as f:
            f.write(xpath)
        logging.info(f"📝 XPath zapisany do: {xpath_file.resolve()}")
    else:
        logging.info("ℹ️ XPath pominięty – brak lub zignorowany (//*[@id=\"recordBtn\"]).")


def save_hash_if_provided(page_hash: str, target_dir: Path):
    if page_hash and page_hash.strip():
        hash_file = target_dir / "pageHash.txt"
        with open(hash_file, "w", encoding="utf-8") as f:
            f.write(page_hash.strip())
        logging.info(f"🔑 Hash strony zapisany do: {hash_file.resolve()}")
    else:
        logging.info("ℹ️ Hash strony pominięty – brak.")


def handle_upload(audio: UploadFile, xpath: str = None, page_hash: str = None) -> dict:
    try:
        temp_audio = save_temp_audio(audio)
        target_folder = create_next_subfolder(TARGET_BASE_DIR)
        final_audio = move_to_final_destination(temp_audio, target_folder)
        save_xpath_if_provided(xpath, target_folder)
        save_hash_if_provided(page_hash, target_folder)
        return {
            "status": "ok",
            "path": str(final_audio.resolve()),
            "xpath_included": bool(xpath),
            "hash_included": bool(page_hash)
        }
    except Exception as e:
        logging.error(f"❌ Upload zakończony błędem: {e}")
        return {
            "status": "error",
            "detail": str(e)
        }

@app.post("/backendSrv02")
async def upload_backend_srv02(
    request: Request,
    audio: UploadFile,
    xpath: str = Form(None),
    hash: str = Form(None)
):
    logging.info("📥 Odebrano POST /backendSrv02")
    result = handle_upload(audio, xpath, hash)
    status_code = 200 if result["status"] == "ok" else 500
    return JSONResponse(status_code=status_code, content=result)

if __name__ == "__main__":
    import uvicorn
    logging.info("📡 Serwer startuje na http://0.0.0.0:8084")
    uvicorn.run("request_handler:app", host="0.0.0.0", port=8084, reload=False)
