2017-03-02 40 views
0

我最近開始與Haskell玩,似乎無法找出這一個。Haskell從YAML文件中讀取嵌套的時間戳

我試圖從具有這種格式的YAML文件讀取:

id: 1 
kind: good 
created_at: !ruby/object:ActiveSupport::TimeWithZone 
    utc: &1 2017-01-01 10:34:12.533704000 Z 
    zone: &2 !ruby/object:ActiveSupport::TimeZone 
    time: *2 

到目前爲止,我可以做這個讀取ID和那種完美的罰款:

data Item= Item{ 
    id :: Integer, 
    kind::String 
    } 

而且

instance FromJSON Item where 
    parseJSON(Object v) = Item <$> 
     v .: "id" <*> 
     v .: "kind" 

我正在使用軟件包「Data.Yaml」,此功能:
let items = Data.Yaml.decode ymlData :: Maybe[Item]

但我似乎無法弄清楚如何獲得時間戳。

什麼是獲得時間戳的正確方法,只需要「utc」。

+1

我看到的第一個問題是你必須大寫你的類型和構造函數,所以'data Item = Item ...'和'instance FromJSON Item where ...'。我認爲你的問題實際上是關於如何訪問嵌套元素,這是你真正想問什麼?這個問題似乎並不是關於獲取時間戳,而是關於如何在YAML中使用嵌套結構。 – bheklilr

+0

@bheklilr謝謝你的迴應,是的,你是對的。這個問題的確應該是:「如何訪問嵌套元素?」 – QuickQuestionGuy

+0

您是否使用[* yaml *包](https://hackage.haskell.org/package/yaml-0.8.9/docs/Data-Yaml.html)?如果是這樣,你應該在問題中提到它。 (順便說一下,你可以編輯它來添加說明。) – duplode

回答

2

最簡單的方法是創建一個newtype實現FromJSON

import Data.Time 
import Data.Yaml 

data Item = Item 
    { id :: Int 
    , kind :: String 
    , createdAt :: UTCTime 
    } deriving (Show) 

instance FromJSON Item where 
    parseJSON (Object v) = 
    Item <$> v .: "id" <*> v .: "kind" <*> v .: "created_at" 

newtype Time = Time String deriving (Show, Eq) 

instance FromJSON Time where 
    parseJSON (Object v) = Time <$> v .: "utc" 

希望有所幫助。

+2

值得注意的是['UTCTime'有一個'FromJSON'實例](https://hackage.haskell.org/package/aeson-1.1.0.0/docs/Data-Aeson.html#t:FromJSON),並且所以在'Time'的定義中用'UTCTime'替換'String'將會正常工作,不需要進一步的改變。 – duplode

+0

啊!感謝您指出了這一點。我沒有意識到。 – Erik

+0

@Erik這個作品,謝謝你的幫助! – QuickQuestionGuy