2013-08-02 18 views
7

सुरक्षित & बेहतर & क्लीनर & अधिक उपयोग करने की अनुशंसा की जाती है?कोशिश :: छोटे या Eval का उपयोग कर?

मैं प्रयोग किया है:

sub insert_exec { 
    my ($self, $c, $args) = @_; 
    my ($params, $table, $model) = $self->_init({context => $c, args => $args}); 
    eval { $model->insert($table, $params); 
    }; 
    if ([email protected]) { return $c->show_error([email protected]); } ## error 
    $c->redirect("/index"); 
} 

लेकिन मामलों के इस प्रकार (त्रुटि भाग देखें) के लिए, मैं कोशिश :: छोटे बेहतर है का उपयोग करते हुए कि कहा गया है?

मेरा प्रश्न है: आप इसे कैसे लिखेंगे और आप इस तरह क्यों चुनेंगे?

उत्तर

10

अद्यतन

एक अनाम उपयोगकर्ता मैं अपने जवाब में एक बग को सही करने में सक्षम है के लिए धन्यवाद। catch ब्लॉक में वांछित प्रभाव नहीं था, क्योंकि यह केवल catch सबराउटिन से लौटा था।

यदि कोई अपवाद नहीं था, trytry ब्लॉक का मान देता है, अन्यथा catch ब्लॉक का मान। तो insert सफल होने पर यह संस्करण सही ढंग से निष्पादित करता है और $c->redirect("/index") का मान देता है, अन्यथा यह $c->show_error($_) का मान देता है और देता है।

sub insert_exec { 
    my ($self, $c, $args) = @_; 
    my ($params, $table, $model) = $self->_init({context => $c, args => $args}); 
    try { 
    $model->insert($table, $params); 
    $c->redirect("/index"); 
    } 
    catch { 
    $c->show_error($_); 
    }; 
} 

Try::Tiny काफी के रूप में eval साथ निपटने त्रुटि सही सामान्य स्थिति में पाने के लिए वास्तव में बहुत कठिन है आवश्यक है। मॉड्यूल के प्रलेखन का कहना है कि यह

यह मॉड्यूल बेयर हड्डियों को कोशिश/पकड़/आखिरकार बयान प्रदान करता है जो eval ब्लॉक के साथ सामान्य गलतियों को कम करने के लिए डिज़ाइन किए गए हैं, और कुछ भी नहीं।

इस मॉड्यूल का मुख्य फोकस उन लोगों के लिए सरल और विश्वसनीय त्रुटि प्रबंधन प्रदान करना है जो अभी भी बॉयलरप्लेट की 5 लाइनों के बिना सही eval ब्लॉक लिखना चाहते हैं।

आपका कोड इस

use Try::Tiny; 

sub insert_exec { 
    my ($self, $c, $args) = @_; 
    my ($params, $table, $model) = $self->_init({context => $c, args => $args}); 
    try { 
    $model->insert($table, $params); 
    } 
    catch { 
    return $c->show_error($_); 
    }; 
    $c->redirect("/index"); 
} 

कैसा दिखेगा जो मुझे आशा है कि आप इस बात से सहमत हूँ बहुत अच्छे है।

दो अंक उल्लेखनीय हैं:

  • try और catchसबरूटीन्स भाषा शब्द की तरह लग रहे करने के लिए कोडित रहे हैं। इसका मतलब अंतिम समापन ब्रेस के बाद एक अर्धविराम आवश्यक है।

  • उसी कारण से, returntry या catch ब्लॉक के भीतर अपेक्षा के अनुरूप काम नहीं होगा, और बस ब्लॉक बाहर निकल जाएगा, माता पिता सबरूटीन की ओर लौटने। ऊपर मेरा अपडेट देखें।

  • catch ब्लॉक [email protected] के भीतर try से पहले इसका मूल मूल्य है। त्रुटि से उत्पन्न मूल्य $_

+0

यह वास्तव में बहुत अच्छा है – ado

+0

एक * अज्ञात उपयोगकर्ता * जिसने टिप्पणी पोस्ट करने के लिए अपर्याप्त प्रतिष्ठा थी, इस पाठ को जोड़ने के लिए मेरे उत्तर को संपादित करने का प्रयास किया। यह एक बहुत अच्छा मुद्दा है और मैंने एक उचित अद्यतन किया है। * 'Try :: Tiny' के साथ निर्माण अच्छा है लेकिन मूल पोस्ट से काफी अलग है। जैसा कि आपने लिखा है और ब्लॉक को पकड़ने के लिए सबराउटिन हैं, इस प्रकार कैच के अंदर वापसी केवल 'insert_exec' से नहीं, अज्ञात उप से होती है। इसका मतलब है कि अपवाद के मामले में रीडायरेक्ट भी किया जाता है। यह 'ट्री :: टिनी' का एक आम नुकसान है। * – Borodin

4

Try::Tiny का उपयोग नहीं करते हुए आपको अतिरिक्त निर्भरता बचाती है।

इसका उपयोग करके आप कोड लिखने की अनुमति देते हैं जो पर्ल मुहावरे के ज्ञान के बिना समझ में आता है (उन्हें उद्योग में अधिक सामान्य रूप से मान्यता प्राप्त शर्तों के साथ बदलकर)।

आपको यह तय करने की आवश्यकता है कि उनमें से कौन सा आपके लिए अधिक मूल्यवान है, क्योंकि उनके सापेक्ष मूल्य को व्यावहारिक रूप से मापना मुश्किल है।

1

यह त्रुटियों संकेत करने के लिए, लेकिन सिर्फ त्रुटि संदेशों में से स्रोत के रूप में उपयोग करने के लिए [email protected] पर निर्भर नहीं सबसे अच्छा है में है, इसलिए मैं के रूप में यह लिखा है:

my $success = eval { $model->insert($table, $params) }; 
unless ($success) { 
    return $c->show_error([email protected]); 
} 

आप कुछ है कि सफलता पर एक सच्चे मूल्य वापस नहीं हो सकता है, तो eval'ing रहे हैं:

my $success = eval { $model->insert($table, $params); 1 }; 

मैं शायद :: टिनी प्रयास करें जब चीजें अधिक जटिल हो प्रयोग करेंगे इससे, उदाहरण के लिए, फ़ंक्शन एक मान देता है जिसे आप सहेजना चाहते हैं, लेकिन हो सकता है कि यह एक वास्तविक मान न हो (या परिभाषित भी न हो), और आप अपवादों को पकड़ना चाहते हैं।

संबंधित मुद्दे