on master help sign in
Add Decode.oneOf
b737fa0Evan Czaplicki
src/Json/Decode.hs+26−1
@@ -6,7 +6,7 @@ module Json.Decode
6 , list, dict, maybe
6 , list, dict, maybe
7 , field, at
7 , field, at
8 , index
8 , index
9− , map, map2, succeed, fail, andThen
9+ , map, map2, succeed, fail, andThen, oneOf
10 )
10 )
11 where
11 where
12
12
@@ -37,6 +37,7 @@ data Decoder a =
37data Error
37data Error
38 = Field Text Error
38 = Field Text Error
39 | Index Int Error
39 | Index Int Error
40+ | OneOf [Error]
40 | Failure Aeson.Value String
41 | Failure Aeson.Value String
41
42
42
43
@@ -269,3 +270,27 @@ andThen callback (Decoder runA) =
269 do a <- runA mkError value
270 do a <- runA mkError value
270 let (Decoder runB) = callback a
271 let (Decoder runB) = callback a
271 runB mkError value
272 runB mkError value
273+
274+
275+
276+-- ONE OF
277+
278+
279+oneOf :: [Decoder a] -> Decoder a
280+oneOf decoders =
281+ Decoder (oneOfHelp decoders [])
282+
283+
284+oneOfHelp :: [Decoder a] -> [Error] -> (Error -> Error) -> Aeson.Value -> Either Error a
285+oneOfHelp decoders errors mkError value =
286+ case decoders of
287+ [] ->
288+ Left (mkError (OneOf (reverse errors)))
289+
290+ Decoder run : otherDecoders ->
291+ case run mkError value of
292+ Right a ->
293+ Right a
294+
295+ Left err ->
296+ oneOfHelp otherDecoders (err:errors) mkError value