@@ -44,11 +44,7 @@ apiAlias n ls = TypeDecl noLoc n [] alias
44verbDecl :: Service s r -> Local -> Local -> Method -> Decl
44verbDecl :: Service s r -> Local -> Local -> Method -> Decl
45verbDecl s p l m = TypeDecl noLoc (vname p l) [] alias
45verbDecl s p l m = TypeDecl noLoc (vname p l) [] alias
47− alias = case path ++ qry of
49− x:xs -> foldl' (\l r -> TyInfix l (UnQual (sym ":>")) r) x xs
47+ alias = foldr' (\l r -> TyInfix l (UnQual (sym ":>")) r) verb (path ++ qry)
51−-- Need to deal with interpolation?
53 path :: [Type]
49 path :: [Type]
54 path = map match
50 path = map match
@@ -87,6 +83,99 @@ verbDecl s p l m = TypeDecl noLoc (vname p l) [] alias
87 typ = tycon "'[JSON]"
83 typ = tycon "'[JSON]"
88 res = maybe (tycon "()") (tycon . Free) (_mResponse m)
84 res = maybe (tycon "()") (tycon . Free) (_mResponse m)
86+jsonDecls :: Id -> Pre -> Map Local Solved -> [Decl]
87+jsonDecls n p rs = [from, to]
89+ from = InstDecl noLoc Nothing [] [] (unqual "FromJSON") [tycon n]
91+ app (app (var "withObject") (str (idToText n))) $
92+ lamE noLoc [pvar "o"] $
93+ ctorE n (map decode (Map.toList rs))
97+ | Just x <- def s = defJS l x
98+ | s ^. required = reqJS l
99+ | monoid s = defJS l (var "mempty")
100+ | otherwise = optJS l
102+ to = InstDecl noLoc Nothing [] [] (unqual "ToJSON") [tycon n]
103+ [ wildcardD "toJSON" n omit none (map encode (Map.toList rs))
106+ omit = app (var "object")
107+ . app (var "catMaybes")
110+ none = paren $ app (var "Object") (var "mempty")
113+ | TMaybe {} <- _type s = infixApp (paren (app n o)) "<$>" a
114+ | otherwise = app (var "Just") (infixApp n ".=" a)
126+wildcardD f n enc x = \case
128+ xs -> InsDecl (FunBind [match prec xs])
131+ Match noLoc (name f) [p] Nothing (UnGuardedRhs (enc es)) noBinds
133+ prec = PRec (UnQual (dname n)) [PFieldWildcard]
135+defJS :: Local -> Exp -> Exp
136+defJS n x = infixApp (infixApp (var "o") ".:?" (str (local n))) ".!=" x
138+reqJS :: Local -> Exp
139+reqJS = infixApp (var "o") ".:" . str . local
141+optJS :: Local -> Exp
142+optJS = infixApp (var "o") ".:?" . str . local
144+funD :: String -> Exp -> InstDecl
145+funD f = InsDecl . patBind noLoc (pvar (name f))
147+constD :: String -> Exp -> InstDecl
148+constD f x = InsDecl $
149+ sfun noLoc (name f) [] (UnGuardedRhs (app (var "const") x)) noBinds
151+ctorE :: Id -> [Exp] -> Exp
152+ctorE n = seqE (var (dname n)) . map paren
154+seqE :: Exp -> [Exp] -> Exp
155+seqE l [] = app (var "pure") l
156+seqE l (r:rs) = infixApp l "<$>" (infixE r "<*>" rs)
158+-- toJSOND :: Protocol -> Id -> [Field] -> Decl
159+-- toJSOND p n = instD1 "ToJSON" n
160+-- . wildcardD n "toJSON" enc (paren $ app (var "Object") memptyE)
161+-- . map (Right . toJSONE p)
163+-- enc = app (var "object")
164+-- . app (var "catMaybes")
166+-- . map (either id id)
168+-- instD1 :: Text -> Id -> InstDecl -> Decl
169+-- instD1 c n = instD c n . (:[])
171+-- instD :: Text -> Id -> [InstDecl] -> Decl
172+-- instD c n = InstDecl noLoc Nothing [] [] (unqual c) [tycon (typeId n)]
175+-- memptyE = var "mempty"
90objDecl :: Id -> Pre -> Map Local Solved -> AST Decl
179objDecl :: Id -> Pre -> Map Local Solved -> AST Decl
91objDecl n p rs = DataDecl noLoc arity [] d [] [conDecl d p rs] <$> derivings n
180objDecl n p rs = DataDecl noLoc arity [] d [] [conDecl d p rs] <$> derivings n
@@ -126,23 +215,13 @@ ctorDecl n p rs = sfun noLoc c ps (UnGuardedRhs rhs) noBinds
126fieldUpdate :: Pre -> Local -> Solved -> FieldUpdate
215fieldUpdate :: Pre -> Local -> Solved -> FieldUpdate
127fieldUpdate p l s = FieldUpdate (UnQual (fname p l)) rhs
216fieldUpdate p l s = FieldUpdate (UnQual (fname p l)) rhs
129− rhs | s ^. required = v
218+ rhs | s ^. required = v
130− | Just x <- s ^. defaulted = def x (_schema s)
219+ | Just x <- def s = x
131− | Just x <- iso (_type s) = infixApp x "#" v
220+ | Just x <- iso (_type s) = infixApp x "#" v
132− | otherwise = var (name "Nothing")
221+ | otherwise = var (name "Nothing")
134 v = var (pname p l)
223 v = var (pname p l)
137− Enum {} -> var (bname (_prefix s) x)
138− Lit _ Bool -> lit (upperHead x)
141− --- FIXME: lift to AST
142− s -> error $ "Unmatched fieldUpdate:\n" ++ show s
144− lit = var . name . Text.unpack
146lensSig :: Id -> Pre -> Local -> Solved -> Decl
225lensSig :: Id -> Pre -> Local -> Solved -> Decl
147lensSig n p l s = TypeSig noLoc [lname p l] $
226lensSig n p l s = TypeSig noLoc [lname p l] $
148 TyApp (TyApp (tycon "Lens'") (tycon n))
227 TyApp (TyApp (tycon "Lens'") (tycon n))
@@ -165,6 +244,19 @@ derivings k = map ((,[]) . unqual . drop 1 . show) <$> derive k
165parameters :: [Solved] -> [Type]
244parameters :: [Solved] -> [Type]
166parameters = map (external . _type) . filter (view required)
245parameters = map (external . _type) . filter (view required)
247+def :: Solved -> Maybe Exp
249+ | Just x <- s ^. defaulted = Just (go x (_prefix s) (_schema s))
250+ | otherwise = Nothing
253+ Enum {} -> var (bname p x)
254+ Lit _ Bool -> lit (upperHead x)
258+ lit = var . name . Text.unpack
168external, internal :: TType -> Type
260external, internal :: TType -> Type
169external = internal . \case
261external = internal . \case
170 TMaybe t@TList {} -> t
262 TMaybe t@TList {} -> t