asp.net 如何为一对一关系编写控制器?我的模型中出现“需要ApplicationUser字段”错误

yxyvkwin  于 2023-05-30  发布在  .NET
关注(0)|答案(1)|浏览(104)

我有两个模型:ApplicationUser(Identity)和Review。这些模型具有一对一的关系。我为Review搭建了一个控制器,当我试图创建一个对象时,我在我的模型中得到了“TheApplicationUser字段是必需的”错误。我应该如何编写这个控制器?
下面是Review模型的代码

using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;

namespace ZaryadApp.Models
{
    public class Review
    {
        [ForeignKey("ApplicationUser")]
        [Required]
        public string ReviewId { get; set; }
        [Required]
        public string Text { get; set; }
        public DateTime CreatedAt { get; set; }
        public virtual ApplicationUser ApplicationUser { get; set; }
    }
}

应用程序用户模型

using Microsoft.AspNetCore.Identity;

namespace ZaryadApp.Models
{
    public class ApplicationUser : IdentityUser
    {
        public virtual Review Review { get; set; }
    }
}

Reviews控制器的“创建”部分

public IActionResult Create()
{
    ViewData["ReviewId"] = new SelectList(_context.Users, "Id", "Id");
    return View();
}

// POST: Reviews/Create
// To protect from overposting attacks, enable the specific properties you want to bind to.
// For more details, see http://go.microsoft.com/fwlink/?LinkId=317598.
[HttpPost]
[ValidateAntiForgeryToken]
public async Task<IActionResult> Create([Bind("ReviewId,Text,CreatedAt")] Review review)
{
    //ClaimsPrincipal currentUser = this.User;
    //var currentUserID = currentUser.FindFirst(ClaimTypes.NameIdentifier).Value;
    //var user = _context.Users.FirstOrDefault(u => u.Id == currentUserID);
    //review.ApplicationUser = user;
    //Debug.WriteLine(review.ApplicationUser.UserName);
    foreach (var modelState in ViewData.ModelState.Values)
    {
        foreach (ModelError error in modelState.Errors)
        {
            Debug.WriteLine(error.ToString());
        }
    }
    if (ModelState.IsValid)
    {
        _context.Add(review);
        await _context.SaveChangesAsync();
        return RedirectToAction(nameof(Index));
    }
    ViewData["ReviewId"] = new SelectList(_context.Users, "Id", "Id", review.ReviewId);
    return View(review);
}

我的创建视图

<form asp-action="Create">
            <div asp-validation-summary="ModelOnly" class="text-danger"></div>
            <div class="form-group">
                <label asp-for="ReviewId" class="control-label"></label>
                <select asp-for="ReviewId" class ="form-control" asp-items="ViewBag.ReviewId"></select>
            </div>
            <div class="form-group">
                <label asp-for="Text" class="control-label"></label>
                <input asp-for="Text" class="form-control" />
                <span asp-validation-for="Text" class="text-danger"></span>
            </div>
            <div class="form-group">
                <label asp-for="CreatedAt" class="control-label"></label>
                <input asp-for="CreatedAt" class="form-control" />
                <span asp-validation-for="CreatedAt" class="text-danger"></span>
            </div>
            <div class="form-group">
                <input type="submit" value="Create" class="btn btn-primary" />
            </div>
        </form>

我尝试添加review.ApplicationUser = currentUser但没有成功

pcrecxhr

pcrecxhr1#

对,所以基本上在控制器启动之前,框架试图帮你一个忙,并得到错误。其实有两种方法可以阻止它。

1.更改创建/查看

因此,当用户点击create,然后传入应用程序用户,并通常在表单中设置id(主键)。
通常复习类(在你的例子中)应该有类似的内容

public int ApplicationUserId { get; set; }

 public virtual ApplicationUser ApplicationUser { get; set; }

其中ApplicationUserId是数据库中链接回ApplicationUser表的字段。
您可以在创建页面上创建ApplicationUser(并存储在数据库中),然后在回发时将applicationUser和review链接在一起。
在视图中,ApplicationUserId有一个隐藏字段,它是用户的id

2.更改回发

因此,在回发时删除ModelState.IsValid。我们知道这是无效的。在第一次回发时,在数据库中创建ApplicationUser,然后在review对象中设置id。使用TryValidateModel(review)将测试您的review对象,如果可以,您可以保存它。之后,您可以使用已保存的评论更新ApplicationUser。

相关问题