2012-12-12 10 views
6

मैं data रिकॉर्ड कर रहा हूं JIRAJSON ऑब्जेक्ट को मार्शल करने के लिए रिकॉर्ड। समस्या यह है कि, एकाधिक ऑब्जेक्ट्स में नाम/मान जोड़े के लिए समान लेबल होते हैं।हास्केल नाम स्थान से कैसे निपटें?

(कर्ल से लौटे और स्वरूपित)

{"expand":"schema,names" 
,"startAt":0 
,"maxResults":2 
,"total":74 
,"issues":[ 
      {"expand":"editmeta,renderedFields,transitions,changelog,operations" 
      ,"id":"183614" 
      ,"self":"https://10.64.16.44/rest/api/latest/issue/183614" 
      ,"key":"BNAP-339" 
      ,"fields":{"versions":[ 
            {"self":"https://10.64.16.44/rest/api/2/version/28240" 
            ,"id":"28240" 
            ,"name":"2012-12-07" 
            ,"archived":false 
            ,"released":false 
            } 
           ] 
        ,"status":{"self":"https://10.64.16.44/rest/api/2/status/1" 
           ,"description":"The issue is open and ready for the assignee to start work on it." 
           ,"iconUrl":"https://10.64.16.44/images/icons/status_open.gif" 
           ,"name":"Open" 
           ,"id":"1" 
           } 
        ,"description":"Do Re Mi Fa" 
        ,"resolution":null 
        } 
      } 
      ] 

जब मैं समस्याग्रस्त इसी हास्केल data रिकॉर्ड मैं का निर्माण:

data Issue = Issue {expand :: String 
        ,id :: String 
        ,self :: String 
        ,key :: String 
        ,fields :: Fields 
        } deriving Generic 


data Version = Version {self :: String 
         ,id :: String 
         ,name :: String 
         ,archived :: Bool 
         ,released :: Bool 
         } deriving Generic 

और 'आईडी' और 'स्वयं' संघर्ष होगा उदाहरण के लिए । यह मेरे लिए हुआ, मैं रिकॉर्ड में नामों को बदलकर इसे मैन्युअल रूप से बनाए गए FromJSON उदाहरण के साथ ठीक करके इसे हल कर सकता हूं। किसी भी वैकल्पिक समाधान का स्वागत किया जाएगा।

उत्तर

10

मैं उसी पदानुक्रम में अलग फ़ाइलों में Issue और Version जैसी चीजों को डालकर प्रोटोकॉल बफर में इसे हल करता हूं।

हास्केल केवल नामस्थानों को नियंत्रित करने के लिए अलग-अलग मॉड्यूल का उपयोग करता है, इसलिए यह रूढ़िवादी समाधान है।

बहुत ज्यादा अधिक सजावटी: उपयोग प्रकार कक्षाएं उपलब्ध नाम निर्धारित करने के लिए:

class Has'self a b | a -> bwhere 
    get'self :: a -> b 
    set'self :: b -> a -> b 

instance Has'self Issue String where ... 
instance Has'self Version String where .... 

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

पीएस: शायद आप अपने क्षेत्रों के लिए lens लाइब्रेरी का उपयोग कर सकते हैं!

+7

ध्यान दें कि 'HasFoobar' शैली typeclasses जब यह साफ है, अच्छी तरह से संरचित हास्केल कोड लिखने की बात आती है लगभग हमेशा एक भयानक विचार कर रहे हैं: उदाहरण के लिए, निम्न डेटा प्रकार क्षेत्र संघर्ष के बिना अपने मूल्य का प्रतिनिधित्व करने में सक्षम है। लेकिन इंटरऑप प्रयोजनों के लिए गैर-हास्केल कोड की संरचना से मेल खाने का प्रयास करते समय, यदि दूसरी तरफ अधिभारित कार्यों और/या उप प्रकार के पदानुक्रमों पर भारी निर्भर करता है, तो कोई बेहतर दृष्टिकोण नहीं हो सकता है। –

+0

मैं उस भाग को ऊपर उठा रहा हूं जहां आपने अलग-अलग फाइलों की सिफारिश की थी। कक्षाओं को खराब नामस्थान समाधान के लिए टाइप करें क्योंकि उपयोगकर्ताओं के प्रकारों के कारण वे बहुत मुश्किल हैं और चुपचाप असफल हो जाएंगे और गलत प्रकार पर लागू होने पर गलत चीज करेंगे। –

3

एक और विकल्प जो काम करना चाहिए वह एक अलग डेटा प्रकार का उपयोग करना है जिसमें विशिष्ट रिकॉर्ड हैं।

import Prelude hiding (id) 

data JIRA = JIRA 
    { expand :: String 
    , startAt :: Int 
    , maxResults :: Int 
    , total :: Int 
    , issues :: [JIRA] 
    } | Issue 
    { expand :: String 
    , id :: Int 
    , self :: String 
    , key :: String 
    , fields :: JIRA 
    } | Field 
    { versions :: [JIRA] 
    , status :: JIRA 
    , description :: String 
    , resolution :: Maybe String 
    } | Version 
    { self :: String 
    , id :: Int 
    , name :: String 
    , archived :: Bool 
    , released :: Bool 
    } | Status 
    { self :: String 
    , description :: String 
    , iconUrl :: String 
    , name :: String 
    , id :: Int 
    } 


yourExample = JIRA 
    { expand = "schema, names" 
    , startAt = 0 
    , maxResults = 2 
    , total = 74 
    , issues = [ Issue 
       { expand = "editmeta, etc..." 
       , id = 12345 
       , self = "https://xyz" 
       , key = "BLAH" 
       , fields = Field 
          { versions = [ Version 
              { self = "https://foobar" 
              , id = 1234 
              , name = "quux" 
              , archived = False 
              , released = False 
              } 
             ] 
          , status = Status 
            { self = "https://etc" 
            , description = "issue" 
            , iconUrl = "https://iconurl" 
            , name = "open" 
            , id = 1 
            } 
          , description = "another description" 
          , resolution = Nothing 
          } 
       } 
       ] 
    } 
+0

ध्यान दें कि उपरोक्त केवल तभी काम करता है जब सभी 'आईडी' एक ही प्रकार ('Int') हैं और सभी 'स्वयं' एक ही प्रकार (' स्ट्रिंग') आदि हैं। –

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