如何在ASP.NET MVC中验证失败后保持输入类型=文件字段值?

时间:2009-06-09 02:47:44

标签: asp.net-mvc forms

我在我制作的MVC应用程序中有一个简单的表单。它包含一个文件字段,因此用户可以上传图像。一切都很好。

问题是,如果表单提交未通过验证,则文件字段的内容将丢失(其他字段仍会填充,例如HtmlHelpers!)。 如何在验证失败后保留文件字段?

TIA!

7 个答案:

答案 0 :(得分:57)

由于安全风险,浏览器以这种方式设计。在HTML源代码中或通过Javascript设置文件输入框的值是不可能的。否则,恶意脚本可能会在没有用户注意的情况下窃取某些私人文件。

关于这个主题有an interesting information

答案 1 :(得分:2)

据我所知,您无法设置HTML文件输入框的值。 我建议将文件输入框与标签或文本框耦合。

然后,您可以使用文件输入框中的值填充它,以便稍后重新提交。

答案 2 :(得分:1)

有基于Flash的文件上传器。尝试其中一个。如果不支持flash和java脚本,它们中的一些甚至会回退到常规文件输入框。我建议寻找jQuery插件。

答案 3 :(得分:1)

如果文件不是太大,你可以将它作为基础64并将其用作隐藏字段的值。

答案 4 :(得分:1)

我建议事先通过ajax进行验证并进行部分页面更新。在这种情况下,您不会丢失文件。

答案 5 :(得分:0)

您无法设置HTML文件输入框的值。解决方法是,在验证后输出表单时,将文件上传框替换为隐藏的输入字段。

提交时,使用文件输入框中的值填充隐藏字段(稍后重新提交)。请记住,任何时候都要存在文件上传或隐藏字段名称(不是两者):

注意:以下代码仅适用于插图/解释。将其替换为与您使用的语言相适应的代码。

<?php /* You may need to sanitize the value of $_POST['file_upload']; 
* this is just a start */
if(isset($_POST['file_upload']) && !empty($_POST['file_upload'])){ ?>
<input type="hidden" name="file_upload" value="<?php print($_POST['file_upload']); ?>" />
<?php } else { ?>
<input type="file" name="file_upload" />
<?php } ?>

答案 6 :(得分:0)

我不同意&#34;不可能&#34;被标记为正确答案。 如果有人仍然在寻找可能性,那么这里的工作对我有用。我正在使用MVC5。想法是使用会话变量。我从ASP.Net Form得到了这个想法。

我的模型/ ViewModel(仅限相关属性):

public partial class emp_leaves
    {
        public string fileNameOrig { get; set; }
        public byte[] fileContent { get; set; }

        public HttpPostedFileBase uploadFile { get; set; }
    }

在我的控制器(HttpPost)中: //检查

[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Edit(emp_leaves emp_leaves)
{
    if (emp_leaves.uploadFile != null && emp_leaves.uploadFile.ContentLength>0 && !string.IsNullOrEmpty(emp_leaves.uploadFile.FileName))
    {
        emp_leaves.fileNameOrig = Path.GetFileName(emp_leaves.uploadFile.FileName);
        emp_leaves.fileContent = new byte[emp_leaves.uploadFile.ContentLength];
        emp_leaves.uploadFile.InputStream.Read(emp_leaves.fileContent, 0, emp_leaves.uploadFile.ContentLength);
        Session["emp_leaves.uploadFile"] = emp_leaves.uploadFile; //saving the file in session variable here
    }
    else if (Session["emp_leaves.uploadFile"] != null)
    {//if re-submitting after a failed validation you will reach here.
        emp_leaves.uploadFile = (HttpPostedFileBase)Session["emp_leaves.uploadFile"];
        if (emp_leaves.uploadFile != null && emp_leaves.uploadFile.ContentLength>0 && !string.IsNullOrEmpty(emp_leaves.uploadFile.FileName))
        {
            emp_leaves.fileNameOrig = Path.GetFileName(emp_leaves.uploadFile.FileName);
            emp_leaves.uploadFile.InputStream.Position = 0;
            emp_leaves.fileContent = new byte[emp_leaves.uploadFile.ContentLength];
            emp_leaves.uploadFile.InputStream.Read(emp_leaves.fileContent, 0, emp_leaves.uploadFile.ContentLength);    
        }
    }
//code to save follows here...
}

最后在我的编辑视图中:在这里,我有条件地显示文件上传控件。

&#13;
&#13;
< script type = "text/javascript" >
  $("#removefile").on("click", function(e) {
    if (!confirm('Delete File?')) {
      e.preventDefault();
      return false;
    }
    $('#fileNameOrig').val('');
    //toggle visibility for concerned div
    $('#downloadlrfdiv').hide();
    $('#uploadlrfdiv').show();
    return false;
  }); <
/script>
&#13;
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.0/jquery.min.js"></script>
@model PPMSWEB.Models.emp_leaves @{ HttpPostedFileBase uploadFileSession = Session["emp_leaves.uploadFile"] == null ? null : (HttpPostedFileBase)Session["emp_leaves.uploadFile"]; } @using (Html.BeginForm(null, null, FormMethod.Post, new { enctype = "multipart/form-data"
})) { @Html.AntiForgeryToken()
<div class="row">
  @*irrelevant content removed*@
  <div id="downloadlrfdiv" @((!String.IsNullOrEmpty(Model.fileNameOrig) && (Model.uploadFile==n ull || uploadFileSession !=null)) ? "" : "style=display:none;")>
    <label>Attachment</label>
    <span>
            <strong>
                <a id="downloadlrf" href="@(uploadFileSession != null? "" : Url.Action("DownloadLRF", "emp_leaves", new { empLeaveId = Model.ID }))" class="text-primary ui-button-text-icon-primary" title="Download attached file">
                    @Model.fileNameOrig
                </a>
            </strong>
            @if (isEditable && !Model.readonlyMode)
            {
                @Html.Raw("&nbsp");
                <a id="removefile" class="btn text-danger lead">
                    <strong title="Delete File" class="glyphicon glyphicon-minus-sign">  </strong>
                </a>
            }
            </span>
  </div>
  <div id="uploadlrfdiv" @(!(!String.IsNullOrEmpty(Model.fileNameOrig) && Model.uploadFile==n ull) && !Model.readonlyMode ? "" : "style=display:none;")>
    <label>Upload File</label> @Html.TextBoxFor(model => model.uploadFile, new { @type = "file", @class = "btn btn-default", @title = "Upload file (max 300 KB)" }) @Html.ValidationMessageFor(x => x.uploadFile)
  </div>
</div>
}
&#13;
&#13;
&#13;