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

C#多用户登录表单无法写入SQL Server数据库及验证异常排查

问题排查与解决方案

已确认的问题根因

  • 用户类型选择空引用异常:user_type.SelectedItem在用户未主动选择用户类型时为null,直接调用ToString()方法会直接触发异常,进入catch分支弹出通用错误提示。
  • SQL查询逻辑漏洞+SQL注入风险:当前查询仅过滤用户名和密码,未将用户类型加入查询条件,若账号密码匹配但用户类型选择错误,程序无任何提示反馈,用户感知为登录无响应。同时字符串拼接SQL的写法存在严重SQL注入风险,攻击者可通过特殊输入绕过登录验证。
  • 匹配成功后未中断逻辑:用户类型匹配完成跳转页面后,未添加break或return终止循环,逻辑冗余。
  • 数据写入缺失用户类型字段:多用户表单无法正常存库,是因为新增用户的INSERT语句未加入usertype字段赋值,若该字段在数据库中设置为非空约束,写入操作会直接触发约束错误失败。

可行修复方案

1. 登录逻辑修复(替换原有代码即可)

private void button1_Click(object sender, EventArgs e)
{
    // 先做前端校验,避免空值触发异常
    if (string.IsNullOrWhiteSpace(username.Text) || string.IsNullOrWhiteSpace(password.Text) || user_type.SelectedItem == null)
    {
        MessageBox.Show("请填写完整的账号、密码并选择用户类型", "输入错误", MessageBoxButtons.OK, MessageBoxIcon.Warning);
        return;
    }

    try
    {
        // 使用参数化查询,避免SQL注入,同时直接加入用户类型过滤,无需后续循环判断
        string query = "SELECT * FROM log_data WHERE username = @username AND password = @password AND usertype = @usertype";
        using (SqlCommand cmd = new SqlCommand(query, sqlco))
        {
            // 传入参数,自动处理特殊字符转义
            cmd.Parameters.AddWithValue("@username", username.Text.Trim());
            cmd.Parameters.AddWithValue("@password", password.Text.Trim());
            cmd.Parameters.AddWithValue("@usertype", user_type.SelectedItem.ToString());

            SqlDataAdapter sda = new SqlDataAdapter(cmd);
            DataTable dt = new DataTable();
            sda.Fill(dt);

            if (dt.Rows.Count > 0)
            {
                string loginUserType = dt.Rows[0]["usertype"].ToString();
                MessageBox.Show("You are logged in as " + loginUserType);

                // 根据用户类型跳转对应页面
                switch (user_type.SelectedIndex)
                {
                    case 0:
                        new customer().Show();
                        break;
                    case 1:
                        new Staff().Show();
                        break;
                    case 2:
                        new Trainer().Show();
                        break;
                }
                this.Hide();
            }
            else
            {
                MessageBox.Show("账号、密码或用户类型错误,请重新输入", "登录失败", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
        }
    }
    catch (Exception ex)
    {
        // 调试阶段可输出ex.Message排查具体错误,生产环境可隐藏详细报错
        MessageBox.Show("登录出错:" + ex.Message, "错误", MessageBoxButtons.OK, MessageBoxIcon.Error);
    }
    finally
    {
        sqlco.Close();
    }
}

2. 数据写入逻辑修复

新增用户时,INSERT语句必须加入usertype字段的参数赋值,示例写法:

string insertSql = "INSERT INTO log_data (username,password,usertype) VALUES (@username,@password,@usertype)";
// 按参数化查询的方式传入三个字段的值即可,确保usertype的值和数据库存储的格式完全一致

内容的提问来源于stack exchange,提问作者Judel Dobbs

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.24 02:54:07