简体   繁体   English

Model 绑定在 ASP.NET 核心 Razor 页

[英]Model Binding in ASP.NET Core Razor Pages

I have a question about model binding in ASP.NET Core Razor pages.我有一个关于 model 绑定在 ASP.NET Core Razor 页面的问题。 I've spent a lot of time reading the Microsoft documentation, Stackoverflow posts and learnrazorpages.com, but haven't quite found the answer I'm looking for.我花了很多时间阅读 Microsoft 文档、Stackoverflow 帖子和 learnrazorpages.com,但还没有完全找到我正在寻找的答案。 So below is a stripped down version of three classes I have.所以下面是我拥有的三个课程的精简版。 As you can see, both Client and ReferralPerson contain Person objects and Client also contains a ReferralPerson object. On my razor page (the data entry form), I intentionally do not show all of the fields for the Person object that is part of the ReferralPerson.如您所见,Client 和 ReferralPerson 都包含 Person 对象,Client 还包含 ReferralPerson object。在我的 razor 页面(数据输入表单)上,我有意不显示属于 ReferralPerson 的 Person object 的所有字段. There are also other properties of the ReferralPerson object that are not shown such as NumberOfReferrals. ReferralPerson object 的其他属性也未显示,例如 NumberOfReferrals。 If a user recalls a record, modifies some of the data and then saves (Post), only those properties that I have included inside of the element end up being populated in the model in the OnPost (OnPostSave).如果用户调用一条记录,修改一些数据然后保存 (Post),只有我包含在元素中的那些属性最终会填充到 OnPost (OnPostSave) 的 model 中。 I understand why this is.我明白这是为什么。 My question is do I have to include every single property, individually on the page in order for those properties to be populated in the OnPost event?我的问题是我是否必须在页面上单独包含每个属性,以便在 OnPost 事件中填充这些属性? If you look at my Razor page code below, you will see that I add a number of hidden fields at the top of the element.如果您查看下面我的 Razor 页面代码,您会看到我在元素的顶部添加了一些隐藏字段。 Do I need to do that for every single property that isn't visible or included somewhere else inside that form?我是否需要为每个不可见或包含在该表单内其他地方的属性执行此操作? Ideally I would just be able to do something like the following to include the entire object versus having hidden fields for every single property.理想情况下,我将能够执行类似以下的操作以包含整个 object,而不是为每个属性设置隐藏字段。 I just want to make sure there isn't something I'm not aware of in terms of how this can or should be handled.我只是想确保在如何处理或应该如何处理方面没有我不知道的事情。

<input type="hidden" asp-for="Client.ReferralPerson" />

Here are the C# classes (model)这是 C# 类(模型)

public class Person
{
    public int ID { get; set; }

    [Required, StringLength(50)]
    public string FirstName { get; set; } = "N/A";

    [Required, StringLength(50)]
    public string LastName { get; set; } = "N/A";

    [StringLength(30)]
    public string PhoneNumberPrimary { get; set; }

    [StringLength(30)]
    public string PhoneNumberSecondary { get; set; }

    [StringLength(50)]
    public string Address { get; set; }

    [StringLength(50)]
    public string EmailAddress { get; set; }

}

public class Client
{
    public int ID { get; set; }
    public Person Person { get; set; }

    public DateTime InitalContactDate { get; set; }       

    [Required, StringLength(100)]
    public string ReasonForVisit { get; set; }
    public ReferralPerson ReferralPerson { get; set; }

    //other properties removed for brevity
}

public class ReferralPerson
{
    public int ID { get; set; }
    public Person Person { get; set; }

    [StringLength(100)]
    public string BusinessName { get; set; }
    public int NumberOfReferrals { get; set; }

}

Here's a simplified version of my Razor page:这是我的 Razor 页面的简化版本:

<form class="needs-validation p-2" novalidate="" method="post">
    <input type="hidden" asp-for="Client.ID" />
    <input type="hidden" asp-for="Client.Person.ID" />
    <input type="hidden" asp-for="Client.ContactType.ID" />
    <input type="hidden" asp-for="Client.ReferralPerson.ID" />
    <input type="hidden" asp-for="Client.ReferralPerson.Person.ID" />


    <div class="row mb-3">

        <div class="col-sm-6">
            <label asp-for="Client.Person.FirstName" class="form-label">First name</label>
            <input type="text" class="form-control" asp-for="Client.Person.FirstName">
            <span asp-validation-for="Client.Person.FirstName" class="text-danger font-weight-bold"></span>
        </div>

        <div class="col-sm-6">
            <label asp-for="Client.Person.LastName" class="form-label">Last name</label>
            <input type="text" class="form-control" asp-for="Client.Person.LastName">
            <span asp-validation-for="Client.Person.LastName" class="text-danger font-weight-bold"></span>
        </div>
    </div>

    <div class="row mb-3">

        <div class="col-sm-6">
            <label for="type" class="form-label stacked-justify-left">Date</label>
            <input type="date" class="form-control" asp-for="Client.InitalContactDate">
            <span asp-validation-for="Client.InitalContactDate" class="text-danger font-weight-bold"></span>
        </div>

        <div class="col-6">
            <label for="email" class="form-label">Email <span class="text-muted">(Optional)</span></label>
            <input type="email" class="form-control" placeholder="you@example.com" asp-for="Client.Person.EmailAddress">
        </div>
    </div>

    <div class="row mb-3">

        <div class="col-6">
            <label for="primaryPhone" class="form-label">Phone # (Primary)</label>
            <input type="text" class="form-control" placeholder="Phone Number" asp-for="Client.Person.PhoneNumberPrimary">
        </div>

        <div class="col-6">
            <label for="secodaryPhone" class="form-label">Phone # (Secondary)</label>
            <input type="text" class="form-control" placeholder="Phone Number" asp-for="Client.Person.PhoneNumberSecondary">
        </div>

    </div>

    <div class="row mb-3">
        <div class="col-12">
            <label for="address" class="form-label">Address</label>
            <input type="text" class="form-control" placeholder="1234 Main St" asp-for="Client.Person.Address">
        </div>
    </div>


    <div class="row mb-3" id="ReferralPersonDetails" style="display:none">

        <div class="col-sm-6">
            <label asp-for="Client.ReferralPerson.Person.FirstName" class="form-label">Referral By First name</label>
            <input type="text" class="form-control" asp-for="Client.ReferralPerson.Person.FirstName">
        </div>

        <div class="col-sm-6">
            <label asp-for="Client.ReferralPerson.Person.LastName" class="form-label">Referral By Last name</label>
            <input type="text" class="form-control" asp-for="Client.ReferralPerson.Person.LastName">
        </div>
    </div>

    <hr class="my-4">

    <div class="row mb-3 ml-1 mr-1">
        <hr class="my-4">
        <button type="submit" class="w-100 btn btn-primary btn-lg" asp-page-handler="Save">Save</button>
    </div>

</form>

Model binding is based on the name of properties in model, If you don't use Model binding是根据model中的属性名,如果不使用

<input asp-for="xxx">

to bind the specified property, After submitting the form, These properties will not be populated in post method.绑定指定的属性,提交表单后,这些属性不会被填充到post方法中。 So if you don't bind all properties, those that are not bound will not be populated in the post method.所以如果你不绑定所有的属性,那些没有绑定的将不会填充到 post 方法中。

But in your data form, I think you just want to let the user modify some properties.但是在你的数据表单中,我认为你只是想让用户修改一些属性。 So in my opinion, You can create a viewmodel to include the properties whitch you want to change, In this method you don't need to bind all the properties in the form.所以在我看来,您可以创建一个viewmodel来包含您想要更改的属性,在这种方法中您不需要绑定表单中的所有属性。 Then in your controller, You just need to replace the original data with the data in the viewmodel .然后在你的 controller 中,你只需要将原始数据替换为viewmodel中的数据即可。

You don't need to do the same with all id fields.您不需要对所有 id 字段执行相同的操作。 I guess you are trying to edit the information of Client and ReferralPerson, adding the.Person.ID fields is not necessary because surely your database already has information about Person in each Client or ReferralPerson, get it out in controller process this action then edit it with data from the form.我猜你正在尝试编辑 Client 和 ReferralPerson 的信息,添加 .Person.ID 字段是没有必要的,因为你的数据库肯定已经有每个 Client 或 ReferralPerson 中的 Person 的信息,在 controller 处理这个操作然后编辑它与表格中的数据。

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

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM