on master help sign in
Change the functionality of deriveSerailizeWith
commit5381715f97ab2b2dfc5066b7ec010cc0202a1226 authorAdithya Kumar <adithya@composewell.com> dateThu 31 Aug 2023, 19:21 (3 years ago) parent50fc60c
2 files changed+33−34
core/src/Streamly/Internal/Data/Serialize/TH.hs+32−32 test/Streamly/Test/Data/Unbox.hs+1−2
core/src/Streamly/Internal/Data/Serialize/TH.hs+32−32
@@ -362,34 +362,43 @@ deriveSerializeInternal preds headTy cons = do
362362 ]
363363 return [plainInstanceD preds (AppT (ConT ''Serialize) headTy) methods]
364364
365−-- | Template haskell helper to create instances of 'Serialize' automatically.
365+-- | Similar to 'deriveSerialize,' but with the ability to specify which type
366+-- variables should not be subjected to the 'Serialize' constraint and how to
367+-- replace these variables when defining the 'Serialize' instance for the
368+-- primary data type.
366369--
367370-- Consider the datatype:
368371-- @
369−-- data CustomDataType a b c = ...
372+-- data CustomDataType a f c = CDT a (f Int)
370373-- @
371374--
372−-- Usage: @$(deriveSerialize ''CustomDataType)@
375+-- Usage: @$(deriveSerializeWith ["c", "f"] [("f", ConT ''Identity)] ''CustomDataType)@
373376--
374−-- Note: All type variables automatcally get an "Serialize" constraint.
375−-- The derived code will look like the following,
376377-- @
377−-- instance (Serialize a, Serialize b, Serialize c) => Serialize (CustomDataType a b c) where
378+-- instance (Serialize a) => Serialize (CustomDataType a Identity c) where
378379-- ...
379380-- @
380381--
381−-- To control which type variables get the Serialize constraint, use
382−-- 'deriveSerializeWith'.
383−deriveSerialize :: Name -> Q [Dec]
384−deriveSerialize name = do
382+-- In the above example, 'Serialize' constraint is omitted for @f@ and @c@, and
383+-- @f@ is replaced with 'Identity' when defining the 'Serialize' instance for
384+-- the primary data type.
385+deriveSerializeWith :: [String] -> [(String, Type)] -> Name -> Q [Dec]
386+deriveSerializeWith ignoring substitutions name = do
385387 dt <- reifyDataType name
386− let preds = map (unboxPred . VarT) (dtTvs dt)
387− headTy = appsT (ConT name) (map VarT (dtTvs dt))
388+ let preds = map (unboxPred . VarT) (filterOutVars (dtTvs dt))
389+ headTy = appsT (ConT name) (map substituteVar (dtTvs dt))
388390 cons = dtCons dt
389391 deriveSerializeInternal preds headTy cons
390392
391393 where
392394
395+ filterOutVars vs =
396+ map mkName $ filter (not . flip elem ignoring) $ map nameBase vs
397+ substituteVar v =
398+ case lookup (nameBase v) substitutions of
399+ Nothing -> VarT v
400+ Just ty -> ty
401+
393402 unboxPred ty =
394403#if MIN_VERSION_template_haskell(2,10,0)
395404 AppT (ConT ''Serialize) ty
@@ -397,34 +406,25 @@ deriveSerialize name = do
397406 ClassP ''Serialize [ty]
398407#endif
399408
400−-- | Like 'deriveSerialize' but control which types variables get the 'Serialize'
401−-- constraint.
409+-- | Template haskell helper to create instances of 'Serialize' automatically.
402410--
403411-- Consider the datatype:
404412-- @
405413-- data CustomDataType a b c = ...
406414-- @
407415--
408−-- Usage: @$(deriveSerializeWith ["a", "c"] ''CustomDataType)@
416+-- Usage: @$(deriveSerialize ''CustomDataType)@
409417--
418+-- Note: All type variables automatcally get an "Serialize" constraint.
419+-- The derived code will look like the following,
410420-- @
411−-- instance (Serialize a, Serialize c) => Serialize (CustomDataType a b c) where
421+-- instance (Serialize a, Serialize b, Serialize c) => Serialize (CustomDataType a b c) where
412422-- ...
413423-- @
414424--
415−deriveSerializeWith :: [String] -> Name -> Q [Dec]
416−deriveSerializeWith vars name = do
417− dt <- reifyDataType name
418− let preds = map (unboxPred . VarT) (fmap mkName vars)
419− headTy = appsT (ConT name) (map VarT (dtTvs dt))
420− cons = dtCons dt
421− deriveSerializeInternal preds headTy cons
422−
423− where
424−
425− unboxPred ty =
426−#if MIN_VERSION_template_haskell(2,10,0)
427− AppT (ConT ''Serialize) ty
428−#else
429− ClassP ''Serialize [ty]
430−#endif
425+-- To control which type variables don't get the Serialize constraint, use
426+-- 'deriveSerializeWith'.
427+--
428+-- >>> deriveSerialize = deriveSerializeWith [] []
429+deriveSerialize :: Name -> Q [Dec]
430+deriveSerialize name = deriveSerializeWith [] [] name
test/Streamly/Test/Data/Unbox.hs+1−2
@@ -131,7 +131,6 @@ data UnarySum
131131 deriving (Show, Generic, Eq)
132132DERIVE_UNBOX(UnarySum)
133133
134−
135134data UnarySum2
136135 = UnitSum1 Unit
137136 | UnitSum2 Unit
@@ -193,7 +192,7 @@ deriving instance Generic (Ratio Int)
193192#if defined(USE_SERIALIZE)
194193$(deriveSerialize ''Complex)
195194$(deriveSerialize ''Ratio)
196−$(deriveSerializeWith ["a"] ''Const)
195+$(deriveSerializeWith ["b"] [] ''Const)
197196$(deriveSerialize ''Identity)
198197#endif
199198