C#读取SQL数据库用户头像报ImageConverter转换异常解决方法
问题根因
抛出System.NotSupportedException: "ImageConverter cannot convert from System.String."的核心原因是两处逻辑错误:
- 取值目标错误:
table.Rows[0]是整行数据的DataRow对象,调用ToString()得到的是该对象的类型字符串,不是USERAVATAR字段存储的头像二进制数据; - 转换方法误用:
ImageConverter.ConvertFromString仅支持将合法的图像编码字符串转为图像对象,既无法识别你传入的DataRow字符串,也完全不适合读取数据库中二进制格式存储的头像字段。
此外原有代码还存在SQL注入风险、非托管资源未手动释放的隐患。
修复后完整代码
private void LoginBTN_Click(object sender, EventArgs e) { var loguser = AutorizeLoginBox.Text.Trim(); var passuser = AutorizePasswordBox.Text; // 改用参数化查询避免SQL注入 string querystring = "select ID, USERLOGIN, USERPASSWORD, USERAVATAR from USERTESTDB where USERLOGIN=@loguser and USERPASSWORD=@passuser"; using (SqlConnection conn = sqldb.getConnection()) { conn.Open(); using (SqlCommand command = new SqlCommand(querystring, conn)) { // 传入查询参数 command.Parameters.AddWithValue("@loguser", loguser); command.Parameters.AddWithValue("@passuser", passuser); SqlDataAdapter adapter = new SqlDataAdapter(command); DataTable table = new DataTable(); adapter.Fill(table); if (table.Rows.Count == 1) { DataRow userRow = table.Rows[0]; // 直接读取USERAVATAR字段的二进制值,强转为byte数组 byte[] avatarBytes = (byte[])userRow["USERAVATAR"]; // 用using块自动释放流资源 using (MemoryStream ms = new MemoryStream(avatarBytes)) { // 传入参数保留流生命周期,避免流释放后头像控件显示异常 Image avatar = Image.FromStream(ms, true, true); Program.programpg.avatarbox.Image = avatar; } } } } }
关键修复点说明
- 移除了错误的
ImageConverter字符串转换逻辑,直接通过列名USERAVATAR读取行中存储的二进制字节数组 - 所有数据库连接、流对象都用
using块包裹,自动释放非托管资源,避免内存泄漏 - 原SQL字符串拼接写法替换为参数化查询,彻底阻断SQL注入风险
Image.FromStream增加生命周期配置参数,避免流被提前释放导致头像显示失败
内容的提问来源于stack exchange,提问作者xXKoksMenXx
相关产品推荐
相关产品推荐

