import uvicorn
from fastapi import FastAPI, Form, HTTPException
from pydantic import BaseModel

from tool.pdf2md import pdf2ai
from utils import dmQuery
from utils.shellUtil import execute_command_on_linux
from utils.text_to_html import save_html_to_file

from utils.markd_pdf.markdown_pdf import *
from utils.markd_pdf.minio_upload import *
from utils.markd_pdf.save_markdown import *


app = FastAPI() # 创建API实例

@app.get("/")
async def root():
    return {"message": "Hello World"}


# 将数据模型定义为继承BaseModel的类
class Item(BaseModel):
    sql: str


class Pdf2md(BaseModel):
    pdfUrl: str
    prompt: str
    pageNum: int


class Saved2text(BaseModel):
    htmlContent: str
    fileName: str

class MarkdownRequest(BaseModel):
    content: str    #Markdown文本内容
    output_dir: Optional[str] = os.getcwd()  # 输出文件保存目录（可选），默认保存在当前目录
    keep_docx: Optional[bool] = False   #是否保留中间生成的DOCX文件（可选），仅PDF转换时有效

class MinIORequest(BaseModel):
    file_path: str  #本地文件路径，例如：D:/output/test.pdf
    object_name: Optional[str] = None   #MinIO中存储的文件名（可选），默认使用本地文件名

class MinIODownloadRequest(BaseModel):
    object_name: str    # MinIO中要下载的文件名
    local_file_path: Optional[str] = None   # 本地保存路径（可选），默认保存在当前目录

@app.put("/exsql")
async def create_item( item: Item, q: str = None):
    result = {**item.dict()}
    results = dmQuery.execute_query(item.sql)

    return results



@app.put("/exshell")
async def create_item( item: Item, q: str = None):
    # 配置 Linux 服务器信息
    host = '119.29.146.254'
    port = 22
    username = 'root'
    password = 'zrd1236987!'
    # 要执行的命令

    result = execute_command_on_linux(host, port, username, password, item.sql)

    return result


@app.put("/pdf2md")
async def pdf2md(item: Pdf2md, q: str = None):
    pdf_url = 'http://42.194.163.46:9007/ywd/%E6%89%AB%E6%8F%8F%E5%85%A8%E8%83%BD%E7%8E%8B%202025-03-20%2021.38.pdf'
    prompt = "提取有效信息，只输出图片有效信息无效信息不用。"

    result = pdf2ai(item.pdfUrl, item.prompt, item.pageNum)

    return result

@app.put("/md2html")
async def saved2text(htmlContent: str = Form(...), fileName: str = Form(...)):
    pdf_url = 'http://42.194.163.46:9007/ywd/%E6%89%AB%E6%8F%8F%E5%85%A8%E8%83%BD%E7%8E%8B%202025-03-20%2021.38.pdf'
    prompt = "提取有效信息，只输出图片有效信息无效信息不用。"

    result = save_html_to_file(htmlContent, fileName)

    return result


@app.get("/test")
async def test_api():
    """
    测试接口
    :return: 包含测试信息的JSON响应
    """
    return {
        "status": "success",
        "message": "服务运行正常",
        "timestamp": os.path.getmtime(__file__),
        "version": "1.0.0"
    }


@app.post("/convert/pdf",
          summary="Markdown转PDF",
          description="将Markdown文本内容转换为PDF文件，支持中文和代码高亮")
async def convert_to_pdf(request: MarkdownRequest):
    try:
        # 创建临时文件保存Markdown内容
        temp_md = "temp.md"
        with open(temp_md, "w", encoding="utf-8") as f:
            f.write(request.content)

        # 转换PDF
        pdf_path = markdown_to_pdf(temp_md, request.output_dir)

        # 清理临时文件
        os.remove(temp_md)

        return {"status": "success", "pdf_path": pdf_path}
    except Exception as e:
        raise HTTPException(status_code=500, detail=str(e))


@app.post("/convert/docx",
          summary="Markdown转DOCX",
          description="将Markdown文本内容转换为DOCX文件，保留原始格式")
async def convert_to_docx(request: MarkdownRequest):
    try:
        # 创建临时文件保存Markdown内容
        temp_md = "temp.md"
        with open(temp_md, "w", encoding="utf-8") as f:
            f.write(request.content)

        # 转换DOCX
        docx_path = markdown_to_docx(temp_md, request.output_dir)

        # 清理临时文件
        os.remove(temp_md)

        return {"status": "success", "docx_path": docx_path}
    except Exception as e:
        raise HTTPException(status_code=500, detail=str(e))


@app.post("/save/markdown",
          summary="保存Markdown文件",
          description="将Markdown内容保存为本地文件")
async def save_markdown_file(request: MarkdownRequest):
    try:
        # 使用当前时间戳作为默认文件名
        import time
        filename = f"markdown_{int(time.time())}"

        # 保存文件
        filepath = save_markdown(request.content, filename, request.output_dir)

        return {
            "status": "success",
            "message": "Markdown文件保存成功",
            "file_path": filepath
        }
    except Exception as e:
        raise HTTPException(status_code=500, detail=str(e))


@app.post("/minio/upload",
          summary="上传文件到MinIO",
          description="将本地文件上传到MinIO存储服务")
async def upload_file(request: MinIORequest):
    try:
        success = upload_to_minio(request.file_path, request.object_name)
        if success:
            return {"status": "success", "message": "文件上传成功"}
        else:
            raise HTTPException(status_code=500, detail="文件上传失败")
    except Exception as e:
        raise HTTPException(status_code=500, detail=str(e))


@app.post("/minio/download",
          summary="从MinIO下载文件",
          description="从MinIO存储服务下载文件到本地")
async def download_file(request: MinIODownloadRequest):
    try:
        success = download_from_minio(request.object_name, request.local_file_path)
        if success:
            return {"status": "success", "message": "文件下载成功"}
        else:
            raise HTTPException(status_code=500, detail="文件下载失败")
    except Exception as e:
        raise HTTPException(status_code=500, detail=str(e))


if __name__ == "__main__":
    uvicorn.run(app, host="0.0.0.0", port=29015, timeout_keep_alive=600)
