, , . JSON , , , .
. , , .
, FromJSON Text [a]. - Alternative :
instance FromJSON Foo where
parseJSON v = (SimpleText <$> parseJSON v)
<|> (ListOfText <$> parseJSON v)
<|> (ListOfListOfText <$> parseJSON v)
, Aeson Text, , , [Text], , [[Text]].
, , JSON , . , Null , , [[Text]], .
, , . , , ListOfText ListOfListOfText? Vector , :
instance FromJSON Foo where
parseJSON v = case v of
-- If its a string, we return the string as a SimpleText
(String s) -> return $ SimpleText s
-- If its an array, we turn the vector to a list so we can pattern match on it
(Array a) -> case V.toList a of
-- If its a empty list, we return a empty ListOfText
[] -> return $ ListOfText []
-- If the first value is a string, we put it as the first element of our ListOfTexts and try to parse the rest.
(String s: xs) -> ListOfText . (s:) <$> mapM parseJSON xs
-- If the first value is an array, we try to parse it as [Text], then parse the rest.
(Array a: xa) -> ListOfListOfText <$> ((:) <$> parseJSON (Array a) <*> mapM parseJSON xa)
-- If the first value is neither a string or array we return a error message.
_ -> fail "Expected an Array or an Array of Arrays."
-- If the top level value is not a string or array we return a error message.
_ -> fail "Expected a String or Array"