Ok, I am sure this already has an answer somewhere, but I can honestly tell you that everything I have tried, has failed. Here is my current configuration:
Shared _Layout.cshtml (below the footer)
<script src="~/lib/jquery/dist/jquery.min.js"></script>
<script src="~/lib/bootstrap/dist/js/bootstrap.bundle.min.js"></script>
<script src="~/js/site.js" asp-append-version="true"></script>
<script src="https://unpkg.com/dropzone@5/dist/min/dropzone.min.js"></script>
@await RenderSectionAsync("Scripts", required: false)
Images View
@model NewProductVM
<form id="form2" method="post" enctype="multipart/form-data" data-parsley-validate class="form-horizontal form-label-left">
<div class="form-group">
<label class="control-label col-md-2" for="first-name">
<span class="required">*</span>
</label>
<input type="hidden" value="@Model.Id" />
<div class="col-md-6" id="dropzone">
<div action="UploadFiles" class="dropzone" id="uploader">
Drop files here or click to upload.<br>
</div>
</div>
</div>
</form>
Products Controller
[HttpPost]
public async Task<IActionResult> UploadFiles(string Id)
{
bool bSuccess = true;
_ConnectionString = _Configuration.GetConnectionString("StorageConnectionString");
_ContainerName = _Configuration.GetValue<string>("StorageContainerName");
string uploads = Path.Combine(_hostingEnvironment.ContentRootPath, "Uploads");
if (!Directory.Exists(uploads))
Directory.CreateDirectory(uploads);
foreach (var iFormFile in Request.Form.Files)
{
if (iFormFile.Length > 0)
{
if (StorageHelper.IsImage(iFormFile))
{
var filePath = Path.Combine(uploads, iFormFile.FileName);
using (var stream = new FileStream(filePath, FileMode.Create))
{
await iFormFile.CopyToAsync(stream);
}
bSuccess = await StorageHelper.UploadFileToStorage(iFormFile, filePath, _ConnectionString, _ContainerName);
System.IO.File.Delete(filePath);
ProductImage productImage = new ProductImage
{
ProductId = int.Parse(Id),
ImageURL = $"{_Configuration.GetValue<string>("StorageContainerURL")}/{iFormFile.FileName}"
};
await _imageService.AddNewImageAsync(productImage);
}
}
}
return RedirectToAction("Index");
}
I would really like to pass the entire NewProductVM model to the UploadFiles method, but there are not very many properties in the view model, so I could pass each property individually.
Right now I am taking someones suggestion to create a hidden form field and add a value I want to pass to the controller as a form field, but the parameter value in the UploadFiles method is null. I have also tried using asp-route-id="@Model.Id"
. When I did that, the value of id was 0 in the controller method.
Anyone have any suggestions?
CodePudding user response:
Ok, I finally found the answer and I cannot believe how simple it was. I have been working on this for several hours. I found the answer here: https://social.msdn.microsoft.com/Forums/en-US/a87c6936-c0b5-4f47-b074-dbaf4c154cdd/id-parameter-returning-null-after-using-formdataappend-to-append-id-to-model-id-in-mvc-5?forum=aspmvc
This is what I did:
Images.cshtml
<form id="form2" method="post" enctype="multipart/form-data" data-parsley-validate class="form-horizontal form-label-left">
<div class="form-group">
<label class="control-label col-md-2" for="first-name">
<span class="required">*</span>
</label>
<div class="col-md-6" id="dropzone">
<div action="[email protected]" class="dropzone" id="uploader">
Drop files here or click to upload.<br>
</div>
</div>
</div>
</form>
ProductsController.cs
[HttpPost]
public async Task<IActionResult> UploadFiles(int Id)
{
bool bSuccess = true;
_ConnectionString = _Configuration.GetConnectionString("StorageConnectionString");
_ContainerName = _Configuration.GetValue<string>("StorageContainerName");
//int Id = int.Parse(fc["Id"]);
string uploads = Path.Combine(_hostingEnvironment.ContentRootPath, "Uploads");
if (!Directory.Exists(uploads))
Directory.CreateDirectory(uploads);
foreach (var iFormFile in Request.Form.Files)
{
if (iFormFile.Length > 0)
{
if (StorageHelper.IsImage(iFormFile))
{
var filePath = Path.Combine(uploads, iFormFile.FileName);
using (var stream = new FileStream(filePath, FileMode.Create))
{
await iFormFile.CopyToAsync(stream);
}
bSuccess = await StorageHelper.UploadFileToStorage(iFormFile, filePath, _ConnectionString, _ContainerName);
System.IO.File.Delete(filePath);
//ProductImage productImage = new ProductImage
//{
// ProductId = Id,
// ImageURL = $"{_Configuration.GetValue<string>("StorageContainerURL")}/{iFormFile.FileName}"
//};
//await _imageService.AddNewImageAsync(productImage);
}
}
}
return RedirectToAction("Index");
}
The part that really made it work was action="[email protected]"
.
So basically, I am using the action to pass the values I want to my controller method.