diff --git a/src/api/routes.py b/src/api/routes.py index c2c2155..29c33dd 100644 --- a/src/api/routes.py +++ b/src/api/routes.py @@ -119,12 +119,15 @@ async def upload_stp( async def get_status(task_id: str, db_session: AsyncSession = Depends(get_db_session)): """获取任务状态""" from sqlalchemy import select - from models.database import ProcessingTask, STPFile + from models.database import ProcessingTask, STPFile, GeometryData, MoldCavityData, HTMLFile - # 从数据库查询任务详情 + # 从数据库查询任务详情及相关数据 result = await db_session.execute( - select(ProcessingTask, STPFile) + select(ProcessingTask, STPFile, GeometryData, MoldCavityData, HTMLFile) .join(STPFile, ProcessingTask.stp_file_id == STPFile.id) + .outerjoin(GeometryData, STPFile.id == GeometryData.stp_file_id) + .outerjoin(MoldCavityData, STPFile.id == MoldCavityData.stp_file_id) + .outerjoin(HTMLFile, STPFile.id == HTMLFile.stp_file_id) .where(ProcessingTask.task_id == task_id) ) @@ -133,7 +136,7 @@ async def get_status(task_id: str, db_session: AsyncSession = Depends(get_db_ses if not task_record: raise HTTPException(404, "任务不存在") - task, stp_file = task_record + task, stp_file, geometry_data, mold_cavity_data, html_file = task_record # 构建任务详情数据 task_data = { @@ -148,6 +151,60 @@ async def get_status(task_id: str, db_session: AsyncSession = Depends(get_db_ses "error": task.error_message if task.error_message else "" } + # 如果有几何数据,添加到返回结果 + if geometry_data: + task_data["geometry_data"] = { + "volume": geometry_data.volume, + "surface_area": geometry_data.surface_area, + "bounding_box": { + "min": geometry_data.bounding_box_min, + "max": geometry_data.bounding_box_max, + "dimensions": [ + geometry_data.bounding_box_max[0] - geometry_data.bounding_box_min[0] if geometry_data.bounding_box_max and geometry_data.bounding_box_min else 0, + geometry_data.bounding_box_max[1] - geometry_data.bounding_box_min[1] if geometry_data.bounding_box_max and geometry_data.bounding_box_min else 0, + geometry_data.bounding_box_max[2] - geometry_data.bounding_box_min[2] if geometry_data.bounding_box_max and geometry_data.bounding_box_min else 0 + ] + }, + "topology": { + "faces": geometry_data.topology_faces, + "edges": geometry_data.topology_edges, + "vertices": geometry_data.topology_vertices + }, + "center_of_mass": geometry_data.center_of_mass + } + + # 如果有模具型腔数据,添加到返回结果 + if mold_cavity_data: + task_data["key_info"] = { + "metadata": { + "shrinkage_rate": mold_cavity_data.shrinkage_rate, + "draft_angle": mold_cavity_data.draft_angle + }, + "manufacturing_info": { + "mold_material": mold_cavity_data.mold_material, + "estimated_clamping_force": mold_cavity_data.estimated_clamping_force, + "parting_line_length": mold_cavity_data.parting_line_length + }, + "mold_cavities": { + "cavity_key_info": { + "geometric_characteristics": { + "product_weight": mold_cavity_data.product_weight, + "product_volume": mold_cavity_data.product_volume, + "wall_thickness_range": mold_cavity_data.wall_thickness_range, + "complexity_score": mold_cavity_data.complexity_score + } + } + } + } + + # 如果有HTML文件信息,添加到返回结果 + if html_file: + task_data["html_info"] = { + "filename": html_file.filename, + "file_path": html_file.file_path, + "generated_time": html_file.generated_time.isoformat() if html_file.generated_time else "" + } + logger.info(f"返回任务状态: {task_id} - {task.status}") return task_data @@ -270,17 +327,18 @@ async def history_page(request: Request): }) -@router.get("/result/{task_id}") -@router.post("/result/{task_id}") -async def result_page(request: Request, task_id: str, db_session: AsyncSession = Depends(get_db_session)): - """结果详情页面""" +@router.get("/api/html-info/{task_id}") +@router.post("/api/html-info/{task_id}") +async def get_html_info(task_id: str, db_session: AsyncSession = Depends(get_db_session)): + """获取任务的HTML文件信息""" from sqlalchemy import select - from models.database import ProcessingTask, STPFile, GeometryData, MoldCavityData, HTMLFile + from models.database import ProcessingTask, STPFile, HTMLFile - # 从数据库查询任务详情 + # 从数据库查询HTML文件信息 result = await db_session.execute( - select(ProcessingTask, STPFile) + select(ProcessingTask, STPFile, HTMLFile) .join(STPFile, ProcessingTask.stp_file_id == STPFile.id) + .outerjoin(HTMLFile, STPFile.id == HTMLFile.stp_file_id) .where(ProcessingTask.task_id == task_id) ) @@ -289,9 +347,47 @@ async def result_page(request: Request, task_id: str, db_session: AsyncSession = if not task_record: raise HTTPException(404, "任务不存在") - task, stp_file = task_record + task, stp_file, html_file = task_record - # 构建任务详情数据(先只包含基本数据) + if not html_file: + return {"message": "该任务没有HTML可视化报告"} + + # 返回HTML文件信息 + html_info = { + "filename": html_file.filename, + "file_path": html_file.file_path, + "generated_time": html_file.generated_time.isoformat() if html_file.generated_time else "", + "visualization_type": html_file.visualization_type + } + + return html_info + + +@router.get("/result/{task_id}") +@router.post("/result/{task_id}") +async def result_page(request: Request, task_id: str, db_session: AsyncSession = Depends(get_db_session)): + """结果详情页面""" + from sqlalchemy import select + from models.database import ProcessingTask, STPFile, GeometryData, MoldCavityData, HTMLFile + + # 从数据库查询任务详情及相关数据 + result = await db_session.execute( + select(ProcessingTask, STPFile, GeometryData, MoldCavityData, HTMLFile) + .join(STPFile, ProcessingTask.stp_file_id == STPFile.id) + .outerjoin(GeometryData, STPFile.id == GeometryData.stp_file_id) + .outerjoin(MoldCavityData, STPFile.id == MoldCavityData.stp_file_id) + .outerjoin(HTMLFile, STPFile.id == HTMLFile.stp_file_id) + .where(ProcessingTask.task_id == task_id) + ) + + task_record = result.first() + + if not task_record: + raise HTTPException(404, "任务不存在") + + task, stp_file, geometry_data, mold_cavity_data, html_file = task_record + + # 构建任务详情数据 task_data = { "task_id": task.task_id, "filename": stp_file.original_filename if stp_file else "", @@ -304,6 +400,15 @@ async def result_page(request: Request, task_id: str, db_session: AsyncSession = "error": task.error_message if task.error_message else "" } + # 如果有HTML文件,添加HTML文件信息 + html_info = None + if html_file: + html_info = { + "filename": html_file.filename, + "file_path": html_file.file_path, + "generated_time": html_file.generated_time.isoformat() if html_file.generated_time else "" + } + from fastapi.templating import Jinja2Templates import os # 简化路径配置,直接使用当前工作目录下的templates文件夹 @@ -312,6 +417,7 @@ async def result_page(request: Request, task_id: str, db_session: AsyncSession = return templates.TemplateResponse("result.html", { "request": request, "task": task_data, + "html_info": html_info, "pythonocc_available": True, "version": "3.0.0" }) diff --git a/src/main.py b/src/main.py index 97b7753..977cfb4 100644 --- a/src/main.py +++ b/src/main.py @@ -96,6 +96,10 @@ import os static_dir = os.path.join(os.getcwd(), "static") app.mount("/static", StaticFiles(directory=static_dir), name="static") +# 挂载HTML输出目录 +html_output_dir = os.path.join(os.getcwd(), "html_output") +app.mount("/html-output", StaticFiles(directory=html_output_dir), name="html_output") + # 注册路由 app.include_router(router) diff --git a/templates/result.html b/templates/result.html index 5a4c367..bf0a192 100644 --- a/templates/result.html +++ b/templates/result.html @@ -178,6 +178,14 @@