C# 使用ValidateFileAttribute验证图像
我有一个文件,名为:ValidateFileAttribute,用于验证图像上传的正确输入。像这样:C# 使用ValidateFileAttribute验证图像,c#,asp.net-mvc-4,visual-studio-2013,entity-framework-5,C#,Asp.net Mvc 4,Visual Studio 2013,Entity Framework 5,我有一个文件,名为:ValidateFileAttribute,用于验证图像上传的正确输入。像这样: public class ValidateFileAttribute : RequiredAttribute { public override bool IsValid(object value) { var file = value as HttpPostedFileBase; if (file ==
public class ValidateFileAttribute : RequiredAttribute
{
public override bool IsValid(object value)
{
var file = value as HttpPostedFileBase;
if (file == null)
{
return false;
}
if (file.ContentLength > 1 * 1024 * 1024)
{
return false;
}
try
{
using (var img = Image.FromStream(file.InputStream))
{
return img.RawFormat.Equals(ImageFormat.Jpeg);
}
}
catch { }
return false;
}
}
这就是模型的属性:
[DisplayName("Image")]
[ValidateFile(ErrorMessage = "Please select a PNG image smaller than 1MB")]
public byte[] Image { get; set; }
这是我的观点:
<div id="upload-choices">
<div class="editor-label">
@Html.LabelFor(m => m.Image)
@Html.ValidationMessageFor(model => model.Image)
</div>
<div class="editor-row">
@Html.ValidationSummary(true)
</div>
</div>
这就是行动方法:
[HttpPost]
public ActionResult EditPhotos(UserProfile userprofile, HttpPostedFileBase file)
{
if (file != null)
{
// extract only the fielname
var fileName = Path.GetFileName(file.FileName);
// store the file inside ~/App_Data/uploads folder
var path = Path.Combine(Server.MapPath("~/App_Data/uploads"), fileName);
file.SaveAs(path);
ModelState.Clear();
}
if (ModelState.IsValid)
{
string username = User.Identity.Name;
// Get the userprofile
UserProfile user = db.userProfiles.FirstOrDefault(u => u.UserName.Equals(username));
// Update fields
user.Image = new byte[file.ContentLength];
file.InputStream.Read(user.Image, 0, file.ContentLength);
user.ImageMimeType = file.ContentType;
db.Entry(user).State = EntityState.Modified;
try
{
db.SaveChanges();
}
catch (DbEntityValidationException e)
{
foreach (var eve in e.EntityValidationErrors)
{
Console.WriteLine("Entity of type \"{0}\" in state \"{1}\" has the following validation errors:",
eve.Entry.Entity.GetType().Name, eve.Entry.State);
foreach (var ve in eve.ValidationErrors)
{
Console.WriteLine("- Property: \"{0}\", Error: \"{1}\"",
ve.PropertyName, ve.ErrorMessage);
}
}
throw;
}
}
return RedirectToAction("Edit", routeValues: new { controller = "Account", activetab = "tabs-2" });
}
没有:[ValidateFile(ErrorMessage=“请选择小于1MB的PNG图像”)]我可以上传图像。但当然,这必须与验证有关
我现在是这样的:
public override bool IsValid(object value)
{
var ImageProfile = value as byte[];
if (ImageProfile == null)
{
return false;
}
if (ImageProfile.ContentLength > 1 * 1024 * 1024)
{
return false;
}
try
{
using (var img = Image.FromStream(ImageProfile.InputStream))
{
return img.RawFormat.Equals(ImageFormat.Jpeg);
}
}
catch { }
return false;
}
public override bool IsValid(object value)
{
var ImageProfile = value as byte[];
if (ImageProfile == null)
{
return false;
}
if (ImageProfile.Length > 1 * 1024 * 1024)
{
return false;
}
try
{
using (var binaryReader = new BinaryReader(HttpContext.Current.Request.Files[0].InputStream))
{
//return img.RawFormat.Equals(ImageFormat.Jpeg);
ImageProfile = binaryReader.ReadBytes(HttpContext.Current.Request.Files[0].ContentLength);
}
}
catch { }
return false;
}
和财产:
[DisplayName("ImageProfile")]
[ValidateFile(ErrorMessage = "Please select a PNG image smaller than 1MB")]
public byte[] ImageProfile { get; set; }
好吧,我现在有了这样的:
public override bool IsValid(object value)
{
var ImageProfile = value as byte[];
if (ImageProfile == null)
{
return false;
}
if (ImageProfile.ContentLength > 1 * 1024 * 1024)
{
return false;
}
try
{
using (var img = Image.FromStream(ImageProfile.InputStream))
{
return img.RawFormat.Equals(ImageFormat.Jpeg);
}
}
catch { }
return false;
}
public override bool IsValid(object value)
{
var ImageProfile = value as byte[];
if (ImageProfile == null)
{
return false;
}
if (ImageProfile.Length > 1 * 1024 * 1024)
{
return false;
}
try
{
using (var binaryReader = new BinaryReader(HttpContext.Current.Request.Files[0].InputStream))
{
//return img.RawFormat.Equals(ImageFormat.Jpeg);
ImageProfile = binaryReader.ReadBytes(HttpContext.Current.Request.Files[0].ContentLength);
}
}
catch { }
return false;
}
但是ImageProfile仍然为空??这怎么可能
如果我改变这一点:
[DisplayName("ImageProfile")]
[ValidateFile(ErrorMessage = "Please select a PNG image smaller than 1MB")]
public HttpPostedFileBase ImageProfile { get; set; }
那么这就不起作用了:
user.ImageProfile = new byte[file.ContentLength];
file.InputStream.Read(user.ImageProfile, 0, file.ContentLength);
在这种方法中:
[HttpPost]
//[ValidateAntiForgeryToken]
public ActionResult EditPhotos(UserProfile userprofile, HttpPostedFileBase file)
{
if (file != null)
{
// extract only the fielname
var fileName = Path.GetFileName(file.FileName);
// store the file inside ~/App_Data/uploads folder
var path = Path.Combine(Server.MapPath(@"\\Images"), fileName);
file.SaveAs(path);
ModelState.Clear();
}
if (ModelState.IsValid)
{
string username = User.Identity.Name;
// Get the userprofile
UserProfile user = db.userProfiles.FirstOrDefault(u => u.UserName.Equals(username));
// Update fields
user.ImageProfile = new byte[file.ContentLength];
file.InputStream.Read(user.ImageProfile, 0, file.ContentLength);
user.ImageMimeType = file.ContentType;
db.Entry(user).State = EntityState.Modified;
try
{
db.SaveChanges();
}
catch (DbEntityValidationException e)
{
foreach (var eve in e.EntityValidationErrors)
{
Console.WriteLine("Entity of type \"{0}\" in state \"{1}\" has the following validation errors:",
eve.Entry.Entity.GetType().Name, eve.Entry.State);
foreach (var ve in eve.ValidationErrors)
{
Console.WriteLine("- Property: \"{0}\", Error: \"{1}\"",
ve.PropertyName, ve.ErrorMessage);
}
}
throw;
}
}
return RedirectToAction("Edit", routeValues: new { controller = "Account", activetab = "tabs-2" });
}
这是:
公共操作结果GetImage(int id)
{
var image=db.userProfiles.Where(p=>p.Id==Id)
但是在这一行仍然会出现错误:var stream=newmemorystream(image.ToArray());
但是ImageProfile仍然为空??这怎么可能
我无法在您的视图中看到带有name=“ImageProfile”
的输入字段。因此,此属性为null是正常的。因此,您可以从修复以下问题开始:
<input type="file" name="ImageProfile" class="filestyle" data-buttontext="Find file">
并在验证属性中明显反映此更改:
public override bool IsValid(object value)
{
var file = value as HttpPostedFileBase;
if (file == null)
{
return false;
}
if (file.ContentLength > 1 * 1024 * 1024)
{
return false;
}
try
{
using (var img = Image.FromStream(file.InputStream))
{
return img.RawFormat.Equals(ImageFormat.Png);
}
}
catch { }
return false;
}
最后,在控制器操作中删除此文件参数,因为它不再使用:
[HttpPost]
public ActionResult EditPhotos(UserProfile userprofile)
{
...
}
也许你实际上没有上传文件。我没有看到表单元素,因此我不能说你做得是否正确。表单的内容类型应该是
多部分/表单数据
。你调试了代码吗?你的属性中的值
真的是空
?谢谢你的评论,我更新了我的PostPR您的模型上的属性是一个字节[]
,但是您的验证器试图将值强制转换为HttpPostedFileBase
,您不能这样做,值的类型需要与模型上的类型兼容,即,将验证器更改为使用字节数组。输入[type=file]
名为file
,它自动绑定到控制器中的文件
对象。没有与图像
属性关联的输入。是的,但如果我尝试此操作:var file=值为字节[];我不能做这个文件。ContentLength谢谢Darin!!谢谢你的answare。请参阅我上面的编辑你的控制器操作应该以视图模型作为参数,而不是实际的EntityFramework模型。视图模型应该使用HttpPostedFileBase,你应该在将其传递到数据库之前将其映射到EF模型中的字节[]
[HttpPost]
public ActionResult EditPhotos(UserProfile userprofile)
{
...
}