From f192a7a302373ae931104d6cb44076fe694da470 Mon Sep 17 00:00:00 2001
From: zhangxiao <898441624@qq.com>
Date: 星期三, 16 十月 2024 14:53:32 +0800
Subject: [PATCH] 报表合并

---
 .gitignore                           |    1 
 app/api/excel.py                     |  105 +++++++++++++++++++++++++++++++++++
 main.py                              |    2 
 app/utils/excelmerge/conformity.py   |   64 +++++++++++++++++++++
 app/utils/excelmerge/国网上海电力整合模版.xlsx |    0 
 5 files changed, 172 insertions(+), 0 deletions(-)

diff --git a/.gitignore b/.gitignore
index 7836932..cba8701 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,5 +1,6 @@
 venv
 dist
+data
 build
 main
 __pycache__
diff --git a/app/api/excel.py b/app/api/excel.py
new file mode 100644
index 0000000..78a5e03
--- /dev/null
+++ b/app/api/excel.py
@@ -0,0 +1,105 @@
+from fastapi import APIRouter, File, UploadFile
+from fastapi.responses import JSONResponse, FileResponse
+from fastapi.exceptions import HTTPException
+from werkzeug.utils import secure_filename
+from app.utils.excelmerge.conformity import run_conformity
+from pathlib import Path
+import subprocess
+import shutil
+import os
+
+
+router = APIRouter()
+
+ALLOWED_EXTENSIONS = {'xlsx'}
+EXCEL_FILES_PATH = 'data/output'
+SOURCE_FILES_PATH = 'data/source'
+output_path_value = None
+
+
+def allowed_file(filename):
+    return '.' in filename and filename.rsplit('.', 1)[1].lower() in ALLOWED_EXTENSIONS
+
+
+def create_dir_if_not_exists(path):
+    if not os.path.exists(path):
+        os.makedirs(path)
+
+
+@router.post('/excel/upload')
+async def upload_file(files: list[UploadFile] = File(...)):
+    if not any(file.filename for file in files):
+        return JSONResponse(content={"error": "娌℃湁鏂囦欢閮ㄥ垎"}, status_code=400)
+
+    create_dir_if_not_exists(SOURCE_FILES_PATH)
+
+    # 娓呯┖SOURCE_FILES_PATH鐩綍
+    for filename in os.listdir(SOURCE_FILES_PATH):
+        file_path = os.path.join(SOURCE_FILES_PATH, filename)
+        try:
+            if os.path.isfile(file_path) or os.path.islink(file_path):
+                os.unlink(file_path)
+            elif os.path.isdir(file_path):
+                shutil.rmtree(file_path)
+        except Exception as e:
+            return JSONResponse(content={"error": "鏂囦欢澶勭悊鍑洪敊"}, status_code=500)
+
+    save_path_list = []
+    for file in files:
+        if file.filename == '':
+            return JSONResponse(content={"error": "娌℃湁閫夋嫨鏂囦欢"}, status_code=400)
+        if file and allowed_file(file.filename):
+            filename = secure_filename(file.filename)
+            save_path = os.path.join(SOURCE_FILES_PATH, filename)
+            with open(save_path, 'wb') as buffer:
+                shutil.copyfileobj(file.file, buffer)
+            save_path_list.append(save_path)
+        else:
+            return JSONResponse(content={"error": "涓嶅厑璁哥殑鏂囦欢绫诲瀷"}, status_code=400)
+    return JSONResponse(content={"message": "鏂囦欢涓婁紶鎴愬姛", "paths": save_path_list}, status_code=201)
+
+
+@router.post('/excel/conformity')
+async def run_conformity_api():
+    global output_path_value  # 澹版槑鍏ㄥ眬鍙橀噺
+    try:
+        create_dir_if_not_exists(EXCEL_FILES_PATH)
+
+        # 娓呯┖EXCEL_FILES_PATH鐩綍
+        for filename in os.listdir(EXCEL_FILES_PATH):
+            file_path = os.path.join(EXCEL_FILES_PATH, filename)
+            try:
+                if os.path.isfile(file_path) or os.path.islink(file_path):
+                    os.unlink(file_path)
+                elif os.path.isdir(file_path):
+                    shutil.rmtree(file_path)
+            except Exception as e:
+                return JSONResponse(content={"error": "鏂囦欢澶勭悊鍑洪敊"}, status_code=500)
+
+        # 杩愯鏂规硶
+        output_path = run_conformity()
+        output_path_value = output_path
+        return JSONResponse(content={"message": "conformity.py 杩愯鎴愬姛", "output_path": str(output_path)}, status_code=200)
+    except Exception as e:
+        return JSONResponse(content={"error": str(e)}, status_code=500)
+
+
+@router.get('/excel/file/status')
+async def get_file_status():
+    try:
+        return JSONResponse(content={"output_path": str(output_path_value)}, status_code=200)
+    except Exception as e:
+        return JSONResponse(content={"error": str(e)}, status_code=500)
+
+
+@router.get('/excel/download_excel')
+async def download_excel():
+    try:
+        files = os.listdir(EXCEL_FILES_PATH)
+        first_file = files[0]
+        return FileResponse(os.path.join(EXCEL_FILES_PATH, first_file), filename=first_file,
+                            media_type='application/vnd.openxmlformats-officedocument.spreadsheetml.sheet')
+    except FileNotFoundError:
+        raise HTTPException(status_code=404, detail="鏂囦欢涓嶅瓨鍦�")
+    except Exception as e:
+        raise HTTPException(status_code=500, detail="鏈嶅姟鍣ㄩ敊璇�")
\ No newline at end of file
diff --git a/app/utils/excelmerge/conformity.py b/app/utils/excelmerge/conformity.py
new file mode 100644
index 0000000..901357c
--- /dev/null
+++ b/app/utils/excelmerge/conformity.py
@@ -0,0 +1,64 @@
+import xlwings as xw
+from datetime import datetime
+import os
+import shutil
+
+
+def run_conformity():
+
+    source_folder = os.path.join('data', 'source')
+    template_path = os.path.join('app', 'utils', 'excelmerge', '鍥界綉涓婃捣鐢靛姏鏁村悎妯$増.xlsx')
+    EXCEL_FILES_PATH = os.path.join('data', 'output')
+
+    app = xw.App(visible=False)
+    templateExcel = xw.Book(template_path)
+
+    sheet1 = templateExcel.sheets['鎶�鏈洃鐫e伐浣滅粺璁¤〃']
+    sheet2 = templateExcel.sheets['鎶�鏈洃鐫e憡锛堥锛夎鍗曠粺璁¤〃']
+    sheet3 = templateExcel.sheets['鎶曚骇鍓嶆妧鏈洃鐫f姤鍛婄粺璁¤〃']
+    sheet4 = templateExcel.sheets['鎶�鏈洃鐫g粏鍒欏畬鍠勫缓璁�']
+    sheet5 = templateExcel.sheets['鍏稿瀷缁忛獙浜ゆ祦']
+
+    source_files = [f for f in os.listdir(source_folder) if f.endswith('.xlsx') and not f.startswith('~$')]
+
+    for file in source_files:
+        sourceExcel = xw.Book(os.path.join(source_folder, file))
+        ssheet1 = sourceExcel.sheets['鎶�鏈洃鐫e伐浣滅粺璁¤〃']
+        ssheet2 = sourceExcel.sheets['鎶�鏈洃鐫e憡锛堥锛夎鍗曠粺璁¤〃']
+        ssheet3 = sourceExcel.sheets['鎶曚骇鍓嶆妧鏈洃鐫f姤鍛婄粺璁¤〃']
+        ssheet4 = sourceExcel.sheets['鎶�鏈洃鐫g粏鍒欏畬鍠勫缓璁�']
+        ssheet5 = sourceExcel.sheets['鍏稿瀷缁忛獙浜ゆ祦']
+        for ssheet in [ssheet1, ssheet2, ssheet3, ssheet4, ssheet5]:
+            last_row_value = ssheet.range(f'A{ssheet.used_range.rows.count}').value
+            if isinstance(last_row_value, str):
+                ssheet.range(f'A{ssheet.used_range.rows.count}:AA{ssheet.used_range.rows.count}').delete()
+        for (ssheet, tsheet, start_point) in [
+            (ssheet1, sheet1, 4),
+            (ssheet2, sheet2, 3),
+            (ssheet3, sheet3, 3),
+            (ssheet4, sheet4, 4),
+            (ssheet5, sheet5, 3),
+        ]:
+            for row in range(start_point, ssheet.used_range.rows.count + 1):
+                a_cell_value = ssheet.range(f'A{row}').value
+                if not isinstance(a_cell_value, (int, float)):
+                    continue
+                if not all(cell.value is None or cell.value == '' for cell in ssheet.range(f'B{row}:AA{row}')):
+                    tsheet.range(f'B{tsheet.used_range.rows.count + 1}').value = ssheet.range(f'B{row}:AA{row}').value
+        sourceExcel.close()
+    for tsheet, start_point in [(sheet1, 4), (sheet2, 3), (sheet3, 3), (sheet4, 4), (sheet5, 3)]:
+        last_row = tsheet.used_range.rows.count
+        number = 1
+        for i in range(start_point, last_row + 1):
+            tsheet.range(f'A{i}').value = number
+            number += 1
+
+    timestamp = datetime.now().strftime('%Y-%m-%d_%H-%M-%S')
+    output_path = os.path.join(EXCEL_FILES_PATH, f'{timestamp}.xlsx')
+    templateExcel.save(output_path)
+    templateExcel.close()
+    app.quit()
+
+    return timestamp
+
+
diff --git "a/app/utils/excelmerge/\345\233\275\347\275\221\344\270\212\346\265\267\347\224\265\345\212\233\346\225\264\345\220\210\346\250\241\347\211\210.xlsx" "b/app/utils/excelmerge/\345\233\275\347\275\221\344\270\212\346\265\267\347\224\265\345\212\233\346\225\264\345\220\210\346\250\241\347\211\210.xlsx"
new file mode 100644
index 0000000..d7c7e52
--- /dev/null
+++ "b/app/utils/excelmerge/\345\233\275\347\275\221\344\270\212\346\265\267\347\224\265\345\212\233\346\225\264\345\220\210\346\250\241\347\211\210.xlsx"
Binary files differ
diff --git a/main.py b/main.py
index d5a8c5d..70d19c0 100644
--- a/main.py
+++ b/main.py
@@ -2,6 +2,7 @@
 from app.api.auth import router as auth_router
 from app.api.chat import router as chat_router
 from app.api.agent import router as agent_router
+from app.api.excel import router as excel_router
 from app.models.base_model import init_db
 
 init_db()
@@ -14,6 +15,7 @@
 app.include_router(auth_router, prefix='/auth', tags=["auth"])
 app.include_router(chat_router, prefix='/chat', tags=["chat"])
 app.include_router(agent_router, prefix='/agent', tags=["agent"])
+app.include_router(excel_router, prefix='/document', tags=["document"])
 
 if __name__ == "__main__":
     import uvicorn

--
Gitblit v1.8.0