在 MVC4 中,如何将属于域模型一部分的文件(图像)上传到 SQL Server?

2023-11-26

我对 MVC 比较陌生,而且从来没有处理过将文件(特别是图像)上传到 SQL Server 数据库的问题。老实说,我不知道自己在这里做什么。

这是我到目前为止所拥有的 - 这是我的域模型(注意HttpPostedFileBase在我的模型中 - 这就是我要上传的内容):

public class Profile
{
    [Key]
    public int Id { get; set; }

    [Required(ErrorMessage="Years of service is required")]
    [DisplayName("Years Service:")]
    public int YearsService { get; set; }

    [DataType(DataType.MultilineText)]
    [DisplayName("Notable Achivements:")]
    public string NotableAchivements { get; set; }

    [Required(ErrorMessage = "Technical skills are required")]
    [DataType(DataType.MultilineText)]
    [DisplayName("Technical Skills:")]
    public string TechnicalSkills { get; set; }

    [DisplayName("Upload Image: ")]
    public HttpPostedFileBase Photo { get; set; }

    public string CreatedBy { get; set; }
    public DateTime CreatedDate { get; set; }
    public string ModifiedBy { get; set; }
    public DateTime ModifiedDate { get; set; }
}

这是我的观点:

@using (Html.BeginForm("Create", "Profiles", FormMethod.Post, new { enctype = "multipart/form-data" }))
{
<div class="editor-label">
    @Html.LabelFor(model => model.YearsService)
</div>
<div class="editor-field">
    @Html.EditorFor(model => model.YearsService)
    @Html.ValidationMessageFor(model => model.YearsService)
</div>

<div class="editor-label">
    @Html.LabelFor(model => model.NotableAchivements)
</div>
<div class="editor-field">
    @Html.EditorFor(model => model.NotableAchivements)
    @Html.ValidationMessageFor(model => model.NotableAchivements)
</div>

<div class="editor-label">
    @Html.LabelFor(model => model.TechnicalSkills)
</div>
<div class="editor-field">
    @Html.EditorFor(model => model.TechnicalSkills)
    @Html.ValidationMessageFor(model => model.TechnicalSkills)
</div>

<input type="file" name="photo" />
<input type="submit" name="Submit" id="Submit" value="Upload" />
}

我希望有一些明显的事情表明我做错了。任何人都可以提供有关如何将简单文件上传到 SQL Server 数据库的建议吗?


首先,不要将图像保存到数据库中。网上有无数的“指南”建议在 MSSQL 中使用字节数组或“图像”类型。数据库不适用于二进制数据存储。当然,它们会容纳二进制存储,但只是因为你can用 AR-15 搬起石头砸自己的脚,并不意味着你should.

相反,将图像存储在它所属的位置:文件系统。然后,只需引用它在数据库中的路径即可。

现在,处理这一切的最简单方法是使用视图模型。如果您还没有使用视图模型,那么现在是开始的好时机。一般来说,您不想将实际的数据库支持的模型直接发送到视图。在表单中,恶意用户可能会进行各种令人讨厌的数据篡改,即使在简单的视图中,您通常也会传递比他们需要的更多的数据。

因此,第一步是创建一个视图模型Profile。通常将其命名为ProfileViewModel or ProfileVM。然后,在此模型上,您只需添加以下属性Profile您将在视图中进行编辑或以其他方式与之交互。然后,您实际上可以添加其他属性not也可以在数据库支持的模型上用于特殊用途的视图函数,例如SelectList与使用DropDownListFor,所以你实际上可以保持强类型而不是诉诸于ViewBag对于这样的事情。

对于您的图像,您需要两个字段。我通常会选择以下内容:

public string Photo { get; set; }
public HttpPostedFileBase PhotoUpload { get; set; }

在您的编辑/创建视图中,您将仅引用PhotoUpload,这将是您的文件上传字段(尽管您可以使用Photo如果您愿意,也可以显示当前设置的图像)。

@Html.TextBoxFor(m => m.PhotoUpload, new { type = "file" })

然后,要在控制器操作中处理发布的文件:

if (model.PhotoUpload.ContentLength > 0) {
    // A file was uploaded
    var fileName = Path.GetFileName(model.PhotoUpload.FileName);
    var path = Path.Combine(Server.MapPath(uploadPath), fileName);
    model.PhotoUpload.SaveAs(path);
    model.Photo = uploadPath + fileName;
}

Where uploadPath应该是您要存储上传图像的主目录相对路径,即类似~/uploads/profile/photos。确保在尝试发布表单之前创建目录,或者添加一些逻辑来检查目录是否存在并在必要时创建它(但这需要对服务器具有更高的信任,因此在大多数安全性较差的环境中并不理想一个大问题)。

然后,您只需要某种方法将视图模型中的数据映射回数据库支持的模型。您可以手动执行此操作,但使用 AutoMapper 之类的工具将使您的生活变得更加轻松。使用自动映射器(其中model是一个实例ProfileViewModel):

var profile = AutoMapper.Mapper.Map<Profile>(model);

或者,由于使用配置文件之类的东西,编辑现有模型比创建新模型更常见:

var profile = db.Profiles.Find(userId);
...
Automapper.Mapper.Map(model, profile);

那么,在您的实际模型上,您将不会有PhotoUpload财产,只是Photo。您设置的路径Photo视图模型上的 将会映射到模型的同名属性上,因此剩下的就是保存更新后的配置文件。

另外,由于您正在谈论上传照片,因此您可能需要添加一些内容类型检查,以确保用户上传的是图像,而不是诸如 Word 文档之类的愚蠢内容。在你之前if (ModelState.IsValid)检查,添加:

var validTypes = new[] { "image/jpeg", "image/pjpeg", "image/png", "image/gif" };
if (!validTypes.Contains(model.PhotoUpload.ContentType))
{
    ModelState.AddModelError("PhotoUpload", "Please upload either a JPG, GIF, or PNG image.");
}

根据需要更改 MIME 类型以匹配您的业务案例。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

在 MVC4 中,如何将属于域模型一部分的文件(图像)上传到 SQL Server? 的相关文章

随机推荐

  • 在 bash 中回显打印 -e

    我已经得到了在 Bash 中创建的脚本 我正在使用的功能之一是echo我正在使用 e解释标志 反斜杠转义 我有一个以彩色打印文本的脚本 但是当它回显将要以彩色显示的消息时 它也会打印 e带有消息的标记 此处为例 NC 033 31 0m n
  • 如何取消或停止 Google App Engine Cron 作业

    我将一个使用 CRON 作业的应用程序部署到我的 Google App Engine 我跟着this教程 它工作正常 我可以在我的 GAE 控制台中确认它 在我的 Stackdriver 日志中 我还可以看到 CRON 作业正在运行 但我对
  • 尝试在 Lumen 中重置密码

    我正在尝试在 Lumen 中实现密码重置功能 但未能成功 Lumen 可以访问 Laravel 之类的东西密码经纪商 and 密码管理器但我无法使用它并成功 有没有什么解决办法呢 我昨晚才真正弄清楚这一点 并写了一篇关于它的博客 http
  • 布局内的 OpenGL 视图

    如何设置包含 OpenGL 视图的 xml 布局 我现在所做的就是使用 setContentView 将 OpenGL 视图设置为唯一的视图 但我想创建一个包含 OpenGL 视图的 xml 布局 假设我主要想要 OpenGL 视图 并在底
  • 当用户在 jquery 中按 Enter 键时将
    添加到文本框

    我想添加 br 当用户单击输入按钮时 换行符 到文本框 我怎样才能在jquery中实现它onkeyup事件 可以给我展示一个示例或任何实现它的好网站吗 谢谢 从这里复制的文本区域中的插入符位置 从头开始的字符数 See DEMO
  • AJAX GET 请求中查询字符串的最大长度?

    执行 AJAX GET 请求时 查询字符串的最大长度是否存在 更具体地说 我正在使用图像进行跨域 AJAX img new Image img src http www otherdomain com something gif long
  • 获取提供给泛型方法的泛型参数类型和值

    如何获取提供给封闭 构造泛型方法的参数值 已经有一段时间没有接触Reflection了 所有这些都曾经是我的 嗯 无论如何 class Program static void Main string args new ConcreteFoo
  • JVM堆参数

    在阅读了有关该主题的已经提出的问题和大量谷歌搜索后 我仍然无法清楚地了解 Xms option 我的问题是 有什么区别java Xms 512m Xmx 512m and java Xms 64m Xmx 512m 现在我有以下答案 唯一的
  • Chai 断言测试对象结构是否至少包含其他对象结构

    我使用 Mocha 进行单元测试 使用 Chai 进行断言 我想找到一个易于使用的解决方案来检查对象是否具有比较对象中定义的结构和属性 但我不需要对象完全相等 被测对象应包含at least我的测试对象中的所有属性 但它也可能包含当时未测试
  • 如何将工具栏添加到 NSTableView 的底部?

    看看下面的图片 我怎样才能将这种栏添加到我自己的NSTableViews中 其他用途在网络首选项应用程序中 使这项工作成功的秘诀是什么 我不认为有什么 魔术 这是你必须自己实现的事情 看起来像是一群Gradient style NSButt
  • 同时具有接口和实现的 Golang 泛型

    我正在尝试编写以下函数 func Fill X any slice X for i range slice slice i new X xs make int 10 fill with nils Fill xs now fill with
  • 如何在 JavaScript 中创建一个索引从 1 开始的数组?

    默认情况下 每个 JavaScript 数组的索引从 0 开始 我想创建一个索引从 1 开始的数组 我知道 一定很微不足道 感谢您的帮助 这并不是一件小事 不可能 您能做的最好的事情就是使用从 1 开始的数字属性创建一个对象 但这不是同一件
  • 抽象属性(不是属性)?

    定义抽象实例属性而不是属性的最佳实践是什么 我想写一些类似的东西 class AbstractFoo metaclass ABCMeta property abstractmethod def bar self pass class Foo
  • Dropzone 图片上传选项不起作用:(

    我正在尝试构建拖放图像上传 但拖放区选项不起作用 我不知道我是否以正确的方式进行操作 我很想设置以下选项 只上传一个文件 multiupload参数 可以删除该文件 addremovelink 最大文件大小为 2mb maxfilesize
  • 如何将 Console.WriteLine 输出保存到文本文件

    我有一个程序可以将各种结果输出到命令行控制台上 如何使用 a 将输出保存到文本文件StreamReader或其他技术 System Collections Generic IEnumerable
  • 运行CMD命令不显示?

    我已经创建了一个进程来在 CMD 中运行命令 var process Process Start CMD exe c apktool d app apk process WaitForExit 如何运行此命令而不显示实际的 CMD 窗口 您
  • 为什么将列表转换为集合比仅使用列表计算列表差异更快?

    比如说 我想计算两个列表的差异C A B A 1 2 3 4 5 6 7 8 9 B 1 3 5 8 9 C 2 4 6 7 Result A and B都用唯一的整数排序 不确定是否有办法告诉Python列表的这个属性 我需要保留元素的顺
  • 提交带有包含“???”的字符串的 jQuery.ajax 数据它将值更改为“jQuery19107363727174233645_1373301489648?”

    页面端 JavaScript var model NumberOfCPUs 2 NumberOfCores 4 OSType Linux OSVersion var id 0 var success false send to server
  • Jackson:生成带有引用的模式

    当使用 Jackson 的 JSON 模式模块时 我不想在遇到模型类时停止序列化完整的图表 而是使用类名插入另一个模式的 ref 您能引导我到 jackson module jsonSchema 源代码中的正确位置来开始修补吗 下面是一些代
  • 在 MVC4 中,如何将属于域模型一部分的文件(图像)上传到 SQL Server?

    我对 MVC 比较陌生 而且从来没有处理过将文件 特别是图像 上传到 SQL Server 数据库的问题 老实说 我不知道自己在这里做什么 这是我到目前为止所拥有的 这是我的域模型 注意HttpPostedFileBase在我的模型中 这就