Safe Haskell | None |
---|---|
Language | Haskell2010 |
Synopsis
Quickstart
Assume some example data below:
>>>
data ExampleUser = ExampleUser { name :: String, age :: Int } deriving (Show, Eq, Generic)
>>>
instance ToJSON ExampleUser
>>>
instance FromJSON ExampleUser
>>>
data ExampleUserWithMessages = ExampleUserWithMessages { name :: String, age :: Int, messages :: [Int] } deriving (Show, Eq, Generic)
>>>
instance ToJSON ExampleUserWithMessages
>>>
instance FromJSON ExampleUserWithMessages
>>>
let aliceName = "Alice"
>>>
let aliceAge = 25
>>>
let messageIds = [102, 305, 410]
>>>
let alice = ExampleUser aliceName aliceAge
>>>
let aliceWithMessages = ExampleUserWithMessages aliceName aliceAge messageIds
Let's add those messages to the alice object without requiring our custom WithMessages version of the User type.
>>>
let adHocAliceWithMessages = alice :<> (asValue messageIds :: Association "messages" [Int])
>>>
encode aliceWithMessages == encode adHocAliceWithMessages
True
Since "messages" is type (not value) information, we can decode as well.
>>>
decode "{\"age\":25,\"name\":\"Alice\",\"messages\":[102,305,410]}" :: Maybe (ExampleUser :<> Association "messages" [Int])
Just (ExampleUser {name = "Alice", age = 25} :<> Association Proxy [102,305,410])
In the above, Proxy is the value of type "messages".
Association Proxy a
has a stand-alone encoding/decoding too
>>>
encode $ Association (Proxy :: Proxy "one-off-key") [1, 2, 3]
"{\"one-off-key\":[1,2,3]}"
>>>
decode "{\"one-off-key\":[1,2,3]}" :: Maybe (Association "one-off-key" [Int])
Just (Association Proxy [1,2,3])
You can build JSON objects from just values!
>>>
:{
let allValues :: Association "name" String :<> Association "age" Int allValues = asValue aliceName :<> asValue aliceAge in encode allValues == encode alice :} True
Decoding fails if you specify a non-existent key (standard Aeson behavior for failed decoding).
>>>
decode "{\"one-off-key\":[1,2,3]}" :: Maybe (Association "wrong-key" [Int])
Nothing
If you try encoding with a "base" value that is itself not encoded to a JSON object you'll get a runtime exception.
>>>
encode $ True :<> (asValue [1,2,3] :: Association "this-ends-poorly" [Int])
"*** Exception: JsonObjectEncodingException (Bool True)
GHC Extension Note:
- You'll need
DataKinds
for this library (type level literals, no getting around this). - You'll probably want
TypeOperators
as well (although you can useWithAssociation
instead of:<>
to avoid this). - You can avoid
PolyKinds
if you useasValue True :: Association "key" Bool
or type inference instead ofAssociation (Proxy :: Proxy "key") True
.
Re-Exported Core Types/Functions/Lens
module Data.ComposableAssociation
Invalid JSON Encoding Exception
newtype JsonObjectEncodingException Source #
More specific version of ObjectEncodingException
to only Aeson encoding issues.