haskell / aeson

A fast Haskell JSON library
Other
1.25k stars 321 forks source link

Make Sum type encoder more flexible #1050

Open yaitskov opened 1 year ago

yaitskov commented 1 year ago

Hi,

I just noticed a mismatch in enconding conventions between Argounaut (PureScript) and Aeson.

Argounaut always wraps content into sub object with "content" key, when sum type is serialized, mean while Aeson does that only for constructors without named slots! So I have to drop names in Haskell source code and define lenses manually!

There are some tickets about Sum type encoder and I think this one won't be the last. Sum encoder should be more configurable. I agree PureScript encoding might be less compact, but PureScript community is smaller.

I would add following data constructor to SumEncoding:

| SnowFlakeTag (Text -> Value -> Value)

Then original encoding logic for TaggedObject might be expressed like that:

originalLogic :: Text -> Value -> Value
originalLogic dcName (Object encodedContent) = 
  Object $ insertWith keepOldAsItWouldBeOverwritten "tag" (String dcName) encodedContent
  where
    keepOldAsItWouldBeOverwritten _new old = old

and Argonaut case:

argonautLogic :: Text -> Value -> Value
argonautLogic dcName encodedContent = 
  Object $ fromList [ ("tag", String dcName), ("content", encodedContent) ]
phadej commented 1 year ago
| PostProcessBody (Text -> Value -> Value)

is no go. See toEncoding, there is no intermediate Values.

About configurability: #933. The current swiss-knife approach is not maintainable.

yaitskov commented 1 year ago

there is no intermediate Values.

I anticipated that it could be a alternative encoding branch - less efficient - this DC is an escape hatch first.

I was lucky and figured out that on PureScript side was easier to fix the issue, but in case of no power to change encoding format what are the options? An HTTP interceptor with Lua script on nginx rewriting JSON or bash+jq for files?

https://github.com/garyb/purescript-codec-argonaut/issues/59