Im trying to pass the filepath into my ProfileViewModel but it seems to stay Null even thought the other values are filled.
I have tried debugging it but cant seem to find where its going wrong.
My view
#using (Html.BeginForm("EditProfile", "Profile", FormMethod.Post))
{
#Html.AntiForgeryToken()
#Html.LabelFor(model => model.Photo, htmlAttributes: new { #class = "control-label col-md-2" })
<input asp-for="Photo" type="file"/><br />
<div class="form-group">
<div class="col-md-offset-2 col-md-10">
<input type="submit" value="Save" class="btn btn-default" />
</div>
</div>
</div>
my controller
public IActionResult profile()
{
return View();
}
private readonly IHostingEnvironment he;
public ProfileController(IHostingEnvironment e)
{
he = e;
}
[HttpPost]
public ActionResult EditProfile(ProfileViewModel profile)
{
string ID = Request.Cookies["UserID"];
if (ModelState.IsValid)
{
var Photo = profile.Photo;
var FileName = Path.Combine(he.WebRootPath, Path.GetFileName(Photo.FileName));
if (logicprofile.logicEditProfile(profile.BIO, profile.Sex, profile.Preffered, FileName, Convert.ToInt32(ID)) == true)
{
profile.Photo.CopyTo(new FileStream(FileName, FileMode.Create));
ViewBag.Message = "Profile Updated";
return View("profile", profile);
}
else
{
ViewBag.Message = "Something went wrong";
return View("profile", profile);
}
}
else
{
return View("profile", profile);
}
}
ViewModel
[DisplayName("A picture of you!")]
public IFormFile Photo { get; set; }
I expect my pictures to be saved in a folder and the path to a database so I can use them as profile pictures.
You should use enctype in form for passing file type data.
#using (Html.BeginForm("EditProfile", "Profile", FormMethod.Post, new { enctype = "multipart/form-data" }))
Related
I cannot add image in about -> post method. This is my code please help.
This is my controller section:
ActionResult Register(Admin adm)
{
string fileName = Path.GetFileNameWithoutExtension(adm.ImageFile.FileName);
string exe = Path.GetExtension(adm.ImageFile.FileName);
fileName = fileName + DateTime.Now.ToString("yymmssfff") + exe;[enter image description here][1]
adm.Adm_Image_path = "~/Image/" + fileName;
fileName = Path.Combine(Server.MapPath("~/Image/"), fileName);
adm.ImageFile.SaveAs(fileName);
// Upload_Image(adm.ImageFile);
if (ModelState.IsValid)
{
if (adm.Adm_Password == adm.Adm_Confirm_Password)
{
adm.Adm_Type = "Admin";
db.admin.Add(adm);
db.SaveChanges();
return RedirectToAction("Login", "Home");
}
}
return View();
}
View section here
<div class="form-group">
#Html.LabelFor(x => x.Adm_Image_path, new { #class = "control-label col-md-2" })
<div class="col-md-10">
<input type="file" name="ImageFile" id="ImageFile" value="ImageFile" required />
#Html.ValidationMessageFor(x => x.Adm_Image_path, "", new { #class="text-danger"})
</div>
</div>
<input type="submit" value="Save" class="btn btn-default" />`
I cannot upload the image in the specific section.
Use Below code.
Model Class:
public class Admin
{
public string ImagePath { get; set; }
public HttpPostedFileBase ImageFile { get; set; }
}
Controller:
public ActionResult Register()
{
return View();
}
[HttpPost]
public ActionResult Register(Admin adm)
{
string fileName = Path.GetFileNameWithoutExtension(adm.ImageFile.FileName);
string exe = Path.GetExtension(adm.ImageFile.FileName);
fileName = fileName + DateTime.Now.ToString("yymmssfff") + exe;
adm.ImagePath = "~/Images/" + fileName;
fileName = Path.Combine(Server.MapPath("~/Images/"), fileName);
adm.ImageFile.SaveAs(fileName);
//Upload_Image(adm.ImageFile);
if (ModelState.IsValid)
{
//if (adm.Adm_Password == adm.Adm_Confirm_Password)
//{
// adm.Adm_Type = "Admin";
// db.admin.Add(adm);
// db.SaveChanges();
// return RedirectToAction("Login", "Home");
//}
return View();
}
else
{
return View();
}
}
View:
#model testProject.Models.Admin
#{
ViewBag.Title = "Register";
Layout = "~/Views/Shared/_Layout.cshtml";
}
<h2>Register</h2>
#using (Html.BeginForm("Register", "Signup", FormMethod.Post, new { enctype = "multipart/form-data" }))
{
<div class="form-group">
#Html.LabelFor(x => x.ImagePath, new { #class = "control-label col-md-2" })
<div class="col-md-10">
<input type="file" name="ImageFile" id="ImageFile" value="ImageFile" required />
#Html.ValidationMessageFor(x => x.ImagePath, "", new { #class = "text-danger" })
</div>
</div>
<input type="submit" value="Save" class="btn btn-default" />
}
Hope this will surely help you.
I have a problem with uploading files to my database, PostedFile is always a null.
Controller:
public ActionResult Create(Sound sound)
{
if (sound.PostedFile != null && sound.PostedFile.ContentLength > 0)
{
MemoryStream temp = new MemoryStream();
sound.PostedFile.InputStream.CopyTo(temp);
sound.Data = temp.ToArray();
db.SoundsTable.Add(sound);
db.SaveChanges();
ViewBag.Message = "DONE";
}
else
{
ViewBag.Message = "ERR";
}
return RedirectToAction("Index");
}
Model:
public class Sounds : DbContext
{
public Sounds()
: base("name=Sounds")
{
}
public virtual DbSet<Sound> SoundsTable { get; set; }
}
public class Sound
{
public int Id { get; set; }
public string Name { get; set; }
[MaxLength(8388608)]
public byte[] Data { get; set; }
[NotMapped]
[Required(ErrorMessage = "Please select file.")]
public HttpPostedFileBase PostedFile { get; set; }
}
View:
#model WebApp.Models.Sound
#{
ViewBag.Title = "Create";
}
<h2>Create</h2>
#using (Html.BeginForm())
{
<div class="form-horizontal">
<h4>Sound</h4>
#Html.EditorFor(model => model.Name, new { htmlAttributes = new { #class = "form-control" } })<br />
#Html.TextBoxFor(model => model.PostedFile, new { type = "file" })<br />
#Html.ValidationMessageFor(model => model.PostedFile, "", new { #class = "error" })<br />
<input type="submit" value="UPLOAD" />
<br />
#ViewBag.Message
</div>
<div>
#Html.ActionLink("Back to List", "Index")
</div>
}
Everything works fine with Name value being send from View to Controller. But I cant get working sending PostedFile value, as it is always a null.
enctype = multipart/form-data is indeed required
#using (Html.BeginForm("Create", //Your action
"Test", //Your controller
FormMethod.Post,
new { enctype = "multipart/form-data"}))
{
<div class="form-horizontal">
<h4>Sound</h4>
#Html.EditorFor(model => model.Name, new { htmlAttributes = new { #class = "form-control" } })<br />
#Html.TextBoxFor(model => model.PostedFile, new { type = "file" })<br />
#Html.ValidationMessageFor(model => model.PostedFile, "", new { #class = "error" })<br />
<input type="submit" value="UPLOAD" />
<br />
#ViewBag.Message
</div>
<div>
#Html.ActionLink("Back to List", "Index")
</div>
}
try this:
#using (Html.BeginForm("Create", "Test", FormMethod.Post, new { enctype = "multipart/form-data" }))
{
//other controls here
<input type="file" name="postedFile" id="fileInputId" />
//submit button here }
Then your controller:
[HttpPost]
public ActionResult Create(Sound model, HttpPostedFileBase postedFile)
{
//do stuff
}
Make sure that the name in input file element is the same as the parameter name in the controller.
I search much but I am not lucky to find the solution, My aim is save a model depending on the button that the user chooses.
I have two inputs of type button, which should each invoke a different method from the controller at the moment of press click. You must have an account. All this happens in the same view for only a model.
This is my view:
#model WebShop.Models.Product
#{
ViewBag.Title = "Create";
}
<h2>Crear</h2>
#using Newtonsoft.Json
#using (Html.BeginForm(new { #id = "create" }))
{
#Html.AntiForgeryToken()
<div class="form-horizontal">
<h4>Producto</h4>
<hr />
#Html.ValidationSummary(true, "", new { #class = "text-danger" })
<div class="form-group">
#Html.LabelFor(model => model.ProductNumber, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.ProductNumber, new { htmlAttributes = new { #class = "form-control" } })
#Html.ValidationMessageFor(model => model.ProductNumber, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.ProductTitle, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.ProductTitle, new { htmlAttributes = new { #class = "form-control" } })
#Html.ValidationMessageFor(model => model.ProductTitle, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
<div class="col-md-offset-2 col-md-10">
<input type="submit" value="Crear" class="btn btn-default" />
<input type="submit" value="Crear en memoria" class="btn btn-default" id="InMemory" />
</div>
</div>
</div>
}
And these are my methods:
[HttpPost]
public ActionResult Create(Product product)
{
try
{
List<Product> listProducts = new List<Product>();
if (ModelState.IsValid)
{
db.Products.Add(product);
db.SaveChanges();
TempData["list"] = db.Products.ToList();
return RedirectToAction("Index");
}
return View(product);
}
catch
{
return View(product);
}
}
[HttpPost]
public ActionResult CreateInMemory(Product product)
{
try
{
if (ModelState.IsValid)
{
using (SQLiteConnection con = new SQLiteConnection("Data Source=:memory:"))
{
con.Open();
if (string.IsNullOrEmpty(result.ToString()))
{
string query = #"CREATE TABLE Products
(ProductID integer primary key,
ProductNumber integer,
ProductTitle varchar(100));";
using (SQLiteCommand comd = new SQLiteCommand(query,con))
{
comd.ExecuteNonQuery();
TempData["list"] = saveListProduct(product, con);
}
}
else
{
TempData["list"] = saveListProduct(product, con);
}
con.Close();
return RedirectToAction("Index");
}
}
return View(product);
}
catch(Exception e)
{
string message = e.Message;
return View("Index");
}
}
In order that they are in context, I want to guard the model in the database and in memory with SQLite, and any suggestion is welcome.
I think you can use formaction attribute (HTML5) for this. Try the following. Hope to help, my friend :))
<input type="submit" name="response" value="Create" formaction=#Url.Action("Create") formmethod="post" class="btn btn-default" />
<input type="submit" name="response" value="CreateInMemory" formaction=#Url.Action("CreateInMemory") formmethod="post" class="btn btn-default" />
Note: It just can be implemented in HTML5.
consider the following sample , how to send a model to different methods of same controller:
public class HomeController : Controller
{
public ActionResult Index()
{
return View();
}
[HttpPost]
public ActionResult Method1(BooModel model)
{
...
}
[HttpPost]
public ActionResult Method2(BooModel model)
{
...
}
}
public class BooModel
{
public int Id { get; set; }
public string Name { get; set; }
}
#model WebApi.Controllers.BooModel
#using (Html.BeginForm())
{
#Html.TextBoxFor(x=>x.Id)
#Html.TextBoxFor(x=>x.Name)
<input type="submit" value="Method1" onclick='this.form.action="#Url.Action("Method1", "Home", null, this.Request.Url.Scheme)"' />
<input type="submit" value="Method2" onclick='this.form.action="#Url.Action("Method2", "Home", null, this.Request.Url.Scheme)"' />
}
For a jQuery solution change your <input> elements into plain <button> ones and use the below jQuery in your $(document).ready() function :
$("#btnCreate").on('click', function () {
$.ajax({
url: '#Url.Action("Create", "Controller", new { area="Area"})',
type: "POST",
data: $('form').serialize(),
success: function () {
//Go to new location etc
}
})
})
$("#btnCreateInMemory").on('click', function () {
$.ajax({
url: '#Url.Action("CreateInMemory", "Controller", new { area="Area"})',
type: "POST",
data: $('form').serialize(),
success: function () {
//Go to new location etc
}
})
})
I have tried my best however HttpPostedFileBase filee is always null
Controller Action
public ActionResult UploadFile(HttpPostedFileBase filee)
{
try
{
if (filee.ContentLength > 0)
{
string _FileName = Path.GetFileName(filee.FileName);
string _path = Path.Combine(Server.MapPath("~/UploadedFiles"), _FileName);
filee.SaveAs(_path);
}
ViewBag.Message = "File Uploaded Successfully!!";
return View();
}
catch
{
ViewBag.Message = "File upload failed!!";
return View();
}
}
Razor View
#{
ViewBag.Title = "UploadFile";
}
<h2>UploadFile</h2>
#using (Html.BeginForm("UploadFile", "Home", FormMethod.Post, new { enctype = "multipart/form-data" }))
{
<div>
#Html.TextBox("file", "", new { type = "file" }) <br />
<input type="submit" value="Upload" />
#ViewBag.Message
</div>
}
Either change the name of parameter in public ActionResult UploadFile(HttpPostedFileBase filee) to public ActionResult UploadFile(HttpPostedFileBase file) or change the input name #Html.TextBox("file", "", new { type = "file" }) to #Html.TextBox("filee", "", new { type = "file" }).
You have to use same name of yor input field as your HttpPostedFileBase object name while you are working on loosly type view !
Example :
#{
ViewBag.Title = "UploadFile";
}
<h2>UploadFile</h2>
#using (Html.BeginForm("UploadFile", "Home", FormMethod.Post, new { enctype = "multipart/form-data" }))
{
<div>
#Html.TextBox("filee", "", new { type = "file" }) <br />
<input type="submit" value="Upload" />
#ViewBag.Message
</div>
}
Or If you don't want to use same names ?
you just have to use a tightly coupled view type view
Tightly
Example:
#model PROJECTNAME.Models.MODELNAME
#{
ViewBag.Title = "UploadFile";
}
<h2>UploadFile</h2>
#using (Html.BeginForm("UploadFile", "Home", FormMethod.Post, new { enctype = "multipart/form-data" }))
{
<div>
#Html.TextBox(model => model.YOURCOLUMNNAME , "", new { type = "file" }) <br />
<input type="submit" value="Upload" />
#ViewBag.Message
</div>
}
I am setting up a view and ViewModel to accept some data and a File. But when I look at the returned model, I do not see a file.
Here's my ViewModel:
public class ResourceReviewViewModel
{
public Guid ResourceReviewId { get; set; }
//....
[Display(Name="Review Document File")]
public HttpPostedFileBase ReviewFile { get; set; }
}
My view:
My controller to handle the submit:
[HttpPost]
[ValidateAntiForgeryToken]
public virtual ActionResult ResourceReview(ResourceReviewViewModel model)
{
//...
return View(model); // model.ReviewFile is null
}
#model PublicationSystem.ViewModels.ResourceReviewViewModel
#using (Html.BeginForm())
{
#Html.AntiForgeryToken()
<div class="form-horizontal">
<h4>Submit Your Review</h4>
<hr/>
#Html.HiddenFor(model => model.RequestReviewId, new { htmlAttributes = new { #class = "form-control" } })
<div class="form-group">
#Html.LabelFor(model => model.ReviewFile, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
<input type="file" id="ReviewFile" name="ReviewFile" value="ActionHandlerForForm" />
</div>
</div>
<div class="form-group">
<div class="col-md-offset-2 col-md-10">
<input type="submit" value="Submit" class="btn btn-default" />
</div>
</div>
</div>
}
The model comes back with values, but the file property is NULL. The HTML for the Input I copied from another page, so I'm not sure I need value="ActionHandlerForForm".
Yes, it's possible. I think in your example you're just missing multipart/form-data
Try this (replace "Index" and "Home" to the View/Controller you have):
#using (Html.BeginForm("Index", "Home", FormMethod.Post, new { enctype = "multipart/form-data" }))
{
...
}