简体   繁体   English

ASP.NET CORE,查看 model 的所有字段为 null 时传递回 Z9BBF373797BF7CF7BA62C80023

[英]ASP.NET CORE, View model has all fields as null when passed back to Controller

I'm trying to get simple ASP.NET CORE web app going and I'm running into issues with allowing the user to access a file on my server via a html link.我正在尝试让简单的 ASP.NET CORE web 应用程序运行,我遇到了允许用户通过 html 链接访问我服务器上的文件的问题。 I have a model called "TestModel", a view called "TestView" and a controller called "AppController".我有一个名为“TestModel”的 model、一个名为“TestView”的视图和一个名为“AppController”的 controller。 My view allows the user to input some text in two separate fields as well as select two different files from their hard drive, it binds everything to my model and performs a POST when the user clicks a button.我的视图允许用户在两个单独的字段中输入一些文本以及 select 从他们的硬盘驱动器中输入两个不同的文件,它将所有内容绑定到我的 model 并在用户单击按钮时执行 POST。 I have verified that the model is correctly being passed back to my controller.我已验证 model 已正确传递回我的 controller。 My controller correctly saves the files to a folder in my server directory, uses a separate service to manipulate the files, and returns the model back to the view, ie when I use the debugger to inspect "return View(model)" in the Testview action the model being passed back has all it's properties populated.我的 controller 正确地将文件保存到我的服务器目录中的文件夹中,使用单独的服务来操作文件,并将 model 返回到视图,即当我使用调试器检查 Testview 中的“返回视图(模型)”时操作 model 被传回具有填充的所有属性。

The issue is that I want two links on the view to point to the files on the server so that the user can click the link and receive a prompt to download the files, but I can't seem to get it going.问题是我希望视图上的两个链接指向服务器上的文件,以便用户可以单击链接并收到下载文件的提示,但我似乎无法继续。 I am using the @Html.ActionLink() capability in razor to point to a "Download descriptions" action and pass the model to it, thinking that it would be passing the current view's model, but the model it passes has all fields as null. I am using the @Html.ActionLink() capability in razor to point to a "Download descriptions" action and pass the model to it, thinking that it would be passing the current view's model, but the model it passes has all fields as null . Any insight into what I am doing incorrectly?对我做错了什么有任何见解吗?

These are the relevant actions in my AppController:这些是我的 AppController 中的相关操作:

        [HttpPost("~/App/TestView")]
        public IActionResult TestView(TestModel Model)
        {
            if (ModelState.IsValid)
            {
                Console.WriteLine("Something was sent back from the TestView page");
                Model.OnPostAsync();
                var x = _descLogicService.Convert(Model);
            }

            return View(Model);
        }

        public IActionResult DownloadDescriptions(TestModel model)
        {
            var cd = new ContentDispositionHeaderValue("attachment")
            {
                FileNameStar = model.DescriptionFile.FileName
            };

            Response.Headers.Add(HeaderNames.ContentDisposition, cd.ToString());

            byte[] bytes = System.IO.File.ReadAllBytes(model.MeasurementExportFile);

            using (FileStream fs = new FileStream(model.MeasurementExportFile, FileMode.Open, FileAccess.Read))
            {
                fs.Read(bytes, 0, System.Convert.ToInt32(fs.Length));
                fs.Close();
            }

            return File(bytes, "text/csv");

        }

Here is my View Model:这是我的视图 Model:

 public class TestModel
    {
        [BindProperty]
        [Required]
        [MinLength(5)]
        public string Name { get; set; }
        [BindProperty]
        [Required]
        [MaxLength(10,ErrorMessage ="Input string is too long.")]
        public string MyInput { get; set; }

        [BindProperty]
        [Required]
        public IFormFile DescriptionFile { get; set; }


        [BindProperty]
        [Required]
        public IFormFile MeasurementFile { get; set; }
        public string DescriptionDirectory { get; set; } 
        public string DescriptionExportFile { get; set; } 
        public string MeasurementDirectory { get; set; } 
        public string MeasurementExportFile { get; set; }

        public async Task OnPostAsync()
        {
            var token = DateTime.Now.Ticks.ToString();

            var directory =  Directory.CreateDirectory(@"uploads\"+ token + @"\");
            DescriptionDirectory = directory.CreateSubdirectory("Descriptions").FullName + @"\";
            DescriptionExportFile = directory.CreateSubdirectory(@"Descriptions\Exports\").FullName + DescriptionFile.FileName;
            MeasurementDirectory = directory.CreateSubdirectory("Measurements").FullName + @"\";
            MeasurementExportFile = directory.CreateSubdirectory(@"Measurements\Exports\").FullName + MeasurementFile.FileName;

            var file = Path.Combine(DescriptionDirectory, DescriptionFile.FileName);
            using (var fileStream = new FileStream(file, FileMode.Create))
            {
                await DescriptionFile.CopyToAsync(fileStream).ConfigureAwait(true);
            }

             file = Path.Combine(MeasurementDirectory, MeasurementFile.FileName);
            using (var fileStream = new FileStream(file, FileMode.Create))
            {
                await MeasurementFile.CopyToAsync(fileStream).ConfigureAwait(true);
            }
        }
    }

And here is the View:这是视图:

@**I need to add the namespace of C# models I'm creating *@
@using FirstASPNETCOREProject.ViewModels
@*I need to identify the model which 'fits' this page, that is the properties of the model can be
    bound to entities on the view page, using "asp-for"*@
@model TestModel
@{
    ViewData["Title"] = "Page for File Uploads";
}
@section Scripts{
}

<div asp-validation-summary="ModelOnly" style="color:white"></div>
<form method="post" enctype="multipart/form-data">
    <label>Enter a Description File Name</label>
    <input asp-for="Name" type="text" />
    <span asp-validation-for="Name"></span>
    <br>
    <label>Select a Description File</label>
    <input asp-for="DescriptionFile" type="file" />
    <span asp-validation-for="DescriptionFile"></span>
    <br>
    <label>Enter the Measurement File Name</label>
    <input asp-for="MyInput" type="text">
    <span asp-validation-for="MyInput"></span>
    <br>
    <label>Select a Measurement File</label>
    <input asp-for="MeasurementFile" type="file">
    <span asp-validation-for="MeasurementFile"></span>
    <br>
    <input type="submit" value="Send Message" />
</form>


@Html.ActionLink("Description File", "DownloadDescriptions", "App")
@Html.ActionLink("Measurement File", "DownloadMeasurements", "App")

ActionLinks are just anchor tags. ActionLink 只是锚标记。

So they use GET.所以他们使用GET。 So to pass back your model using get you would need to use Query String parameters for example adding "?MyInpu=some cool input" at the end of the url.因此,要使用 get 传回您的 model,您需要使用查询字符串参数,例如在 url 末尾添加“?MyInpu = some cool input”。

You can bind almost ANY complex object like this including Lists and Arrays.您可以像这样绑定几乎任何复杂的 object,包括列表和 Arrays。

For more information on Model Binding有关Model 绑定的更多信息

The file itself you wont be able to pass it like that.文件本身你将无法像那样传递它。 For that you will need to POST the form with a submit button or FormData using javascript.为此,您需要使用 javascript 使用提交按钮或 FormData 发布表单。

You can also add anchors that call javascript functions that use AJAX to post back all you want to the DownloadDescriptions action in your controller.您还可以添加调用 javascript 函数的锚点,这些函数使用 AJAX 将您想要的所有内容回发到 controller 中的 DownloadDescriptions 操作。

Here is an example on how to pass a model using an action link:以下是有关如何使用操作链接传递 model 的示例:

 @Html.ActionLink("Test Action", "TestAction", "Home", new { myInput = "Some Cool Input" })

In my case the previous ActionLink produces an anchor tag with href set to:在我的例子中,之前的 ActionLink 生成了一个带有 href 设置为的锚标记:

http://localhost:64941/Home/TestAction?myInput=Some Cool Input

Notice how I used an anonymous type to pass the model using the same names of the properties of my model in this case MyInput but in camelized version myInput .请注意我如何使用匿名类型来传递 model 使用与我的 model 的属性相同的名称(在这种情况下为 MyInput但在骆驼化版本myInput中)。

You can compose any model like that.您可以像这样组合任何 model。

This is my action in my controller:这是我在 controller 中的操作:

    public IActionResult TestAction([FromQuery]TestModel input) 
    {
        return View(input);
    }

Notice how I used [FromQuery] for the TestModel parameter to indicate that I expect the ASP.NET Core model binder to use the Query String parameters to populate my model.请注意我如何使用 [FromQuery] 作为TestModel参数来表明我期望 ASP.NET 核心 model 绑定器使用查询字符串参数来填充我的 model。

This is my model class:这是我的 model class:

public class TestModel
{
    public string MyInput { get; set; }
}

This is the result during debugging:这是调试期间的结果:

在此处输入图像描述

Notice how during debugging I am able to see the populated value.请注意在调试期间我如何能够看到填充的值。

NOTES:笔记:

If your model changes at the client side.如果您的 model 在客户端发生变化。 You will need to update the Query String parameters in the anchor tag using javascript... for that reason is a good idea to add name to the anchor tag.您将需要使用 javascript... 更新锚标记中的查询字符串参数...因此,将名称添加到锚标记是一个好主意。

Also this might answer your question but might NOT be the best approach to what you are trying to do.这也可能会回答您的问题,但可能不是您尝试做的最佳方法。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 在 ASP.Net Core 5 MVC 控制器中,当传递包含小数的 JSON 对象 FromBody 时,模型始终为空 - In ASP.Net Core 5 MVC Controller, when passed a JSON object FromBody that contains a decimal the model is always null 在 ASP.NET Core 中发布到控制器时,所有值都为空 - All values are null when posting to controller in ASP.NET Core ASP.NET 核心 MVC - Model 属性传递给视图,显示 ZE405C1DF83BD248A07FC9A9122 中的 null - ASP.NET Core MVC - Model properties passed to view showing null in Razor ASP.NET 核心 MVC - 将 Model 数据从视图传递回 Controller - ASP.NET Core MVC - Passing Model Data Back to Controller from View ASP.NET MVC:所有控制器值都传递为null - ASP.NET MVC: all controller values are passed null .NET Core / MVC - 查看Posting Null模型返回控制器 - .NET Core/MVC - View Posting Null Model Back to Controller Model 列表返回为 null 从视图到 controller Z9E0DA8438E1E38A1C30F4B76ZCE3 核心 - Model List returning as null from view to controller ASP.NET Core MVC How can you maintain model state in ASP.NET Core between repeatedly displaying the Model in a View and sending the model back to the Controller? - How can you maintain model state in ASP.NET Core between repeatedly displaying the Model in a View and sending the model back to the Controller? ASP.NET 视图中的表单字段在控制器中显示为 NULL - Form fields from the ASP.NET View appear NULL in the Controller Model 查看 Controller 服务连接(ASP.NET Core) - Model View Controller Service Connection (ASP.NET Core)
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM