You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Tkinter点击按钮导出搜索项到Excel 搜索自动导出问题修复

问题根因

输入搜索内容时自动触发Excel导出,核心是两个问题:

  • 事件绑定错误:输入框的键盘触发事件(或者搜索关联的StringVar变量追踪事件)错误绑定了带导出逻辑的print_area函数,而非仅负责刷新列表的search函数,导致每次按键输入时直接执行了导出代码。
  • 按钮未正确绑定事件:当前Print按钮创建时未指定command参数,即使修复自动触发问题,手动点击按钮也不会执行导出逻辑。

另外现有代码还存在几个隐性bug:

  1. SQL查询用字符串拼接写法,存在SQL注入风险
  2. 遍历查询结果赋值fName时,仅会取最后一条结果的姓名字段作为导出文件名,多结果场景下文件名错误且会覆盖文件
  3. 数据库连接、游标用完未关闭,长期运行会出现连接泄漏
  4. 若excel_backup文件夹不存在,导出时会直接抛路径不存在的错误
  5. print_area和search函数重复写了完全相同的数据库查询、Treeview刷新逻辑,代码冗余
修复方案

1. 修正事件绑定

检查输入框的事件绑定代码,确保<Key>事件仅绑定search函数,如果之前给self.var_search加过trace变量追踪,要移除绑定到print_area的回调:

# 正确的输入框绑定,仅绑定search刷新列表,不要绑print_area
self.txt_search.bind("<Key>", self.search)

2. 给Print按钮绑定导出回调

注意command参数只传函数名,不要加括号(加括号会在窗口初始化时直接执行函数):

self.btn_print = Button(root,text="Print", font=("times new roman", 15), bg="red", fg="white", command=self.print_area)
self.btn_print.pack()

3. 重构优化代码,修复隐性bug

抽离公共查询逻辑,避免重复代码,同时修复其他问题:

import os
import pandas as pd
import pymysql
from tkinter import messagebox, END

# 初始化时先创建备份文件夹,避免路径不存在报错
if not os.path.exists("excel_backup"):
    os.makedirs("excel_backup")

# 抽离公共的查询方法,避免重复写数据库连接逻辑
def fetch_search_data(self):
    con = pymysql.connect(host='localhost', user='root', password='', db='philanthropy')
    cur = con.cursor()
    # 用参数化查询避免SQL注入
    search_key = self.var_search.get()
    cur.execute("select * from istavrity where familycode LIKE %s", (f"%{search_key}%",))
    rows = cur.fetchall()
    # 关闭游标和连接
    cur.close()
    con.close()
    return rows

# 搜索函数仅负责刷新Treeview
def search(self, ev):
    try:
        rows = self.fetch_search_data()
        self.employee_tree.delete(*self.employee_tree.get_children())
        for i in rows:
            self.employee_tree.insert('', END, values=i)
    except Exception as ex:
        messagebox.showerror("Error", f"Error due to {str(ex)}")

# 导出函数仅负责点击按钮后的导出逻辑
def print_area(self):
    try:
        rows = self.fetch_search_data()
        if len(rows) == 0:
            messagebox.showinfo("提示", "没有可导出的搜索结果")
            return
        
        columns = ('S.N.', 'Family Code', 'Family Name', 'Ritwik', 'Swastyayani', 'Family Name', 'Ritwik', 'Swastyayani', 'FamilyCode', 'Family Name', 'Ritwik', 'Swastyayani', 'FamilyCode', 'Family Name', 'Ritwik', 'Swastyayani', 'ravv')
        # 组合文件名,避免多结果场景下文件覆盖
        first_fname = rows[0][1]
        search_key = self.var_search.get()
        treeview_df = pd.DataFrame(rows, columns=columns)
        save_path = f"excel_backup/{search_key}_{first_fname}.xlsx"
        # 导出时取消pandas默认索引列
        treeview_df.to_excel(save_path, index=False)
        messagebox.showinfo("成功", f"导出完成,文件保存至:{save_path}")
    except Exception as ex:
        messagebox.showerror("Error", f"Error due to {str(ex)}")

如果需要导出前同步刷新Treeview的展示结果,可以在print_area里调用self.search(None)复用刷新逻辑,不用重复写节点插入代码。

内容的提问来源于stack exchange,提问作者Ravi Katuwal

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.26 12:06:19