在Haskell中使用aeson的通用解析器进行严格的yaml解析

时间:2014-09-19 20:02:47

标签: parsing haskell yaml

我使用yaml包将.yaml文件解析为Haskell data结构。由于我有很多data个对象,我使用泛型来避免编写"解析器"每一次。这看起来像

instance ToJSON MyData where
 toJSON = genericToJSON defaultOptions

然而,解析不是"严格"足够的,即解析器默默地忽略.yaml文件中存在的字段,但在data结构中没有对应关系。是否有一种简单的方法可以触发某种错误,如果"未知"密钥存在于.yaml文件中?

2 个答案:

答案 0 :(得分:2)

yaml本身绝对不存在此功能,因为yaml不提供用于派生ToJSONFromJSON实例的任何代码。据我所知,aeson没有提供您正在寻找的功能。如果为true,则必须手动编写实例。

答案 1 :(得分:-1)

下面是我为解决问题而编写的代码的简化版本。通过parseJSON = strictParseYaml使用。

import Data.HashMap.Strict (member,insert,keys)

strictParseYaml xs =
 do
  parsed <- genericParseJSON defaultOptions xs
  let diff = minus (keysOfValue xs) (keysOfData parsed)
  return $
   if diff == [] then
    parsed
   else
    error $ "Found unknown keys: " ++ show diff

 where
  keysOfData u = sort $ constrFields $ toConstr u

  keysOfValue :: Value -> [String]
  keysOfValue (Object xs) = sort $ map unpack $ keys xs