34

मैं उन सभी विभिन्न तरीकों से उत्सुक हूं, जो लोग अपने व्यू मॉडेल बना रहे हैं और वे उस विधि को क्यों चुनते हैं।आप अपने व्यू मॉडेल को कैसे पॉप्युलेट/मान्य कर रहे हैं?

मैं यहां कई तरीकों से सोच सकता हूं:

-1। इंजेक्शन रिपोजिटरी - नियंत्रक मॉडल और मानचित्र को व्यूमोडेल में लोड करता है। यहां व्यूमोडेल कन्स्ट्रक्टर पूर्व में सेट करने के लिए विभिन्न संग्रह ले सकता है। एक चुनिंदा सूची में:

 

public CustomerController(ISomeRepository repository) 
{ 
    _repository = repository; 
} 

public ActionResult Create() 
{ 
    CustomerCreateViewModel model = new CustomerCreateViewModel(_repository.GetShipTypes, 
                   _repository.GetStates); 
.. 
.. 
} 
 

-2। ViewModelbuilder - या तो इंजेक्शन वाले इंजेक्शन के उदाहरण के साथ नियंत्रक में इंजेक्शन या तत्काल। ,

var orderViewModel = orderViewModelBuilder.WithStates().Build(orderId);

-3

>var orderViewModel = orderViewModelBuilder.WithStates().Build(orderId);

या की तरह कुछ के माध्यम से कहा जाता है। सीधे नियंत्रक में (कोई कोड आवश्यक नहीं है - इसकी गन्दा)

-4। कुछ अन्य सेवा (इंजेक्शन या नहीं) है कि डोमेन मॉडल है जो नियंत्रक तो नक्शे या एक ViewModel रिटर्न (किसी को भी इस कर रही है कि विशेष रूप से नाम नहीं एक दृश्य मॉडल वापस जाने के लिए/एक ViewModel बिल्डर वर्ग के रूप में उल्लेख किया?)


public JobCreateViewModel BuildJobCreateViewModel(int parentId) 
{ 
    JobCreateViewModel model = new JobCreateViewModel(); 
    model.JobStatus = _unitOfWork.JobRepository.GetJobStatuses(); 
    model.States=_unitOfWork.StateRepository.GetAll(); 
    return model; 
} 

अब वापसी दृश्य पर - अपने दृश्य मॉडल को सत्यापित करने के संबंध में - क्या आप मानक सत्यापन के लिए मूल व्यूमोडेल क्लास से विरासत में हैं, या अपने सभी व्यूमोडल्स के बीच अपनी मान्यताओं (पूर्व डेटा एनोटेशन विशेषताओं) की प्रतिलिपि बना रहे हैं, या बस सर्वर साइड सत्यापन पर भरोसा करते हैं यह सब आपके डोमेन ऑब्जेक्ट को दोबारा सत्यापित किया जा सकता है?

कोई अन्य? कुछ भी बेहतर है? क्यूं कर?

EDIT नीचे दिए गए लिंक के आधार पर, मुझे जिमी बोगर्ड से व्यूमोडेल के आर्किटेक्चर पर एक अच्छा लेख मिला। हालांकि यह ऊपर दिए गए प्रश्न को सीधे संबोधित नहीं करता है, यह ViewModel जानकारी के लिए यहां आने वाले किसी के लिए एक महान संदर्भ है। http://lostechies.com/jimmybogard/2009/06/30/how-we-do-mvc-view-models/

+0

यहां पर एक डाउनवोट था - बस उत्सुक क्यों - कुछ भी मैं स्पष्ट कर सकता हूं? –

+4

मेरे फोन पर और मैंने अनजाने में स्टार की कोशिश करते समय इसे क्लिक किया - क्षमा करें। अब पूर्ववत करने में बहुत देर हो चुकी है। – Jason

+0

आह कोई चिंता नहीं है:) –

उत्तर

14

मैं नियंत्रक, नहीं भंडार में एक सेवा इंजेक्षन, और फिर AutoMapper का उपयोग यह एक दृश्य के मॉडल में परिवर्तित करने के। इस मामले में सेवा परत का लाभ यह है कि यह एक या अधिक भंडारों से एक डोमेन मॉडल को उजागर करने वाले एक ही ऑपरेशन में कई सरल संचालन एकत्र कर सकता है। उदाहरण:

private readonly ICustomerService _service; 
public CustomerController(ICustomerService service) 
{ 
    _service = service; 
} 

[AutoMap(typeof(Customer), typeof(CustomerViewModel))] 
public ActionResult Create(int id) 
{ 
    Customer customer = _service.GetCustomer(id); 
    return View(customer); 
} 

इस उदाहरण में Automap एक कस्टम क्रिया फिल्टर है कि मैं जो नियंत्रक कार्रवाई के बाद निष्पादित करता है लिख सकते हैं, लौट आए वस्तु निरीक्षण करता है और परिभाषित AutoMapper मैपिंग का उपयोग करता है निर्दिष्ट गंतव्य प्रकार से मैप करने के लिए। तो दृश्य मॉडल प्रकार के रूप में संबंधित ग्राहक दृश्य मॉड्यूल प्राप्त करता है।

public ActionResult Create(int id) 
{ 
    Customer customer = _service.GetCustomer(id); 
    CustomerViewModel vm = Mapper.Map<Customer, CustomerViewModel>(customer); 
    return View(vm); 
} 

यह सिर्फ यह है कि यह बहुत ज्यादा पाइपलाइन और दोहराव कोड है कि केंद्रीकृत किया जा सकता है है: के बराबर हो गया होता।

मैं आपको यह भी जिमी Bogard से putting your controllers on a diet video देख सिफारिश करेंगे।

+0

धन्यवाद डारिन। मैंने किसी को एक समान ऑटोमैप विशेषता डेमो देखा - मुझे लगता है कि जिमी के पास एक उपलब्ध है। इन दृश्य मॉडल (या आप नहीं?) के क्लाइंट सत्यापन के लिए आप क्या करते हैं और उनके बीच सत्यापन तर्क साझा करते हैं? क्या आप अपनी रिपोजिटरीज़ को अपनी सेवा परत में इंजेक्ट कर रहे हैं? –

+0

@AdamTuliper, मैं सर्वर साइड सत्यापन के लिए FluentValidation.NET का उपयोग करता हूं और सरल क्लाइंट साइड सत्यापन परिदृश्यों के लिए (आवश्यक, तिथि से अधिक ...)। अधिक जटिल क्लाइंट साइड सत्यापन परिदृश्य (निर्भर गुण, ...) के लिए मैं तय करता हूं कि मुझे इसे क्लाइंट पर संभालने की आवश्यकता है और यदि उन परिदृश्यों के लिए क्लाइंट साइड सत्यापन करने की आवश्यकता है तो मैं कस्टम jquery मान्य एपेंडर्स लिखता हूं। जहां तक ​​सेवा परत में रिपोजिटरी का संबंध है, हां सेवा परत सीटीओ इंजेक्शन का उपयोग करती है ताकि सभी रिपोजिटरी डोमेन मॉडल पर सरल सीआरयूडी संचालन करने की अनुमति दे सकें। –

+0

धन्यवाद डारिन, एक और अच्छा जवाब:) –

0

हमारे विधि नियंत्रक करने के लिए भंडार इंजेक्षन और Automapper http://automapper.org/ का उपयोग कर ViewModel से मैप किया जा सके। हमारे व्यू मॉडल्स में क्लाइंट पर सत्यापन होने की अनुमति देने के लिए डेटा एनोटेशन विशेषताएँ होती हैं।

हम रिपॉजिटरी पर विधियों को कॉल करते हैं जो डोमेन ऑब्जेक्ट्स (इकाई फ्रेमवर्क) लौटाते हैं। डोमेन ऑब्जेक्ट्स को ViewModel में मैप किया गया है। हम संपादन के लिए एक ही व्यूमोडेल का उपयोग करते हैं और जोड़ते हैं ताकि एक बार डेटा एनोटेशन की आवश्यकता हो। इसके सरलतम रूप में यह निम्न कोड की तरह दिखता है:

public ActionResult List(int custId, int projId) 
    { 
     var users = _userRepository.GetByCustomerId(custId); 
     var userList = Mapper.Map<IEnumerable<CMUser>, IEnumerable<UserListViewModel>>(users); 
     return View(userList); 
    } 
+0

लेकिन एक संग्रह मॉडल को मैप नहीं किया गया है। किसी डोमेन ऑब्जेक्ट या व्यूमोडेल को वापस करने के लिए रिपॉजिटरी में कुछ विधि को कॉल किया जाना चाहिए। इसके अलावा इस करता है, तो आप एक मॉडल या एक साझा स्थान, आदि –

+0

लिए अलग-अलग व्याख्या का उपयोग इसके अलावा, अगर संपादन के लिए एक ही ViewModel का उपयोग कर कवर नहीं करता है/तो कहते हैं कि तुम क्या एक पूर्णांक आईडी क्षेत्र के बारे में करने के लिए कर रहे हैं डेटा एनोटेशन के साथ डिफ़ॉल्ट रूप से आवश्यक किया जा रहा ? अगर फॉर्म से गायब है, तो यह वैधता में असफल हो जाएगा। इंट्स को डिफ़ॉल्ट रूप से आवश्यक है, इसलिए आपको "बनाना" परिदृश्य के लिए 0 पर प्रारंभ करना होगा, नहीं? –

1

मैं सिर्फ एक परियोजना जहाँ हम 4 # पर एक परिवर्तन किया था समाप्त हो गया। हमारे पास नियंत्रक में इंजेक्शन वाली एक सर्विस क्लास थी। सेवा वर्ग ने भंडार और एक मॉडल निर्माता वर्ग पर निर्भरताएं आयोजित कीं (हमने इसे मॉडल कारखाना कहा)।

नियंत्रक सेवा कक्षा में बुलाया गया, जिसने व्यापार सत्यापन तर्क को संभाला, और उसके बाद उचित कारखाने से मॉडल देखें। मॉडल स्वयं इनपुट सत्यापन के लिए डेटा एनोटेशन पर निर्भर थे।

यह हमारी टीम के लिए वास्तव में अच्छा काम करता है। देवताओं को एक-दूसरे को प्रभावित किए बिना अपना काम करने की इजाजत देने के लिए चिंताओं का पर्याप्त अलगाव था, लेकिन यह समझने के लिए पर्याप्त प्रबंधनीय था कि क्या हो रहा था।

यह पहली बार हम इसे करने की कोशिश है और हम इसके साथ चिपके हुए हो जाएगा। मुझे यह देखने में दिलचस्पी है कि दूसरों ने जवाब कैसे दिया।

+0

धन्यवाद। तो आपकी सेवा कक्षा बदले में भंडार के साथ इंजेक्शन दिया गया था? पूर्व के लिए आपके तरीके सेटअप की तरह क्या थे। सेवा कक्षा में? आपने एकाधिक लेकिन समान दृश्य मॉडल में क्लाइंट साइड सत्यापन को कैसे संभाला? (उदा। बनाम बनाम बनाएँ) –

+0

यह नीचे डारिन के उदाहरण के समान है, हमारे पास एक पागल आवश्यकता थी कि हम ओपन सोर्स सॉफ्टवेयर का उपयोग नहीं कर सके, इसलिए हम ऑटोमैपर का उपयोग नहीं कर सके। अगली बार हम दृश्य मॉडल फैक्ट्री को ऑटोमैपर के साथ बदल देंगे। हमने उसी मॉडल के विभिन्न विचारों को पूरा करने के लिए प्रदर्शन और संपादक टेम्पलेट का उपयोग किया, डेटा एनोटेशन ने हमें आवश्यक सभी मान्यताओं के साथ प्रदान किया। – Jason

+0

और मॉडल बिल्डर क्लास को कन्स्ट्रक्टर पैरामीटर (रिपोजिटरी ऑब्जेक्ट को संभालने में सेवा) से रिपोजिटरी ऑब्जेक्ट प्राप्त होता है या मॉडल बिल्डर सीधे रिपोजिटरी का उपयोग करता है? क्या आप कृपया कुछ बहुत ही सरल उदाहरण प्रदान कर सकते हैं? – Muflix

0

मैं एक सेवा परत है कि सेवा के तरीकों से ViewModels लौटने नियंत्रक से डोमेन मॉडल खाल का उपयोग करें। यह मुझे क्लाइंट को प्रभावित किए बिना डोमेन मॉडल में परिवर्तन करने की अनुमति देता है।