具有外键和创建操作的ViewModel

时间:2016-09-21 10:24:04

标签: c# asp.net-mvc entity-framework razor viewmodel

我有一个页面显示帖子的详细信息,已识别的用户可以在该帖子上添加评论。

我的问题:

  1. PostID和UserID在评论模型中为FK,不会从视图传递到控制器

  2. CommnetMessage是Null !!

  3. 有什么不对?

    评论模型:

    <div class="container box">
    	    <div class="row">
    	        <div class="cc-testimonial-quote">
    	            <div><img src="/src/to/img.jpg">
    	            Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.</div>
    	        </div>
    	    </div>
    	</div>
    
    
    	

    发布模型:

    public class Comment : System.Object
    {
        public Comment()
        {
            this.CommnetDate = General.tzIran();
        }
    
        [Key]
        public int CommentID { get; set; }
    
        [Required]
        public string CommnetMessage { get; set; }
    
        [Required]
        public DateTime CommnetDate { get; set; }
        public string UserId { get; set; }
        [Key, ForeignKey("UserId")]
        public virtual ApplicationUser ApplicationUser { get; set; }
    
        public int PostID { get; set; }
        [Key, ForeignKey("PostID")]
        public virtual Post posts { get; set; }
    }
    

    查看型号:

    public class Post : System.Object
        {
            public Post()
            {
                this.PostDate = General.tzIran();
                this.PostViews = 0;
            }
    
            [Key]
            public int PostID { get; set; }
            public string PostName { get; set; }
            public string PostSummery { get; set; }
            public string PostDesc { get; set; }
            public string PostPic { get; set; }
            public DateTime PostDate { get; set; }
            public int PostViews { get; set; }
            public string postMetaKeys { get; set; }
            public string PostMetaDesc { get; set; }
    
            public string UserId { get; set; }
            [ForeignKey("UserId")]
            public virtual ApplicationUser ApplicationUser { get; set; }
    
            public int CategoryID { get; set; }
            [ForeignKey("CategoryID")]
            public virtual Category Category { get; set; }
    
            public virtual ICollection<Comment> commnets {get; set;}
        }
    
    
    public class ApplicationUser : IdentityUser
    {
        public string FirstName { get; set; }
        public string LastName { get; set; }
    
        /*Realations*/
    
        public virtual ICollection<Comment> Comments { get; set; }
        public virtual ICollection<Post> Posts { get; set; }
    }
    

    控制器:

    public class PostViewModel
    {
        public ApplicationUser Users { get; set; }
        public Post posts { get; set; }
        public Category Categories { get; set; }
        public IEnumerable<Comment> ListCommnets { get; set; }
        public Comment Commnets { get; set; }
    }
    

    评论部分视图:

    public ActionResult Details(int? id)
    {
        if (id == null)
        {
            return new HttpStatusCodeResult(HttpStatusCode.BadRequest);
        }
        var post = db.Posts.Find(id);
    
        post.PostViews += 1;
        db.SaveChanges();
    
        if (post == null)
        {
            return HttpNotFound();
        }
        return View(new PostViewModel() { posts = post });
    }
    
    [HttpPost]
    [ValidateAntiForgeryToken]
    public ActionResult Details([Bind(Include = "CommentID,CommnetMessage,CommnetDate,UserId,PostID")] Comment comment , int? id)
    {
        int pid = comment.PostID;
        if (ModelState.IsValid)
        {
            db.CommentS.Add(comment);
            db.SaveChanges();
            TempData["notice"] = "پیغام شما با موفقیت ثبت شد.";
            return RedirectToAction("success");
        }
    
        ViewBag.UserId = new SelectList(db.Users, "Id", "FirstName", comment.UserId);
        ViewBag.PostID = id;
        return View( new PostViewModel() { posts = db.Posts.Find(id)});
    }
    
    public ActionResult success()
    {
    
        ViewBag.Message = "از طریق فرم زیر می توانید برایمان پیغام بگذارید.";
    
        return View("Details", new PostViewModel() { ListCommnets = db.CommentS });
    }
    

1 个答案:

答案 0 :(得分:0)

正如@StephenMuecke所说,您的视图模型为PostViewModel,所有编辑器,隐藏字段都是根据您的视图模型创建的。例如,当您使用@Html.HiddenFor(model => model.posts.PostID)生成隐藏字段并尝试发布数据时,MVC模型绑定器会尝试将此字段的值绑定到操作方法中指定的模型。在您的情况下,它是Comment因此,MVC模型绑定器将尝试将生成的隐藏字段的绑定值绑定到不存在的Comment.posts.PostID。为了使一切工作完美,您必须使用相同的视图模型作为操作方法的参数:

[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Details(PostViewModel viewModel)
{
......
}

此外,同样在@StephenMuecke满足时,您的视图模型应该只包含您需要的属性。例如,您的PostViewModel应如下所示:

public class PostViewModel
{
    // Actually, you do not need UserId property
    // as it should be retrieved inside controller
    // from current user data
    public string UserId { get; set; }
    public string UserName { get; set; }
    public int PostID { get; set; }
    public string CommentMessage { get; set; }
}

回到您的操作方法,您必须将视图模型映射到您的模型:

[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Details(PostViewModel viewModel)
{
    Comment comment = new Comment
    {
        CommnetMessage = viewModel.CommentMessage,
        // and other properties
    }

    // Save your model and etc.
}