2011-11-29 25 views
8

Tôi có hai ViewModels (giản thể):Xác nhận của ViewModels lồng nhau

public class ParentViewModel 
{ 
    public ParentViewModel 
    { 
     Content = new ChildViewModel(); 
    } 

    public ChildViewModel Content { get; set, } 
} 

public class ChildViewModel 
{ 
    [Required] 
    public string Name1 { get; set, } 
    [Required] 
    public string Name2 { get; set, } 
} 

Và bộ điều khiển bài hành động sau đây:

[HttpPost] 
public ActionResult Create(ParentViewModel viewModel) 
{ 
    if (ModelState.IsValid) 
    { 
     // process viewModel -> write something into database 
     return RedirectToAction("Index"); 
    } 
    return View(viewModel); 
} 

Bây giờ tôi đang gửi các giá trị hình thức sau đây trong một cơ thể bài yêu cầu URL tương ứng với hành động đó (theo cách thủ công trong Trình yêu cầu Fiddler):

  • Content.Name1 = X

    này hoạt động tốt, tài sản Name1 được điền vào viewModel.Content, Name2null và tình trạng mô hình này là không hợp lệ vì Name2 là bắt buộc. Vì vậy, xác nhận không thành công như mong đợi.

  • Xontent.Name1 = X hoặc Name1 = X hoặc bất cứ điều gì để không có gì bị ràng buộc với viewModel

    Bây giờ viewModel.Content không phải là null (vì tôi đang instantiating nó trong constructor) nhưng tất cả thuộc tính Name1Name2null. Điều này được mong đợi. Điều tôi đã làm không phải là kỳ vọng là trạng thái mô hình là hợp lệ, vì vậy nó vượt qua xác thực (dẫn đến ngoại lệ DB sau này vì có các cột không thể vô hiệu).

Làm cách nào để cải thiện mã này để xác thực cũng hoạt động trong trường hợp thứ hai?

tôi đã làm ba thí nghiệm:

  • Tôi đã gỡ bỏ instantiation của Content trong constructor ParentViewModel, sau đó Contentnull trong ví dụ thứ hai ở trên, nhưng xác nhận vẫn trôi qua.

  • Tôi đã thêm một thuộc tính [Required] đến Content tài sản (nhưng không loại bỏ các instantiation của Content trong constructor ParentViewModel). Điều này không có tác dụng gì cả, hành vi được mô tả của hai bài kiểm tra ở trên là như nhau.

  • Tôi đã thêm một thuộc tính [Required] đến Content tài sản loại bỏ các instantiation của Content trong constructor ParentViewModel. Điều này dường như hoạt động như tôi muốn: Trong thử nghiệm thứ hai Contentnull và xác thực không thành công do thuộc tính [Required].Nó sẽ giống như thế này:

    public class ParentViewModel 
    { 
        [Required] 
        public ChildViewModel Content { get; set, } 
    } 
    
    public class ChildViewModel 
    { 
        [Required] 
        public string Name1 { get; set, } 
        [Required] 
        public string Name2 { get; set, } 
    } 
    

tôi sẽ kết luận bây giờ mà instantiating tài sản Content con trong constructor ParentViewModel là nguồn gốc của vấn đề và rằng mô hình chất kết dính tự phải nhanh chóng các thuộc tính con (hay không , nếu không có trường biểu mẫu phù hợp trong yêu cầu) để có xác thực hợp lệ phía máy chủ hoạt động.

Tôi có bản thuyết trình thuộc tính con ở một số nhà xây dựng mô hình chế độ xem khác và không nhận thấy vấn đề này cho đến bây giờ. Vì vậy, đây có phải là một thực tế không tốt? Có cách nào khác để giải quyết vấn đề không?

+0

Tôi hiện đang vật lộn với điều gì đó tương tự. Chỉ có sự khác biệt trong trường hợp của tôi là, tôi có một 'IEnumerable' của ChildViewModels. Tôi đã thử tất cả ba lựa chọn ở trên và dường như không có gì làm việc cho tôi. –

Trả lời

0

Giải pháp thứ ba là tốt:

public class ParentViewModel 
{ 
    [Required] 
    public ChildViewModel Content { get; set, } 
} 

public class ChildViewModel 
{ 
    [Required] 
    public string Name1 { get; set, } 
    [Required] 
    public string Name2 { get; set, } 
} 

Tôi đang sử dụng nó tại một số nơi và không nhận thấy bất kỳ các vấn đề.

0

ModelState.IsValid cho bạn biết nếu bất kỳ lỗi mô hình nào đã được thêm vào ModelState.

Trình kết nối mô hình mặc định sẽ thêm một số lỗi cho các vấn đề chuyển đổi loại cơ bản, chẳng hạn như chuyển số không cho một số nào đó là "int". Bạn có thể cư trú ModelState hoàn toàn hơn dựa trên bất kỳ hệ thống xác thực nào bạn đang sử dụng. Tôi sẽ đề nghị xem xét các chú thích dữ liệu để xác nhận các ViewModels vì nó hoạt động tốt.

Cú pháp này có thể sai hoặc cũ. ModelState.AddModelError ("key", Exception)

diễn giải từ What is ModelState.IsValid valid for in ASP.NET MVC in NerdDinner?

+0

Tôi thấy rằng đây là * kỹ thuật * một thay thế nhưng * thực tế * nó sẽ có nghĩa như sau: Trong mỗi bài đăng hành động với các mô hình xem có lồng nhau xem mô hình tôi phải làm một cái gì đó như: 'if (viewModel.Content.Name1 == null && viewModel.Content.Name2 == null && ...) ModelState.AddModelError (...); 'Điều này trông không đẹp. Đối với chú thích dữ liệu: Tôi không biết người nào có thể giúp tôi. Tôi đã sử dụng '[Bắt buộc]' và đó là tất cả những gì xác nhận nên xem xét trong mô hình của tôi. Có một số chú thích "lừa" khác không? – Slauma

Các vấn đề liên quan