Created
May 14, 2016 04:53
-
-
Save queertypes/daad733400f0ef98c74568eee7b7dc88 to your computer and use it in GitHub Desktop.
JSON data model in Haskell (mostly from scratch) with a compact printing function
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
{-# LANGUAGE OverloadedStrings #-} | |
module Json ( | |
Value, | |
-- core API | |
true, false, nil, number, text, array, object, | |
-- utils and demo | |
objects, (.:), jprint, run | |
) where | |
import Data.Monoid | |
-- need a few non-std imports for efficiency | |
-- e.g.: Never use String in Haskell | |
import Data.Text (Text, unpack, pack, intercalate) | |
import Data.Map.Strict (Map, foldlWithKey', empty, insert, toList) | |
-- core data type | |
data Value | |
= Null | |
| JBool Bool | |
| JNumber Double | |
| JString Text | |
| JArray [Value] | |
| JObject Object | |
-- convenience wrapper | |
newtype Object = Object (Map Text Value) | |
-- convenience functions | |
array = JArray | |
true = JBool True | |
false = JBool False | |
number = JNumber | |
text = JString | |
nil = Null | |
object = JObject | |
objects :: Object | |
objects = Object empty | |
infixl 5 .: | |
(.:) :: Object -> (Text,Value) -> Object | |
(Object o) .: (k,v) = Object (insert k v o) | |
jprint :: Value -> Text | |
jprint val = | |
case val of | |
Null -> "null" | |
(JBool x) -> if x then "true" else "false" | |
(JNumber x) -> pack (show x) | |
(JString x) -> x | |
(JArray xs) -> "[" <> intercalate "," (map jprint xs) <> "]" | |
(JObject o) -> "{" <> pprintMap o <> "}" | |
where pprintMap (Object m) = | |
intercalate "," (map (\(k,v) -> k <> ":" <> jprint v) $ toList m) | |
run :: IO () | |
run = | |
let objs = object (objects .: ("foo", text "FOO") .: ("bar", text "BAR")) | |
val = JArray [objs, number 3, nil, true, false] | |
in print (jprint val) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Uses this
json.cabal
file: