#!/usr/bin/env python3 # -*- coding: utf-8 -*- """ 修复数据库表结构脚本 用于检查和修复 t_daily_report_history 表的 file_path 字段 """ import pymysql import sys # 数据库配置 DB_CONFIG = { 'host': 'haoslm2.xicp.net', 'port': 10216, 'user': 'root', 'password': 'DsideaL147258369', 'database': 'yltcharge', 'charset': 'utf8mb4' } def check_table_structure(): """检查表结构""" try: connection = pymysql.connect(**DB_CONFIG) cursor = connection.cursor() # 检查历史表是否存在 cursor.execute("SHOW TABLES LIKE 't_daily_report_history'") result = cursor.fetchone() if not result: print("❌ t_daily_report_history 表不存在") print("请先访问 http://localhost:5000/api/init-tables 初始化数据库") return False print("✓ t_daily_report_history 表存在") # 检查表结构 cursor.execute("DESCRIBE t_daily_report_history") columns = cursor.fetchall() column_names = [col[0] for col in columns] print(f"\n表结构包含 {len(columns)} 个字段:") for col in columns: print(f" - {col[0]}: {col[1]}") # 检查是否有 file_path 字段 if 'file_path' not in column_names: print("\n❌ 缺少 file_path 字段") return False print("\n✓ file_path 字段存在") # 检查是否有其他必要字段 required_fields = ['id', 'report_date', 'start_time', 'end_time', 'split_type', 'split_value', 'split_name', 'config_id', 'total_orders', 'total_amount', 'sum_results', 'file_path', 'status', 'create_time'] missing_fields = [f for f in required_fields if f not in column_names] if missing_fields: print(f"\n❌ 缺少以下字段: {', '.join(missing_fields)}") return False print("✓ 所有必要字段都存在") # 检查数据 cursor.execute("SELECT COUNT(*) FROM t_daily_report_history") count = cursor.fetchone()[0] print(f"\n历史记录数量: {count}") if count > 0: # 检查最近的记录 cursor.execute(""" SELECT id, status, file_path, report_date, split_name FROM t_daily_report_history ORDER BY create_time DESC LIMIT 5 """) records = cursor.fetchall() print("\n最近5条记录:") for record in records: id, status, file_path, report_date, split_name = record status_text = '成功' if status == 1 else '失败' file_status = '有文件' if file_path else '无文件' print(f" ID: {id}, 状态: {status_text}, {file_status}, 日期: {report_date}, 名称: {split_name}") if status == 1 and not file_path: print(f" ⚠️ 警告: 状态为成功但file_path为空!") cursor.close() connection.close() return True except Exception as e: print(f"❌ 检查失败: {e}") return False def fix_table(): """修复表结构(删除旧表重建)""" try: print("\n" + "="*50) print("开始修复表结构...") print("="*50) connection = pymysql.connect(**DB_CONFIG) cursor = connection.cursor() # 删除旧表 print("\n1. 删除旧表...") cursor.execute("DROP TABLE IF EXISTS t_daily_report_history") print(" ✓ 已删除 t_daily_report_history") cursor.execute("DROP TABLE IF EXISTS t_daily_report_config") print(" ✓ 已删除 t_daily_report_config") # 重建历史表 print("\n2. 重建历史表...") create_history_table = """ CREATE TABLE t_daily_report_history ( id BIGINT NOT NULL COMMENT '历史ID', report_date VARCHAR(20) NULL COMMENT '报表日期', start_time VARCHAR(50) NULL COMMENT '开始时间', end_time VARCHAR(50) NULL COMMENT '结束时间', split_type VARCHAR(20) NULL COMMENT '拆分方式', split_value VARCHAR(100) NULL COMMENT '拆分值', split_name VARCHAR(200) NULL COMMENT '拆分显示名称', config_id BIGINT NULL COMMENT '配置ID', total_orders INT NULL COMMENT '订单总数', total_amount DECIMAL(10,2) NULL COMMENT '总金额', sum_results VARCHAR(2000) NULL COMMENT '求和结果', file_path VARCHAR(500) NULL COMMENT '文件路径', status TINYINT NULL COMMENT '状态', create_time DATETIME NULL COMMENT '创建时间' ) UNIQUE KEY(id) DISTRIBUTED BY HASH(id) BUCKETS 1 PROPERTIES("replication_num" = "1") """ cursor.execute(create_history_table) print(" ✓ 已创建 t_daily_report_history") # 重建配置表 print("\n3. 重建配置表...") create_config_table = """ CREATE TABLE t_daily_report_config ( id BIGINT NOT NULL COMMENT '配置ID', config_name VARCHAR(100) NOT NULL COMMENT '配置名称', split_type VARCHAR(20) NOT NULL COMMENT '拆分方式', split_value VARCHAR(100) NOT NULL COMMENT '拆分值', split_name VARCHAR(200) NULL COMMENT '拆分显示名称', selected_fields VARCHAR(3000) NOT NULL COMMENT '选择的字段列表', sum_fields VARCHAR(3000) NULL COMMENT '求和字段列表', is_active TINYINT NULL COMMENT '是否启用', sort_order INT NULL COMMENT '排序顺序', create_time DATETIME NULL COMMENT '创建时间', update_time DATETIME NULL COMMENT '更新时间' ) UNIQUE KEY(id) DISTRIBUTED BY HASH(id) BUCKETS 1 PROPERTIES("replication_num" = "1") """ cursor.execute(create_config_table) print(" ✓ 已创建 t_daily_report_config") connection.commit() cursor.close() connection.close() print("\n" + "="*50) print("✓ 表结构修复完成!") print("="*50) print("\n请重新创建配置并生成日报") return True except Exception as e: print(f"\n❌ 修复失败: {e}") return False def main(): print("="*50) print("数据库表结构检查和修复工具") print("="*50) # 检查表结构 print("\n【步骤1】检查表结构...") if not check_table_structure(): # 询问是否修复 print("\n" + "="*50) choice = input("是否删除旧表并重建?(y/n): ") if choice.lower() == 'y': fix_table() else: print("\n取消修复") else: print("\n" + "="*50) print("✓ 表结构正常") print("="*50) print("\n如果仍然无法下载,请:") print("1. 重启服务: python app.py") print("2. 清除浏览器缓存: Ctrl+F5") print("3. 重新生成日报") print("\n按回车键退出...") input() if __name__ == '__main__': main()