2016-06-21 11 views
39

तो, मैं क्लोजर एसपीसी में गहरा और गहराई से डाइविंग कर रहा हूं।Clojure.Spec के लिए चश्मा कहां रखा जाए?

एक चीज जिस पर मैंने ठोकर खाई, जहां मेरी चश्मा डाली गई है। मैं तीन विकल्प देखें:

वैश्विक युक्ति फ़ाइल

सबसे उदाहरण में, मैं ऑनलाइन पाया, एक बड़ा spec.clj फ़ाइल, मुख्य नाम स्थान में आवश्यक हो जाता है कि वहाँ है। इसमें सभी "डेटा प्रकार" और कार्यों के लिए सभी (s/def) और (s/fdef) हैं।

प्रो:

  • एक फ़ाइल उन्हें शासन करने के लिए सभी

कॉन्ट्रा:

  • इस फ़ाइल में बड़ा हो सकता है
  • एकल Responsibliy सिद्धांत का उल्लंघन किया?

उत्पादन नामस्थान

में चश्मा आप डाल सकता है आपके (s/def) और (s/fdef) सही अपने उत्पादन कोड के बगल में। इसलिए, कार्यान्वयन और spec एक ही नामस्थान में सह-अस्तित्व में है।

प्रो:

  • कार्यान्वयन और कल्पना के सह स्थान
  • एक नाम स्थान - एक चिंता का विषय है?

कॉन्ट्रा:

  • उत्पादन कोड गन्दा
  • एक नाम स्थान मिल सकता है - दो चिंताएं हैं?

समर्पित कल्पना नाम स्थान संरचना

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

├─ src 
│  └─ package 
│   ├─ a.clj 
│   └─ b.clj 
├─ test 
│  └─ package 
│   ├─ a_test.clj 
│   └─ b_test.clj 
└─ spec 
  └─ package 
      ├─ a_spec.clj 
      └─ b_spec.clj 

प्रो:

  • समर्पित (लेकिन संबंधित) चश्मा के लिए नामस्थान

कॉन्ट्रा:

  • आपको स्रोत नाम देना होगा और सही नामस्थानों की आवश्यकता होगी

किसके दृष्टिकोण में से एक का अनुभव है?
क्या कोई और विकल्प है?
आप विभिन्न विकल्पों के बारे में क्या सोचते हैं?

उत्तर

14

मैं आमतौर पर नामस्थान के साथ-साथ अपने नामस्थान में चश्मा डालता हूं। यह विशेष रूप से कोई फर्क नहीं पड़ता कि उनका नाम क्या है, जब तक कि वे कुछ सुसंगत नामकरण सम्मेलन का उपयोग करते हैं। उदाहरण के लिए, यदि मेरा कोड my.app.foo में है, तो मैं my.app.foo.specs में चश्मा डालूंगा।

spec कुंजी नाम कोड के नामस्थान में होना बेहतर है, हालांकि, spec का नामस्थान नहीं है।

(ns my.app.foo.specs 
    (:require [my.app.foo :as f])) 

(s/def ::f/name string?) 

मैं (। क्या एक बुरा सपना) एक विशाल कल्पना नाम स्थान में सब कुछ डाल करने के लिए एक ओर जहां मैं निश्चित रूप से उन्हें सही डाल सकता है की कोशिश कर रहा से दूर रहना चाहते हैं: यह अभी भी कीवर्ड पर नाम स्थान उर्फ ​​का उपयोग करके करना आसान है उसी फ़ाइल में spec'd कोड के साथ, जो पठनीयता आईएमओ दर्द होता है।

आप एक अलग स्रोत पथ में अपने सभी कल्पना नामस्थान डाल सकता है, लेकिन ऐसा करने के लिए कोई वास्तविक लाभ है जब तक आप एक स्थिति में हैं, जहां आप लेकिन कोड वितरित करना चाहते हैं नहीं चश्मा या ठीक इसके विपरीत .. कल्पना करना मुश्किल है कि हालांकि क्या होगा।

+5

[अलग नामस्थान में होने पर विनाश के लिए चश्मा का उपयोग करके] [http://stackoverflow.com/q/38024650/5044950) के लिए आपकी सलाह क्या होगी? –

+1

@levand सैम एस्टेप ने अपने प्रश्न में एक अच्छा मुद्दा बनाया है कि आप इसे पार्सिंग के लिए इस्तेमाल करने के लिए लोड किए जा रहे एक स्पेक पर भरोसा नहीं कर सकते हैं क्योंकि यदि आपको पहले से ही अपने एनएस की आवश्यकता है तो आपको spec ns की आवश्यकता नहीं हो सकती है। तो शायद एक '(लोड "मेरा/ऐप/foo_specs")/(in-ns' my.app.foo) ('[clojure.spec: as s] की आवश्यकता है)' कोई अलग एनएस के साथ एक बेहतर पैटर्न होगा यदि आप पठनीयता –

+1

के लिए एक अलग फ़ाइल में चश्मा चाहते हैं यह एक अच्छा बिंदु है ... ऐसी स्थितियां हैं जहां आप अपने कार्यान्वयन नेमस्पेस को अपने स्पेस नेमस्पेस पर निर्भर करते हैं, जिसका तात्पर्य है कि आपका spec ns * impl * n पर निर्भर नहीं हो सकता है। वर्तमान में, इसे हल करने का कोई अच्छा तरीका नहीं है - सबसे अच्छा सिर्फ spec में पूरी तरह से योग्य नामस्थान नाम टाइप करना होगा। सौभाग्य से, कार्यों में कुछ बदलाव हैं जो आपको उन नामस्थानों को उपनाम करने की अनुमति देंगे जिन्हें अभी तक लोड/आवश्यक नहीं किया गया है, जो इस समस्या को अच्छी तरह से हल करना चाहिए। – levand

6

आपके उपयोग के मामले के आधार पर एक अन्य विचार - अपने मुख्य कोड सीमाओं के साथ चश्मे को क्लोजर 1.9 क्लाइंट्स के लिए अपने कोड का उपयोग करना, जो आप चाहते हैं या नहीं हो सकता है। @levand की तरह, मैं आपके प्रत्येक कोड नामस्थान के लिए समांतर नामस्थान की अनुशंसा करता हूं।

10

मेरी राय में चश्मा कोड के समान एनएस में होना चाहिए।

मेरा मुख्य विचार मेरा व्यक्तिगत दर्शन है, और तकनीकी रूप से यह अच्छी तरह से काम करता है। मेरा दर्शन यह है कि एक समारोह का spec अभिन्न हिस्सा है। यह एक अतिरिक्त बात नहीं है। यह निश्चित रूप से ओपी में डाले गए "दो चिंताओं" नहीं है। दरअसल, यह कार्य है, क्योंकि शुद्धता के मामले में: कौन कार्यान्वयन की परवाह करता है? जो आपके defn में आपने जो लिखा है उसकी परवाह करता है? पहचानकर्ता के बारे में कौन परवाह करता है? कुछ भी परवाह करता है लेकिन कल्पना?
मुझे लगता है कि यह अजीब है क्योंकि न केवल clojure.spec बाद में आया था, अधिकांश भाषाएं आपको चश्मे को एक अभिन्न चीज़ के रूप में नहीं होने देगी, भले ही आप इसे चाहते थे, और कुछ भी करीब (कोड में परीक्षण) आमतौर पर फहराया जाता है , तो निश्चित रूप से यह अजीब लगता है। लेकिन इसे कुछ विचार दें, और आप एक निष्कर्ष तक पहुंच सकते हैं जैसे मैंने किया (या आप नहीं कर सकते हैं, इस भाग की राय है)।

  1. यह अपने कोड clutters:

    केवल अच्छे कारणों मैं क्यों आप एक ही एनएस में चश्मा नहीं चाहता है के रूप में सोच सकते हैं इन दो कारण हैं।

  2. आप क्लोजर संस्करणों को क्लोजर 1.9.0 का समर्थन करना चाहते हैं।

पहले कारण के रूप में, ठीक है, मुझे लगता है कि यह आपके कार्यों का एक अभिन्न अंग है। यदि आपको लगता है कि यह वास्तव में बहुत अधिक है, तो मेरी सलाह उतनी ही होगी जैसे कि आपकी एनएस स्पेक के बावजूद बहुत अव्यवस्थित हो जाएगी: देखें कि क्या आप इसे विभाजित कर सकते हैं।

दूसरे कारण के लिए, यदि आप वास्तव में परवाह करते हैं, तो क्लोजर.spec ns उपलब्ध होने पर आप कोड में जांच सकते हैं, यदि नहीं तो एनओपी वाले कार्यों/मैक्रोज़ के नामों को छाया दें। एक और विकल्प clojure-future-spec का उपयोग करना है, लेकिन मैंने इसे स्वयं नहीं किया है इसलिए मुझे नहीं पता कि यह कितना अच्छा काम करता है।

यह एक और तरीका है जो तकनीकी रूप से अच्छी तरह से काम करता है यह कभी-कभी एक चक्रीय निर्भरता है जिसे आप अलग-अलग नामस्थानों से संभाल नहीं सकते हैं, उदा। जब आपकी चश्मा आपके कोड (फ़ंक्शन चश्मे के लिए) पर निर्भर करती है और आपका कोड पार्सिंग के लिए आपके चश्मे पर निर्भर करता है (यह question देखें)।

+2

मुझे लगता है कि मैं इसके साथ सहमत हूं। Spec पर तर्क लेख दस्तावेज का एक पहलू के रूप में उल्लेख करता है। यदि आप उन्हें कोड से कहीं दूर रखते हैं, तो आप उस लाभ को खो चुके हैं। –

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