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

如何解决MSSQL中的‘无效列名’SQL异常

搞定"Invalid Column Name"异常:别再手动拼SQL啦!

哥们,你遇到的这个问题我太熟了——直接拼接SQL字符串简直是踩坑重灾区!咱们先看看你代码里的问题,再给你彻底解决的办法。

首先说你当前报错的直接原因:你看代码里像OdaSayisi、KişiSayisi这些明显是数字类型的列,结果你把它们的值用单引号包起来了(比如'" + oda_sayisi + "'")。数据库看到这个带引号的内容,会误以为你要引用一个叫这个值的列,自然就报“无效列名”了!

而且这种手动拼字符串的写法还有更大的隐患:SQL注入。要是有人输入个带单引号的内容,直接就能把你的SQL搞崩,甚至篡改数据库数据,这可太危险了。

正确的姿势:用参数化查询

直接上修改后的代码,你照着改就行:

// 用using自动管理连接和命令对象,不用手动关连接
using (SqlConnection con = new SqlConnection("这里填你的数据库连接字符串"))
{
    con.Open();
    // 把SQL写成带参数占位符的形式,参数名用@开头
    string sql = @"INSERT INTO rezervasyon 
                  (Ad,Soyad,TelefonNo,OdaSayisi,KişiSayisi,Ucret,Acıklama,GirisTarihi,CikisTarihi,KayitTarihi) 
                  VALUES 
                  (@Ad, @Soyad, @TelefonNo, @OdaSayisi, @KisiSayisi, @Ucret, @Aciklama, @GirisTarihi, @CikisTarihi, @KayitTarihi)";
    
    using (SqlCommand cmd = new SqlCommand(sql, con))
    {
        // 逐个添加参数,不用管引号和类型,数据库驱动会自动处理
        cmd.Parameters.AddWithValue("@Ad", isim);
        cmd.Parameters.AddWithValue("@Soyad", soyisim);
        cmd.Parameters.AddWithValue("@TelefonNo", telefon);
        // 数字类型直接传数值,不用加引号!
        cmd.Parameters.AddWithValue("@OdaSayisi", oda_sayisi);
        cmd.Parameters.AddWithValue("@KisiSayisi", kisi_sayisi);
        cmd.Parameters.AddWithValue("@Ucret", ucret);
        cmd.Parameters.AddWithValue("@Aciklama", aciklama);
        // 日期直接传DateTime对象,不用转成字符串格式
        cmd.Parameters.AddWithValue("@GirisTarihi", giris_tar);
        cmd.Parameters.AddWithValue("@CikisTarihi", cikis_tar);
        cmd.Parameters.AddWithValue("@KayitTarihi", current_tarih);
        
        cmd.ExecuteNonQuery();
    }
}

要是你真的需要动态传列名怎么办?

你说你想在运行时传入列名,那可不能直接把列名拼进SQL(照样会有注入风险),得先做个白名单校验:

// 先定义所有允许的列名,确保只有合法的列才能被使用
var allowedColumns = new HashSet<string> { 
    "Ad", "Soyad", "TelefonNo", "OdaSayisi", 
    "KişiSayisi", "Ucret", "Acıklama", 
    "GirisTarihi", "CikisTarihi", "KayitTarihi" 
};

// 假设你动态获取的列名列表是selectedColumns
foreach (var col in selectedColumns)
{
    if (!allowedColumns.Contains(col))
    {
        throw new ArgumentException($"别瞎搞!无效的列名:{col}");
    }
}

// 校验通过后再拼接列名和参数
string columns = string.Join(",", selectedColumns);
string parameters = string.Join(",", selectedColumns.Select(col => $"@{col}"));

string sql = $"INSERT INTO rezervasyon ({columns}) VALUES ({parameters})";
// 后面再对应添加参数就行,和上面的参数化写法一样

这样既实现了动态列名的需求,又不会踩注入和列名错误的坑。

总结一下:你现在的报错就是因为手动拼字符串时给数字加了引号,数据库认错了东西。改用参数化查询不仅能解决这个问题,还能让你的代码更安全、更易维护,一举多得!

内容的提问来源于stack exchange,提问作者David Hayter

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.29 08:11:37