डीडीडी में अपवाद


12

मैं DDD सीख रहा हूं और मैं कुछ स्थितियों में अपवादों को फेंकने के बारे में सोच रहा हूं। मैं समझता हूं कि कोई वस्तु खराब स्थिति में प्रवेश नहीं कर सकती है इसलिए यहां अपवाद ठीक हैं, लेकिन कई उदाहरणों में अपवाद भी उदाहरण के लिए फेंक रहे हैं यदि हम डेटाबेस में मौजूद ईमेल के साथ नए उपयोगकर्ता को जोड़ने का प्रयास कर रहे हैं।

public function doIt(UserData $userData)
{
    $user = $this->userRepository->byEmail($userData->email());
    if ($user) {
        throw new UserAlreadyExistsException();
    }

    $this->userRepository->add(
        new User(
            $userData->email(),
            $userData->password()
        )
    );
}

इसलिए यदि इस ईमेल वाला उपयोगकर्ता मौजूद है, तो हम एप्लिकेशन सेवा में अपवाद को पकड़ सकते हैं, लेकिन हमें कोशिश करने वाले ब्लॉक का उपयोग करके एप्लिकेशन के संचालन को नियंत्रित नहीं करना चाहिए।

इसके लिए सबसे अच्छा तरीका कैसे है?


1
डोमेन सेवा (हैंडलर) अपवादों को फेंकना ठीक है।
एंडी

जवाबों:


21

आइए इसे समस्या स्थान की एक छोटी समीक्षा के साथ शुरू करें: डीडीडी के मौलिक प्रिंसिपलों में से एक व्यवसाय के नियमों को उन स्थानों पर यथासंभव बंद करना है जहां उन्हें लागू करने की आवश्यकता है। यह एक अत्यंत महत्वपूर्ण अवधारणा है क्योंकि यह आपके सिस्टम को अधिक "सामंजस्यपूर्ण" बनाता है। मूविंग रूल्स "ऊपर की ओर" आमतौर पर एनीमिक मॉडल का संकेत है; जहाँ ऑब्जेक्ट्स डेटा के केवल बैग होते हैं और नियमों को लागू करने के लिए उस डेटा के साथ इंजेक्ट किया जाता है।

एनीमिक मॉडल डेवलपर्स के लिए बहुत कुछ समझ सकता है जो केवल डीडीडी के साथ शुरू हो रहा है। आप एक Userमॉडल बनाते हैं और EmailMustBeUnqiueRuleजो ईमेल को मान्य करने के लिए आवश्यक जानकारी के साथ इंजेक्ट किया जाता है। सरल। सुरुचिपूर्ण। मुद्दा यह है कि यह "तरह" सोच प्रकृति में मौलिक रूप से प्रक्रियात्मक है। डीडीडी नहीं। क्या हो रहा है समाप्त होता है आप दर्जनों Rulesबड़े करीने से लिपटे और encapsulated के साथ एक मॉड्यूल के साथ छोड़ दिया जाता है, लेकिन वे संदर्भ के लिए पूरी तरह से रहित हैं जहां उन्हें अब नहीं बदला जा सकता है क्योंकि यह स्पष्ट नहीं है कि कब / कहाँ लागू किया जाता है। क्या इसका कोई मतलब है? यह स्व-स्पष्ट हो सकता है कि एक EmailMustBeUnqiueRuleके निर्माण पर लागू किया जाएगा User, लेकिन क्या होगा UserIsInGoodStandingRule? धीरे-धीरे लेकिन निश्चित रूप से, निकालने का दानेदारकरणRulesउनके संदर्भ में से आपको एक ऐसी प्रणाली के साथ छोड़ देता है जिसे समझना कठिन है (और इस प्रकार बदला नहीं जा सकता है)। नियमों को केवल तभी लागू किया जाना चाहिए जब वास्तविक क्रंचिंग / निष्पादन इतना वर्बोज़ हो कि आपका मॉडल ढीला फोकस करना शुरू कर दे।

अब आपके विशिष्ट प्रश्न पर: मुद्दा Service/ CommandHandlerफेंकने के साथ यह Exceptionहै कि आपके व्यवसाय का तर्क आपके डोमेन से लीक ("ऊपर की ओर") होने लगा है। किसी ईमेल को जानने के लिए आपकी Service/ CommandHandlerआवश्यकता क्यों विशिष्ट होनी चाहिए? एप्लिकेशन सेवा परत का उपयोग आमतौर पर कार्यान्वयन के बजाय समन्वय के लिए किया जाता है। इसका कारण यह स्पष्ट किया जा सकता है कि यदि हम ChangeEmailआपके सिस्टम में कोई विधि / कमांड जोड़ते हैं । अब बीओटीएच विधियों / कमांड हैंडलर को आपकी अनूठी जांच को शामिल करना होगा। यह वह जगह है जहां एक डेवलपर को "निकालने" का प्रलोभन दिया जा सकता है EmailMustBeUniqueRule। जैसा कि ऊपर बताया गया है, हम उस मार्ग पर नहीं जाना चाहते हैं।

कुछ अतिरिक्त ज्ञान crunching हमें एक अधिक DDD उत्तर दे सकते हैं। एक ईमेल की विशिष्टता एक अपरिवर्तनीय Userवस्तु है जिसे वस्तुओं के संग्रह में लागू किया जाना चाहिए । क्या आपके डोमेन में एक अवधारणा है जो " Userवस्तुओं का संग्रह" का प्रतिनिधित्व करती है ? मुझे लगता है कि आप शायद देख सकते हैं कि मैं यहाँ कहाँ जा रहा हूँ।

इस विशेष मामले के लिए (और कई और संग्रह में आक्रमणकारियों को शामिल करना) इस तर्क को लागू करने के लिए सबसे अच्छी जगह है Repository। यह विशेष रूप से सुविधाजनक है क्योंकि Repositoryइस तरह के सत्यापन (डेटा स्टोर) को निष्पादित करने के लिए आवश्यक बुनियादी ढांचे का अतिरिक्त टुकड़ा " आपका " भी जानता है। आपके मामले में, मैं इस जाँच को addविधि में रखूँगा। यह सही समझ में आता है? वैचारिक रूप से, यह इस पद्धति है जो वास्तव में Userआपके सिस्टम में जोड़ता है। डेटा स्टोर एक कार्यान्वयन विवरण है।


क्या मैं पूछ सकता हूं कि आपका क्या मतलब है Moving rules "upwards" is generally a sign of an anemic model? ऊपर की ओर अनुप्रयोग परत का मतलब है? या डोमेन मॉडल के लिए?
अयननाम डोनटकेयर

1
"ऊपर की ओर" का अर्थ है आपकी एप्लिकेशन परत (एक स्तरित वास्तुकला के बारे में सोचें)। मैंने इसे ऊपर से छुआ है, लेकिन ऊपर की ओर बढ़ते हुए नियम एनेमिक मॉडल का संकेत है, यह डेटा और व्यवहार को अलग करने का प्रतिनिधित्व करता है जो कोर डोमेन मॉडल होने के पूरे उद्देश्य को पराजित करता है। यदि किसी ईमेल को सत्यापित करना ईमेल भेजने से अलग मॉड्यूल में है, तो आपके Emailमॉडल में डेटा का एक बैग होना चाहिए , जिसे भेजने से पहले चालान के लिए निरीक्षण किया जाता है। देखें: softwareengineering.stackexchange.com/questions/372338/…
किंग-साइड-स्लाइड

2
डोमेन लॉजिक को रिपॉजिटरी में ले जाना गलत है। आपको डोमेन लेयर में समग्र रूट द्वारा डोमेन नियम लागू करना चाहिए।
Arash

2
@ क्रैश सेट सत्यापन मुश्किल है, और अक्सर DDD के साथ अच्छा नहीं खेलता है। आप या तो यह सत्यापित करने के लिए छोड़ दिए जाते हैं कि कुछ प्रक्रिया उस प्रक्रिया (a ) को जोड़ने से पहले काम करेगी User, या स्वीकार करेगी कि इस विशिष्ट प्रकार का अपरिवर्तनीयता आपके डोमेन में बड़े करीने से कूटबद्ध नहीं होगा। पूर्व डेटा और व्यवहार के पृथक्करण का प्रतिनिधित्व करता है जिसके परिणामस्वरूप एक प्रक्रियागत प्रतिमान होता है। यह आदर्श से कम है। सत्यापन डेटा के साथ मौजूद होना चाहिए , डेटा के आसपास नहीं । इसके अलावा, एक डोमेन सेवा बनाने के लिए क्या लाभ है जो केवल इस एक नियम की जांच करने के लिए कार्य करता है? मूल रूप से, यह सेवा ...
राजा-साइड-स्लाइड

2
@ अराश जोड़े अपने Repository, Userऔर इस अजेय और इसलिए उस पवित्र दृष्टि को प्राप्त नहीं करते हैं जिसे आप वैसे भी ढकेल रहे हैं। रिपॉजिटरी कार्यान्वयन डोमेन का हिस्सा है, और इसलिए इसे कुछ जिम्मेदारियां दी जा सकती हैं।
राजा-पक्ष-स्लाइड

0

आप अपने आवेदन की हर परत में सत्यापन कर सकते हैं। कौन से नियम आपके आवेदन पर निर्भर करते हैं।

उदाहरण के लिए, संस्थाएँ उन विधियों को लागू करती हैं जो व्यावसायिक नियमों का प्रतिनिधित्व करती हैं जबकि उपयोग-मामले आपके आवेदन के लिए विशिष्ट नियमों को लागू करते हैं।

यदि आपकी ई-मेल जैसी ई-मेल सेवा का निर्माण हो सकता है, तो यह तर्क दिया जा सकता है कि नियम "उपयोगकर्ताओं को एक अद्वितीय ई-मेलड्रेस होना चाहिए" एक व्यावसायिक नियम है।

यदि आपका निर्माण एक नई CRM प्रणाली के लिए पंजीकरण प्रक्रिया का उपयोग करता है, तो यह नियम उपयोग-मामले में सबसे अच्छा कार्यान्वित किया जाता है क्योंकि यह नियम आपके उपयोग-मामले का भी हिस्सा होने की संभावना है। इसके अलावा, यह परीक्षण करना भी आसान हो सकता है क्योंकि आप आसानी से अपने उपयोग के मामले में रिपॉजिटरी कॉल को स्टब कर सकते हैं।

सशर्त सुरक्षा के लिए, आप इस नियम को अपनी रिपॉजिटरी में भी लागू कर सकते हैं।

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.