Haskell:带有aeson的动态对象字段名称

时间:2016-06-20 11:23:27

标签: json haskell aeson

如果我的数据结构从readFile获取两个值;如何将这些值用作我的toJSON实例声明的字段名?

例如,在下面的代码中,名称“2015”和“2016”将根据输入文件进行更改。

data MyOutput = MyOutput
              { periodOne   :: YearInfo
              , periodTwo   :: YearInfo
              , updateStamp :: String
              } deriving (Show)

instance ToJSON MyOutput where
  toJSON MyOutput {..} =
    object [ "2015"       .= periodOne
           , "2016"       .= periodTwo
           , "Data up to" .= updateStamp
           ]

1 个答案:

答案 0 :(得分:3)

不幸的是,ToJSON个实例不能依赖于数据结构外部的值。

我的建议是更改数据结构以包含periodOneperiodTwo的字段名称:

data MyOutput = MyOutput {
                  periodOneName, periodTwoName :: String,
                  periodOne, periodTwo :: YearInfo
                  ...
              }

现在toJSON实例可以访问句点的名称。

完整示例:

{-# LANGUAGE RecordWildCards #-}
{-# LANGUAGE OverloadedStrings #-}

import Data.Aeson
import qualified Data.Text as T

type YearInfo = [ Int ]

data MyOutput = MyOutput
              { periodOne   :: YearInfo
              , periodTwo   :: YearInfo
              , periodOneName :: T.Text
              , periodTwoName :: T.Text
              , updateStamp :: String
              } deriving (Show)

instance ToJSON MyOutput where
  toJSON MyOutput {..} =
    object [ periodOneName .= toJSON periodOne
           , periodTwoName .= toJSON periodTwo
           , "Data up to"  .= toJSON updateStamp
           ]