{-# LANGUAGE NoOverloadedStrings #-}
module Language.PureScript.CoreFn.ToJSON
( moduleToJSON
) where
import Prelude
import Control.Arrow ((***))
import Data.Either (isLeft)
import Data.Map.Strict qualified as M
import Data.Aeson (ToJSON(..), Value(..), object)
import Data.Aeson qualified
import Data.Aeson.Key qualified
import Data.Aeson.Types (Pair)
import Data.Version (Version, showVersion)
import Data.Text (Text)
import Data.Text qualified as T
import Language.PureScript.AST.Literals (Literal(..))
import Language.PureScript.AST.SourcePos (SourceSpan(..))
import Language.PureScript.CoreFn (Ann, Bind(..), Binder(..), CaseAlternative(..), ConstructorType(..), Expr(..), Meta(..), Module(..))
import Language.PureScript.Names (Ident, ModuleName(..), ProperName(..), Qualified(..), QualifiedBy(..), runIdent)
import Language.PureScript.PSString (PSString)
constructorTypeToJSON :: ConstructorType -> Value
constructorTypeToJSON :: ConstructorType -> Value
constructorTypeToJSON ConstructorType
ProductType = forall a. ToJSON a => a -> Value
toJSON String
"ProductType"
constructorTypeToJSON ConstructorType
SumType = forall a. ToJSON a => a -> Value
toJSON String
"SumType"
infixr 8 .=
(.=) :: ToJSON a => String -> a -> Pair
String
key .= :: forall a. ToJSON a => String -> a -> Pair
.= a
value = String -> Key
Data.Aeson.Key.fromString String
key forall kv v. (KeyValue kv, ToJSON v) => Key -> v -> kv
Data.Aeson..= a
value
metaToJSON :: Meta -> Value
metaToJSON :: Meta -> Value
metaToJSON (IsConstructor ConstructorType
t [Ident]
is)
= [Pair] -> Value
object
[ String
"metaType" forall a. ToJSON a => String -> a -> Pair
.= String
"IsConstructor"
, String
"constructorType" forall a. ToJSON a => String -> a -> Pair
.= ConstructorType -> Value
constructorTypeToJSON ConstructorType
t
, String
"identifiers" forall a. ToJSON a => String -> a -> Pair
.= Ident -> Value
identToJSON forall a b. (a -> b) -> [a] -> [b]
`map` [Ident]
is
]
metaToJSON Meta
IsNewtype = [Pair] -> Value
object [ String
"metaType" forall a. ToJSON a => String -> a -> Pair
.= String
"IsNewtype" ]
metaToJSON Meta
IsTypeClassConstructor = [Pair] -> Value
object [ String
"metaType" forall a. ToJSON a => String -> a -> Pair
.= String
"IsTypeClassConstructor" ]
metaToJSON Meta
IsForeign = [Pair] -> Value
object [ String
"metaType" forall a. ToJSON a => String -> a -> Pair
.= String
"IsForeign" ]
metaToJSON Meta
IsWhere = [Pair] -> Value
object [ String
"metaType" forall a. ToJSON a => String -> a -> Pair
.= String
"IsWhere" ]
metaToJSON Meta
IsSyntheticApp = [Pair] -> Value
object [ String
"metaType" forall a. ToJSON a => String -> a -> Pair
.= String
"IsSyntheticApp" ]
sourceSpanToJSON :: SourceSpan -> Value
sourceSpanToJSON :: SourceSpan -> Value
sourceSpanToJSON (SourceSpan String
_ SourcePos
spanStart SourcePos
spanEnd) =
[Pair] -> Value
object [ String
"start" forall a. ToJSON a => String -> a -> Pair
.= SourcePos
spanStart
, String
"end" forall a. ToJSON a => String -> a -> Pair
.= SourcePos
spanEnd
]
annToJSON :: Ann -> Value
annToJSON :: Ann -> Value
annToJSON (SourceSpan
ss, [Comment]
_, Maybe SourceType
_, Maybe Meta
m) = [Pair] -> Value
object [ String
"sourceSpan" forall a. ToJSON a => String -> a -> Pair
.= SourceSpan -> Value
sourceSpanToJSON SourceSpan
ss
, String
"meta" forall a. ToJSON a => String -> a -> Pair
.= forall b a. b -> (a -> b) -> Maybe a -> b
maybe Value
Null Meta -> Value
metaToJSON Maybe Meta
m
]
literalToJSON :: (a -> Value) -> Literal a -> Value
literalToJSON :: forall a. (a -> Value) -> Literal a -> Value
literalToJSON a -> Value
_ (NumericLiteral (Left Integer
n))
= [Pair] -> Value
object
[ String
"literalType" forall a. ToJSON a => String -> a -> Pair
.= String
"IntLiteral"
, String
"value" forall a. ToJSON a => String -> a -> Pair
.= Integer
n
]
literalToJSON a -> Value
_ (NumericLiteral (Right Double
n))
= [Pair] -> Value
object
[ String
"literalType" forall a. ToJSON a => String -> a -> Pair
.= String
"NumberLiteral"
, String
"value" forall a. ToJSON a => String -> a -> Pair
.= Double
n
]
literalToJSON a -> Value
_ (StringLiteral PSString
s)
= [Pair] -> Value
object
[ String
"literalType" forall a. ToJSON a => String -> a -> Pair
.= String
"StringLiteral"
, String
"value" forall a. ToJSON a => String -> a -> Pair
.= PSString
s
]
literalToJSON a -> Value
_ (CharLiteral Char
c)
= [Pair] -> Value
object
[ String
"literalType" forall a. ToJSON a => String -> a -> Pair
.= String
"CharLiteral"
, String
"value" forall a. ToJSON a => String -> a -> Pair
.= Char
c
]
literalToJSON a -> Value
_ (BooleanLiteral Bool
b)
= [Pair] -> Value
object
[ String
"literalType" forall a. ToJSON a => String -> a -> Pair
.= String
"BooleanLiteral"
, String
"value" forall a. ToJSON a => String -> a -> Pair
.= Bool
b
]
literalToJSON a -> Value
t (ArrayLiteral [a]
xs)
= [Pair] -> Value
object
[ String
"literalType" forall a. ToJSON a => String -> a -> Pair
.= String
"ArrayLiteral"
, String
"value" forall a. ToJSON a => String -> a -> Pair
.= forall a b. (a -> b) -> [a] -> [b]
map a -> Value
t [a]
xs
]
literalToJSON a -> Value
t (ObjectLiteral [(PSString, a)]
xs)
= [Pair] -> Value
object
[ String
"literalType" forall a. ToJSON a => String -> a -> Pair
.= String
"ObjectLiteral"
, String
"value" forall a. ToJSON a => String -> a -> Pair
.= forall a. (a -> Value) -> [(PSString, a)] -> Value
recordToJSON a -> Value
t [(PSString, a)]
xs
]
identToJSON :: Ident -> Value
identToJSON :: Ident -> Value
identToJSON = forall a. ToJSON a => a -> Value
toJSON forall b c a. (b -> c) -> (a -> b) -> a -> c
. Ident -> Text
runIdent
properNameToJSON :: ProperName a -> Value
properNameToJSON :: forall (a :: ProperNameType). ProperName a -> Value
properNameToJSON = forall a. ToJSON a => a -> Value
toJSON forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall (a :: ProperNameType). ProperName a -> Text
runProperName
qualifiedToJSON :: (a -> Text) -> Qualified a -> Value
qualifiedToJSON :: forall a. (a -> Text) -> Qualified a -> Value
qualifiedToJSON a -> Text
f (Qualified QualifiedBy
qb a
a) =
case QualifiedBy
qb of
ByModuleName ModuleName
mn -> [Pair] -> Value
object
[ String
"moduleName" forall a. ToJSON a => String -> a -> Pair
.= ModuleName -> Value
moduleNameToJSON ModuleName
mn
, String
"identifier" forall a. ToJSON a => String -> a -> Pair
.= forall a. ToJSON a => a -> Value
toJSON (a -> Text
f a
a)
]
BySourcePos SourcePos
ss -> [Pair] -> Value
object
[ String
"sourcePos" forall a. ToJSON a => String -> a -> Pair
.= forall a. ToJSON a => a -> Value
toJSON SourcePos
ss
, String
"identifier" forall a. ToJSON a => String -> a -> Pair
.= forall a. ToJSON a => a -> Value
toJSON (a -> Text
f a
a)
]
moduleNameToJSON :: ModuleName -> Value
moduleNameToJSON :: ModuleName -> Value
moduleNameToJSON (ModuleName Text
name) = forall a. ToJSON a => a -> Value
toJSON (Text -> Text -> [Text]
T.splitOn (String -> Text
T.pack String
".") Text
name)
moduleToJSON :: Version -> Module Ann -> Value
moduleToJSON :: Version -> Module Ann -> Value
moduleToJSON Version
v Module Ann
m = [Pair] -> Value
object
[ String
"sourceSpan" forall a. ToJSON a => String -> a -> Pair
.= SourceSpan -> Value
sourceSpanToJSON (forall a. Module a -> SourceSpan
moduleSourceSpan Module Ann
m)
, String
"moduleName" forall a. ToJSON a => String -> a -> Pair
.= ModuleName -> Value
moduleNameToJSON (forall a. Module a -> ModuleName
moduleName Module Ann
m)
, String
"modulePath" forall a. ToJSON a => String -> a -> Pair
.= forall a. ToJSON a => a -> Value
toJSON (forall a. Module a -> String
modulePath Module Ann
m)
, String
"imports" forall a. ToJSON a => String -> a -> Pair
.= forall a b. (a -> b) -> [a] -> [b]
map (Ann, ModuleName) -> Value
importToJSON (forall a. Module a -> [(a, ModuleName)]
moduleImports Module Ann
m)
, String
"exports" forall a. ToJSON a => String -> a -> Pair
.= forall a b. (a -> b) -> [a] -> [b]
map Ident -> Value
identToJSON (forall a. Module a -> [Ident]
moduleExports Module Ann
m)
, String
"reExports" forall a. ToJSON a => String -> a -> Pair
.= Map ModuleName [Ident] -> Value
reExportsToJSON (forall a. Module a -> Map ModuleName [Ident]
moduleReExports Module Ann
m)
, String
"foreign" forall a. ToJSON a => String -> a -> Pair
.= forall a b. (a -> b) -> [a] -> [b]
map Ident -> Value
identToJSON (forall a. Module a -> [Ident]
moduleForeign Module Ann
m)
, String
"decls" forall a. ToJSON a => String -> a -> Pair
.= forall a b. (a -> b) -> [a] -> [b]
map Bind Ann -> Value
bindToJSON (forall a. Module a -> [Bind a]
moduleDecls Module Ann
m)
, String
"builtWith" forall a. ToJSON a => String -> a -> Pair
.= forall a. ToJSON a => a -> Value
toJSON (Version -> String
showVersion Version
v)
, String
"comments" forall a. ToJSON a => String -> a -> Pair
.= forall a b. (a -> b) -> [a] -> [b]
map forall a. ToJSON a => a -> Value
toJSON (forall a. Module a -> [Comment]
moduleComments Module Ann
m)
]
where
importToJSON :: (Ann, ModuleName) -> Value
importToJSON (Ann
ann,ModuleName
mn) = [Pair] -> Value
object
[ String
"annotation" forall a. ToJSON a => String -> a -> Pair
.= Ann -> Value
annToJSON Ann
ann
, String
"moduleName" forall a. ToJSON a => String -> a -> Pair
.= ModuleName -> Value
moduleNameToJSON ModuleName
mn
]
reExportsToJSON :: M.Map ModuleName [Ident] -> Value
reExportsToJSON :: Map ModuleName [Ident] -> Value
reExportsToJSON = forall a. ToJSON a => a -> Value
toJSON forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a b k. (a -> b) -> Map k a -> Map k b
M.map (forall a b. (a -> b) -> [a] -> [b]
map Ident -> Text
runIdent)
bindToJSON :: Bind Ann -> Value
bindToJSON :: Bind Ann -> Value
bindToJSON (NonRec Ann
ann Ident
n Expr Ann
e)
= [Pair] -> Value
object
[ String
"bindType" forall a. ToJSON a => String -> a -> Pair
.= String
"NonRec"
, String
"annotation" forall a. ToJSON a => String -> a -> Pair
.= Ann -> Value
annToJSON Ann
ann
, String
"identifier" forall a. ToJSON a => String -> a -> Pair
.= Ident -> Value
identToJSON Ident
n
, String
"expression" forall a. ToJSON a => String -> a -> Pair
.= Expr Ann -> Value
exprToJSON Expr Ann
e
]
bindToJSON (Rec [((Ann, Ident), Expr Ann)]
bs)
= [Pair] -> Value
object
[ String
"bindType" forall a. ToJSON a => String -> a -> Pair
.= String
"Rec"
, String
"binds" forall a. ToJSON a => String -> a -> Pair
.= forall a b. (a -> b) -> [a] -> [b]
map (\((Ann
ann, Ident
n), Expr Ann
e)
-> [Pair] -> Value
object
[ String
"identifier" forall a. ToJSON a => String -> a -> Pair
.= Ident -> Value
identToJSON Ident
n
, String
"annotation" forall a. ToJSON a => String -> a -> Pair
.= Ann -> Value
annToJSON Ann
ann
, String
"expression" forall a. ToJSON a => String -> a -> Pair
.= Expr Ann -> Value
exprToJSON Expr Ann
e
]) [((Ann, Ident), Expr Ann)]
bs
]
recordToJSON :: (a -> Value) -> [(PSString, a)] -> Value
recordToJSON :: forall a. (a -> Value) -> [(PSString, a)] -> Value
recordToJSON a -> Value
f = forall a. ToJSON a => a -> Value
toJSON forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a b. (a -> b) -> [a] -> [b]
map (forall a. ToJSON a => a -> Value
toJSON forall (a :: * -> * -> *) b c b' c'.
Arrow a =>
a b c -> a b' c' -> a (b, b') (c, c')
*** a -> Value
f)
exprToJSON :: Expr Ann -> Value
exprToJSON :: Expr Ann -> Value
exprToJSON (Var Ann
ann Qualified Ident
i) = [Pair] -> Value
object [ String
"type" forall a. ToJSON a => String -> a -> Pair
.= forall a. ToJSON a => a -> Value
toJSON String
"Var"
, String
"annotation" forall a. ToJSON a => String -> a -> Pair
.= Ann -> Value
annToJSON Ann
ann
, String
"value" forall a. ToJSON a => String -> a -> Pair
.= forall a. (a -> Text) -> Qualified a -> Value
qualifiedToJSON Ident -> Text
runIdent Qualified Ident
i
]
exprToJSON (Literal Ann
ann Literal (Expr Ann)
l) = [Pair] -> Value
object [ String
"type" forall a. ToJSON a => String -> a -> Pair
.= String
"Literal"
, String
"annotation" forall a. ToJSON a => String -> a -> Pair
.= Ann -> Value
annToJSON Ann
ann
, String
"value" forall a. ToJSON a => String -> a -> Pair
.= forall a. (a -> Value) -> Literal a -> Value
literalToJSON Expr Ann -> Value
exprToJSON Literal (Expr Ann)
l
]
exprToJSON (Constructor Ann
ann ProperName 'TypeName
d ProperName 'ConstructorName
c [Ident]
is) = [Pair] -> Value
object [ String
"type" forall a. ToJSON a => String -> a -> Pair
.= String
"Constructor"
, String
"annotation" forall a. ToJSON a => String -> a -> Pair
.= Ann -> Value
annToJSON Ann
ann
, String
"typeName" forall a. ToJSON a => String -> a -> Pair
.= forall (a :: ProperNameType). ProperName a -> Value
properNameToJSON ProperName 'TypeName
d
, String
"constructorName" forall a. ToJSON a => String -> a -> Pair
.= forall (a :: ProperNameType). ProperName a -> Value
properNameToJSON ProperName 'ConstructorName
c
, String
"fieldNames" forall a. ToJSON a => String -> a -> Pair
.= forall a b. (a -> b) -> [a] -> [b]
map Ident -> Value
identToJSON [Ident]
is
]
exprToJSON (Accessor Ann
ann PSString
f Expr Ann
r) = [Pair] -> Value
object [ String
"type" forall a. ToJSON a => String -> a -> Pair
.= String
"Accessor"
, String
"annotation" forall a. ToJSON a => String -> a -> Pair
.= Ann -> Value
annToJSON Ann
ann
, String
"fieldName" forall a. ToJSON a => String -> a -> Pair
.= PSString
f
, String
"expression" forall a. ToJSON a => String -> a -> Pair
.= Expr Ann -> Value
exprToJSON Expr Ann
r
]
exprToJSON (ObjectUpdate Ann
ann Expr Ann
r [(PSString, Expr Ann)]
fs) = [Pair] -> Value
object [ String
"type" forall a. ToJSON a => String -> a -> Pair
.= String
"ObjectUpdate"
, String
"annotation" forall a. ToJSON a => String -> a -> Pair
.= Ann -> Value
annToJSON Ann
ann
, String
"expression" forall a. ToJSON a => String -> a -> Pair
.= Expr Ann -> Value
exprToJSON Expr Ann
r
, String
"updates" forall a. ToJSON a => String -> a -> Pair
.= forall a. (a -> Value) -> [(PSString, a)] -> Value
recordToJSON Expr Ann -> Value
exprToJSON [(PSString, Expr Ann)]
fs
]
exprToJSON (Abs Ann
ann Ident
p Expr Ann
b) = [Pair] -> Value
object [ String
"type" forall a. ToJSON a => String -> a -> Pair
.= String
"Abs"
, String
"annotation" forall a. ToJSON a => String -> a -> Pair
.= Ann -> Value
annToJSON Ann
ann
, String
"argument" forall a. ToJSON a => String -> a -> Pair
.= Ident -> Value
identToJSON Ident
p
, String
"body" forall a. ToJSON a => String -> a -> Pair
.= Expr Ann -> Value
exprToJSON Expr Ann
b
]
exprToJSON (App Ann
ann Expr Ann
f Expr Ann
x) = [Pair] -> Value
object [ String
"type" forall a. ToJSON a => String -> a -> Pair
.= String
"App"
, String
"annotation" forall a. ToJSON a => String -> a -> Pair
.= Ann -> Value
annToJSON Ann
ann
, String
"abstraction" forall a. ToJSON a => String -> a -> Pair
.= Expr Ann -> Value
exprToJSON Expr Ann
f
, String
"argument" forall a. ToJSON a => String -> a -> Pair
.= Expr Ann -> Value
exprToJSON Expr Ann
x
]
exprToJSON (Case Ann
ann [Expr Ann]
ss [CaseAlternative Ann]
cs) = [Pair] -> Value
object [ String
"type" forall a. ToJSON a => String -> a -> Pair
.= String
"Case"
, String
"annotation" forall a. ToJSON a => String -> a -> Pair
.= Ann -> Value
annToJSON Ann
ann
, String
"caseExpressions"
forall a. ToJSON a => String -> a -> Pair
.= forall a b. (a -> b) -> [a] -> [b]
map Expr Ann -> Value
exprToJSON [Expr Ann]
ss
, String
"caseAlternatives"
forall a. ToJSON a => String -> a -> Pair
.= forall a b. (a -> b) -> [a] -> [b]
map CaseAlternative Ann -> Value
caseAlternativeToJSON [CaseAlternative Ann]
cs
]
exprToJSON (Let Ann
ann [Bind Ann]
bs Expr Ann
e) = [Pair] -> Value
object [ String
"type" forall a. ToJSON a => String -> a -> Pair
.= String
"Let"
, String
"annotation" forall a. ToJSON a => String -> a -> Pair
.= Ann -> Value
annToJSON Ann
ann
, String
"binds" forall a. ToJSON a => String -> a -> Pair
.= forall a b. (a -> b) -> [a] -> [b]
map Bind Ann -> Value
bindToJSON [Bind Ann]
bs
, String
"expression" forall a. ToJSON a => String -> a -> Pair
.= Expr Ann -> Value
exprToJSON Expr Ann
e
]
caseAlternativeToJSON :: CaseAlternative Ann -> Value
caseAlternativeToJSON :: CaseAlternative Ann -> Value
caseAlternativeToJSON (CaseAlternative [Binder Ann]
bs Either [(Expr Ann, Expr Ann)] (Expr Ann)
r') =
let isGuarded :: Bool
isGuarded = forall a b. Either a b -> Bool
isLeft Either [(Expr Ann, Expr Ann)] (Expr Ann)
r'
in [Pair] -> Value
object
[ String
"binders" forall a. ToJSON a => String -> a -> Pair
.= forall a. ToJSON a => a -> Value
toJSON (forall a b. (a -> b) -> [a] -> [b]
map Binder Ann -> Value
binderToJSON [Binder Ann]
bs)
, String
"isGuarded" forall a. ToJSON a => String -> a -> Pair
.= forall a. ToJSON a => a -> Value
toJSON Bool
isGuarded
, (if Bool
isGuarded then String
"expressions" else String
"expression")
forall a. ToJSON a => String -> a -> Pair
.= case Either [(Expr Ann, Expr Ann)] (Expr Ann)
r' of
Left [(Expr Ann, Expr Ann)]
rs -> forall a. ToJSON a => a -> Value
toJSON forall a b. (a -> b) -> a -> b
$ forall a b. (a -> b) -> [a] -> [b]
map (\(Expr Ann
g, Expr Ann
e) -> [Pair] -> Value
object [ String
"guard" forall a. ToJSON a => String -> a -> Pair
.= Expr Ann -> Value
exprToJSON Expr Ann
g, String
"expression" forall a. ToJSON a => String -> a -> Pair
.= Expr Ann -> Value
exprToJSON Expr Ann
e]) [(Expr Ann, Expr Ann)]
rs
Right Expr Ann
r -> Expr Ann -> Value
exprToJSON Expr Ann
r
]
binderToJSON :: Binder Ann -> Value
binderToJSON :: Binder Ann -> Value
binderToJSON (VarBinder Ann
ann Ident
v) = [Pair] -> Value
object [ String
"binderType" forall a. ToJSON a => String -> a -> Pair
.= String
"VarBinder"
, String
"annotation" forall a. ToJSON a => String -> a -> Pair
.= Ann -> Value
annToJSON Ann
ann
, String
"identifier" forall a. ToJSON a => String -> a -> Pair
.= Ident -> Value
identToJSON Ident
v
]
binderToJSON (NullBinder Ann
ann) = [Pair] -> Value
object [ String
"binderType" forall a. ToJSON a => String -> a -> Pair
.= String
"NullBinder"
, String
"annotation" forall a. ToJSON a => String -> a -> Pair
.= Ann -> Value
annToJSON Ann
ann
]
binderToJSON (LiteralBinder Ann
ann Literal (Binder Ann)
l) = [Pair] -> Value
object [ String
"binderType" forall a. ToJSON a => String -> a -> Pair
.= String
"LiteralBinder"
, String
"annotation" forall a. ToJSON a => String -> a -> Pair
.= Ann -> Value
annToJSON Ann
ann
, String
"literal" forall a. ToJSON a => String -> a -> Pair
.= forall a. (a -> Value) -> Literal a -> Value
literalToJSON Binder Ann -> Value
binderToJSON Literal (Binder Ann)
l
]
binderToJSON (ConstructorBinder Ann
ann Qualified (ProperName 'TypeName)
d Qualified (ProperName 'ConstructorName)
c [Binder Ann]
bs) = [Pair] -> Value
object [ String
"binderType" forall a. ToJSON a => String -> a -> Pair
.= String
"ConstructorBinder"
, String
"annotation" forall a. ToJSON a => String -> a -> Pair
.= Ann -> Value
annToJSON Ann
ann
, String
"typeName" forall a. ToJSON a => String -> a -> Pair
.= forall a. (a -> Text) -> Qualified a -> Value
qualifiedToJSON forall (a :: ProperNameType). ProperName a -> Text
runProperName Qualified (ProperName 'TypeName)
d
, String
"constructorName"
forall a. ToJSON a => String -> a -> Pair
.= forall a. (a -> Text) -> Qualified a -> Value
qualifiedToJSON forall (a :: ProperNameType). ProperName a -> Text
runProperName Qualified (ProperName 'ConstructorName)
c
, String
"binders" forall a. ToJSON a => String -> a -> Pair
.= forall a b. (a -> b) -> [a] -> [b]
map Binder Ann -> Value
binderToJSON [Binder Ann]
bs
]
binderToJSON (NamedBinder Ann
ann Ident
n Binder Ann
b) = [Pair] -> Value
object [ String
"binderType" forall a. ToJSON a => String -> a -> Pair
.= String
"NamedBinder"
, String
"annotation" forall a. ToJSON a => String -> a -> Pair
.= Ann -> Value
annToJSON Ann
ann
, String
"identifier" forall a. ToJSON a => String -> a -> Pair
.= Ident -> Value
identToJSON Ident
n
, String
"binder" forall a. ToJSON a => String -> a -> Pair
.= Binder Ann -> Value
binderToJSON Binder Ann
b
]