{-# LANGUAGE AllowAmbiguousTypes #-}
module Yamlet.Generic
(
GenericYaml (..)
, GenericYamlOptions (..)
, YamlOptions (..)
, defaultYamlOptions
, SumEncodingKind (..)
, requiredField
, snakeCase
, kebabCase
, genericToYaml
, genericParseYaml
, GDatatype (Constructors)
, GConstructors
, GEncoding
, GToConstructor
, GFromConstructor
, GFields
, GToFields
, GFromFields
, Generic
) where
import Control.Exception hiding (TypeError)
import Control.Monad
import Data.Char
import Data.Coerce
import Data.Kind
import Data.Map.Strict qualified as M
import Data.Maybe
import Data.Proxy
import Data.Text qualified as T
import GHC.Generics
import GHC.TypeLits
import System.IO.Unsafe
import Yamlet.Internal.FromYaml
import Yamlet.Internal.Syntax qualified as S
import Yamlet.Internal.ToYaml
import Yamlet.Internal.Utils
import Yamlet.Internal.View
import Yamlet.Value
newtype GenericYaml a = GenericYaml a
instance
( Generic a
, GenericYamlOptions a
, GDatatype (Rep a)
, Constructors (Rep a) ~ f
, GConstructors f
, GEncoding (SumEncoding a) f
, GToConstructor f
, ToYaml a
)
=> ToYaml (GenericYaml a)
where
toYaml :: GenericYaml a -> Node
toYaml = (a -> Node) -> GenericYaml a -> Node
forall a b. Coercible a b => a -> b
coerce (forall a (f :: * -> *).
(Generic a, GenericYamlOptions a, GDatatype (Rep a),
Constructors (Rep a) ~ f, GConstructors f,
GEncoding (SumEncoding a) f, GToConstructor f) =>
a -> Node
genericToYaml @a)
{-# INLINE toYaml #-}
toYamlList :: [GenericYaml a] -> Node
toYamlList [GenericYaml a]
xs = [Node] -> Node
S.sequenceNode ((a -> Node) -> [a] -> [Node]
forall a b. (a -> b) -> [a] -> [b]
map (forall a. ToYaml a => a -> Node
toYaml @a) ([GenericYaml a] -> [a]
forall a b. Coercible a b => a -> b
coerce [GenericYaml a]
xs))
toYamlField :: Node -> GenericYaml a -> (Node, Node)
toYamlField Node
k (GenericYaml a
x)
| Bool -> Bool
not (forall {k} (f :: k). GConstructors f => YamlOptions -> Bool
forall (f :: * -> *). GConstructors f => YamlOptions -> Bool
isTagged @f (forall a. GenericYamlOptions a => YamlOptions
yamlOptions @a))
, Just (Node, Node)
entry <- Node -> Constructors (Rep a) (ZonkAny 3) -> Maybe (Node, Node)
forall p. Node -> Constructors (Rep a) p -> Maybe (Node, Node)
forall {k} (f :: k -> *) (p :: k).
GToConstructor f =>
Node -> f p -> Maybe (Node, Node)
gToUntaggedEntry Node
k (Rep a (ZonkAny 3) -> Constructors (Rep a) (ZonkAny 3)
forall p. Rep a p -> Constructors (Rep a) p
forall (r :: * -> *) p. GDatatype r => r p -> Constructors r p
gUnwrap (a -> Rep a (ZonkAny 3)
forall x. a -> Rep a x
forall a x. Generic a => a -> Rep a x
from a
x)) =
(Node, Node)
entry
| Bool
otherwise = (Node
k, forall a. ToYaml a => a -> Node
toYaml @a a
x)
instance
( Generic a
, GenericYamlOptions a
, GDatatype (Rep a)
, Constructors (Rep a) ~ f
, GConstructors f
, GEncoding (SumEncoding a) f
, GFromConstructor f
, FromYaml a
)
=> FromYaml (GenericYaml a)
where
parseYaml :: Node -> Parser (GenericYaml a)
parseYaml = (Node -> Parser a) -> Node -> Parser (GenericYaml a)
forall a b. Coercible a b => a -> b
coerce (forall a (f :: * -> *).
(Generic a, GenericYamlOptions a, GDatatype (Rep a),
Constructors (Rep a) ~ f, GConstructors f,
GEncoding (SumEncoding a) f, GFromConstructor f) =>
Node -> Parser a
genericParseYaml @a)
{-# INLINE parseYaml #-}
parseYamlList :: Node -> Parser [GenericYaml a]
parseYamlList = (Node -> Parser [a]) -> Node -> Parser [GenericYaml a]
forall a b. Coercible a b => a -> b
coerce (([Node] -> Parser [a]) -> Node -> Parser [a]
forall a. ([Node] -> Parser a) -> Node -> Parser a
withSequence ((Node -> Parser a) -> [Node] -> Parser [a]
forall a. (Node -> Parser a) -> [Node] -> Parser [a]
parseItems (forall a. FromYaml a => Node -> Parser a
parseYaml @a)))
{-# INLINE parseYamlList #-}
parseYamlField :: Node -> Node -> Parser (GenericYaml a)
parseYamlField Node
k Node
v
| Bool -> Bool
not (forall {k} (f :: k). GConstructors f => YamlOptions -> Bool
forall (f :: * -> *). GConstructors f => YamlOptions -> Bool
isTagged @f (forall a. GenericYamlOptions a => YamlOptions
yamlOptions @a))
, Just Parser a
p <- (f (ZonkAny 2) -> a) -> (Node, Node) -> Maybe (Parser a)
forall p a. (f p -> a) -> (Node, Node) -> Maybe (Parser a)
forall {k} (f :: k -> *) (p :: k) a.
GFromConstructor f =>
(f p -> a) -> (Node, Node) -> Maybe (Parser a)
gFromUntaggedEntry (Rep a (ZonkAny 2) -> a
forall a x. Generic a => Rep a x -> a
forall x. Rep a x -> a
to (Rep a (ZonkAny 2) -> a)
-> (f (ZonkAny 2) -> Rep a (ZonkAny 2)) -> f (ZonkAny 2) -> a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. f (ZonkAny 2) -> Rep a (ZonkAny 2)
Constructors (Rep a) (ZonkAny 2) -> Rep a (ZonkAny 2)
forall p. Constructors (Rep a) p -> Rep a p
forall (r :: * -> *) p. GDatatype r => Constructors r p -> r p
gWrap) (Node
k, Node
v) =
forall a b. Coercible a b => a -> b
forall a b. Coercible a b => a -> b
coerce @(Parser a) Parser a
p
| Bool
otherwise = Parser a -> Parser (GenericYaml a)
forall a b. Coercible a b => a -> b
coerce (forall a. FromYaml a => Node -> Parser a
parseYaml @a Node
v)
data YamlOptions = YamlOptions
{ YamlOptions -> String -> String
fieldLabelModifier :: !(String -> String)
, YamlOptions -> String -> String
constructorTagModifier :: !(String -> String)
, YamlOptions -> Text
tagKey :: !T.Text
, YamlOptions -> Text
contentsKey :: !T.Text
, YamlOptions -> Bool
tagSingleConstructors :: !Bool
, YamlOptions -> Bool
omitNullFields :: !Bool
, YamlOptions -> Bool
rejectUnknownFields :: !Bool
}
deriving stock ((forall x. YamlOptions -> Rep YamlOptions x)
-> (forall x. Rep YamlOptions x -> YamlOptions)
-> Generic YamlOptions
forall x. Rep YamlOptions x -> YamlOptions
forall x. YamlOptions -> Rep YamlOptions x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. YamlOptions -> Rep YamlOptions x
from :: forall x. YamlOptions -> Rep YamlOptions x
$cto :: forall x. Rep YamlOptions x -> YamlOptions
to :: forall x. Rep YamlOptions x -> YamlOptions
Generic)
defaultYamlOptions :: YamlOptions
defaultYamlOptions :: YamlOptions
defaultYamlOptions =
YamlOptions
{ fieldLabelModifier :: String -> String
fieldLabelModifier = String -> String
forall a. a -> a
id
, constructorTagModifier :: String -> String
constructorTagModifier = String -> String
forall a. a -> a
id
, tagKey :: Text
tagKey = Text
"tag"
, contentsKey :: Text
contentsKey = Text
"contents"
, tagSingleConstructors :: Bool
tagSingleConstructors = Bool
False
, omitNullFields :: Bool
omitNullFields = Bool
False
, rejectUnknownFields :: Bool
rejectUnknownFields = Bool
True
}
data SumEncodingKind
=
TaggedObject
|
TaggedFlat
|
SingleField
deriving stock (SumEncodingKind -> SumEncodingKind -> Bool
(SumEncodingKind -> SumEncodingKind -> Bool)
-> (SumEncodingKind -> SumEncodingKind -> Bool)
-> Eq SumEncodingKind
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: SumEncodingKind -> SumEncodingKind -> Bool
== :: SumEncodingKind -> SumEncodingKind -> Bool
$c/= :: SumEncodingKind -> SumEncodingKind -> Bool
/= :: SumEncodingKind -> SumEncodingKind -> Bool
Eq, Int -> SumEncodingKind -> String -> String
[SumEncodingKind] -> String -> String
SumEncodingKind -> String
(Int -> SumEncodingKind -> String -> String)
-> (SumEncodingKind -> String)
-> ([SumEncodingKind] -> String -> String)
-> Show SumEncodingKind
forall a.
(Int -> a -> String -> String)
-> (a -> String) -> ([a] -> String -> String) -> Show a
$cshowsPrec :: Int -> SumEncodingKind -> String -> String
showsPrec :: Int -> SumEncodingKind -> String -> String
$cshow :: SumEncodingKind -> String
show :: SumEncodingKind -> String
$cshowList :: [SumEncodingKind] -> String -> String
showList :: [SumEncodingKind] -> String -> String
Show)
class GenericYamlOptions a where
type SumEncoding a :: SumEncodingKind
type SumEncoding a = TaggedObject
yamlOptions :: YamlOptions
yamlOptions = YamlOptions
defaultYamlOptions
yamlDefault :: Maybe a
yamlDefault = Maybe a
forall a. Maybe a
Nothing
requiredField :: a
requiredField :: forall a. a
requiredField = RequiredField -> a
forall a e. (HasCallStack, Exception e) => e -> a
throw RequiredField
RequiredField
data RequiredField = RequiredField
deriving stock (Int -> RequiredField -> String -> String
[RequiredField] -> String -> String
RequiredField -> String
(Int -> RequiredField -> String -> String)
-> (RequiredField -> String)
-> ([RequiredField] -> String -> String)
-> Show RequiredField
forall a.
(Int -> a -> String -> String)
-> (a -> String) -> ([a] -> String -> String) -> Show a
$cshowsPrec :: Int -> RequiredField -> String -> String
showsPrec :: Int -> RequiredField -> String -> String
$cshow :: RequiredField -> String
show :: RequiredField -> String
$cshowList :: [RequiredField] -> String -> String
showList :: [RequiredField] -> String -> String
Show)
instance Exception RequiredField where
displayException :: RequiredField -> String
displayException RequiredField
_ = String
"the field has no default"
defaultField :: a -> Maybe a
defaultField :: forall a. a -> Maybe a
defaultField a
x = case IO (Either RequiredField a) -> Either RequiredField a
forall a. IO a -> a
unsafeDupablePerformIO (IO (Either RequiredField a) -> IO (Either RequiredField a)
forall a. IO a -> IO a
uninterruptibleMask_ (IO a -> IO (Either RequiredField a)
forall e a. Exception e => IO a -> IO (Either e a)
try (a -> IO a
forall a. a -> IO a
evaluate a
x))) of
Left RequiredField
RequiredField -> Maybe a
forall a. Maybe a
Nothing
Right a
_ -> a -> Maybe a
forall a. a -> Maybe a
Just a
x
checkDefault :: forall a. (GenericYamlOptions a, GDatatype (Rep a)) => ()
checkDefault :: forall a. (GenericYamlOptions a, GDatatype (Rep a)) => ()
checkDefault = case forall a. GenericYamlOptions a => Maybe a
yamlDefault @a of
Just a
d
| Maybe a -> Bool
forall a. Maybe a -> Bool
isNothing (a -> Maybe a
forall a. a -> Maybe a
defaultField a
d) ->
String -> ()
forall a. HasCallStack => String -> a
error (String -> ()) -> String -> ()
forall a b. (a -> b) -> a -> b
$
String
"requiredField in a strict field or a newtype of the default of "
String -> String -> String
forall a. [a] -> [a] -> [a]
++ forall (r :: * -> *). GDatatype r => String
gDatatypeName @(Rep a)
Maybe a
_ -> ()
{-# INLINE checkDefault #-}
snakeCase :: String -> String
snakeCase :: String -> String
snakeCase = Char -> String -> String
separateWords Char
'_'
kebabCase :: String -> String
kebabCase :: String -> String
kebabCase = Char -> String -> String
separateWords Char
'-'
separateWords :: Char -> String -> String
separateWords :: Char -> String -> String
separateWords Char
sep = (Char -> Char) -> String -> String
forall a b. (a -> b) -> [a] -> [b]
map Char -> Char
toLower (String -> String) -> (String -> String) -> String -> String
forall b c a. (b -> c) -> (a -> b) -> a -> c
. String -> String
afterLower (String -> String) -> (String -> String) -> String -> String
forall b c a. (b -> c) -> (a -> b) -> a -> c
. String -> String
beforeLower
where
beforeLower :: String -> String
beforeLower :: String -> String
beforeLower = \case
Char
x : Char
u : Char
l : String
rest | Char -> Bool
isUpper Char
u Bool -> Bool -> Bool
&& Char -> Bool
isLower Char
l -> Char
x Char -> String -> String
forall a. a -> [a] -> [a]
: Char
sep Char -> String -> String
forall a. a -> [a] -> [a]
: Char
u Char -> String -> String
forall a. a -> [a] -> [a]
: Char
l Char -> String -> String
forall a. a -> [a] -> [a]
: String -> String
beforeLower String
rest
Char
x : String
rest -> Char
x Char -> String -> String
forall a. a -> [a] -> [a]
: String -> String
beforeLower String
rest
[] -> []
afterLower :: String -> String
afterLower :: String -> String
afterLower = \case
Char
l : Char
u : String
rest | Char -> Bool
isLower Char
l Bool -> Bool -> Bool
&& Char -> Bool
isUpper Char
u -> Char
l Char -> String -> String
forall a. a -> [a] -> [a]
: Char
sep Char -> String -> String
forall a. a -> [a] -> [a]
: Char
u Char -> String -> String
forall a. a -> [a] -> [a]
: String -> String
afterLower String
rest
Char
x : String
rest -> Char
x Char -> String -> String
forall a. a -> [a] -> [a]
: String -> String
afterLower String
rest
[] -> []
class GDatatype (r :: Type -> Type) where
type Constructors r :: Type -> Type
gUnwrap :: r p -> Constructors r p
gWrap :: Constructors r p -> r p
gDatatypeName :: String
instance KnownSymbol name => GDatatype (D1 (MetaData name m p nt) f) where
type Constructors (D1 (MetaData name m p nt) f) = f
gUnwrap :: forall p.
D1 ('MetaData name m p nt) f p
-> Constructors (D1 ('MetaData name m p nt) f) p
gUnwrap = M1 D ('MetaData name m p nt) f p -> f p
M1 D ('MetaData name m p nt) f p
-> Constructors (D1 ('MetaData name m p nt) f) p
forall k i (c :: Meta) (f :: k -> *) (p :: k). M1 i c f p -> f p
unM1
gWrap :: forall p.
Constructors (D1 ('MetaData name m p nt) f) p
-> D1 ('MetaData name m p nt) f p
gWrap = f p -> M1 D ('MetaData name m p nt) f p
Constructors (D1 ('MetaData name m p nt) f) p
-> M1 D ('MetaData name m p nt) f p
forall k i (c :: Meta) (f :: k -> *) (p :: k). f p -> M1 i c f p
M1
gDatatypeName :: String
gDatatypeName = Proxy name -> String
forall (n :: Symbol) (proxy :: Symbol -> *).
KnownSymbol n =>
proxy n -> String
symbolVal (forall {k} (t :: k). Proxy t
forall (t :: Symbol). Proxy t
Proxy @name)
class GConstructors f where
gConstructorNames :: [String]
gConstructorCount :: Int
gNullary :: Bool
instance (GConstructors f, GConstructors g) => GConstructors (f :+: g) where
gConstructorNames :: [String]
gConstructorNames = forall {k} (f :: k). GConstructors f => [String]
forall (f :: k -> *). GConstructors f => [String]
gConstructorNames @f [String] -> [String] -> [String]
forall a. [a] -> [a] -> [a]
++ forall {k} (f :: k). GConstructors f => [String]
forall (f :: k -> *). GConstructors f => [String]
gConstructorNames @g
gConstructorCount :: Int
gConstructorCount = forall {k} (f :: k). GConstructors f => Int
forall (f :: k -> *). GConstructors f => Int
gConstructorCount @f Int -> Int -> Int
forall a. Num a => a -> a -> a
+ forall {k} (f :: k). GConstructors f => Int
forall (f :: k -> *). GConstructors f => Int
gConstructorCount @g
gNullary :: Bool
gNullary = forall {k} (f :: k). GConstructors f => Bool
forall (f :: k -> *). GConstructors f => Bool
gNullary @f Bool -> Bool -> Bool
&& forall {k} (f :: k). GConstructors f => Bool
forall (f :: k -> *). GConstructors f => Bool
gNullary @g
instance GConstructors V1 where
gConstructorNames :: [String]
gConstructorNames = []
gConstructorCount :: Int
gConstructorCount = Int
0
gNullary :: Bool
gNullary = Bool
True
type NoConstructors = Text "A type without constructors cannot derive FromYaml or ToYaml"
instance
(KnownSymbol name, GFields f)
=> GConstructors (C1 (MetaCons name fixity isRecord) f)
where
gConstructorNames :: [String]
gConstructorNames = [Proxy name -> String
forall (n :: Symbol) (proxy :: Symbol -> *).
KnownSymbol n =>
proxy n -> String
symbolVal (forall {k} (t :: k). Proxy t
forall (t :: Symbol). Proxy t
Proxy @name)]
gConstructorCount :: Int
gConstructorCount = Int
1
gNullary :: Bool
gNullary = forall {k} (f :: k). GFields f => Int
forall (f :: k -> *). GFields f => Int
gArity @f Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
== Int
0
class GEncoding (e :: SumEncodingKind) f where
gEncoding :: SumEncodingKind
instance ValidShape (GShape TaggedObject f) => GEncoding TaggedObject f where
gEncoding :: SumEncodingKind
gEncoding = forall (s :: Shape). ValidShape s => ()
validShape @(GShape TaggedObject f) () -> SumEncodingKind -> SumEncodingKind
forall a b. a -> b -> b
`seq` SumEncodingKind
TaggedObject
instance ValidShape (GShape TaggedFlat f) => GEncoding TaggedFlat f where
gEncoding :: SumEncodingKind
gEncoding = forall (s :: Shape). ValidShape s => ()
validShape @(GShape TaggedFlat f) () -> SumEncodingKind -> SumEncodingKind
forall a b. a -> b -> b
`seq` SumEncodingKind
TaggedFlat
instance ValidShape (SingleShape f) => GEncoding SingleField f where
gEncoding :: SumEncodingKind
gEncoding = forall (s :: Shape). ValidShape s => ()
validShape @(SingleShape f) () -> SumEncodingKind -> SumEncodingKind
forall a b. a -> b -> b
`seq` SumEncodingKind
SingleField
data Shape
= NoFields
|
UnnamedField Symbol
|
NamedFields Symbol
type family GShape (e :: SumEncodingKind) (f :: Type -> Type) :: Shape where
GShape e (f :+: g) = CombineShapes (GShape e f) (GShape e g)
GShape TaggedFlat (C1 (MetaCons name fixity True) f) =
TypeError
( Text "TaggedFlat needs constructors with one field without a name, but the constructor "
:<>: Text name
:<>: Text " has named fields."
:$$: FlatFieldsFix
)
GShape e (C1 (MetaCons name fixity True) f) = NamedFields name
GShape e (C1 (MetaCons name fixity False) U1) = NoFields
GShape e (C1 (MetaCons name fixity False) (S1 m f)) = UnnamedField name
GShape e (C1 (MetaCons name fixity False) (f :*: g)) =
TypeError
( Text "The constructor "
:<>: Text name
:<>: Text " has several fields without names."
:$$: SeveralFieldsFix e
)
GShape e V1 = TypeError NoConstructors
type family SeveralFieldsFix (e :: SumEncodingKind) :: ErrorMessage where
SeveralFieldsFix TaggedFlat = FlatFieldsFix
SeveralFieldsFix e = Text "Give the fields names."
type FlatFieldsFix =
Text "Put the fields in a record type, and make it the one field of the constructor."
type family CombineShapes (a :: Shape) (b :: Shape) :: Shape where
CombineShapes NoFields b = b
CombineShapes a NoFields = a
CombineShapes (NamedFields a) (NamedFields _) = NamedFields a
CombineShapes (UnnamedField a) (UnnamedField _) = UnnamedField a
CombineShapes (NamedFields a) (UnnamedField b) = MixedFields a b
CombineShapes (UnnamedField b) (NamedFields a) = MixedFields a b
type family MixedFields (named :: Symbol) (unnamed :: Symbol) :: Shape where
MixedFields named unnamed =
TypeError
( Text "The constructor "
:<>: Text named
:<>: Text " has named fields and the constructor "
:<>: Text unnamed
:<>: Text " has one field without a name."
:$$: Text
"Give them the same kind of fields, or use the sum encoding SingleField, where each constructor has its own value."
)
class ValidShape (s :: Shape) where
validShape :: ()
instance ValidShape NoFields where validShape :: ()
validShape = ()
instance ValidShape (UnnamedField name) where validShape :: ()
validShape = ()
instance ValidShape (NamedFields name) where validShape :: ()
validShape = ()
type family SingleShape (f :: Type -> Type) :: Shape where
SingleShape (f :+: g) = EitherShape (SingleShape f) (SingleShape g)
SingleShape f = GShape SingleField f
type family EitherShape (a :: Shape) (b :: Shape) :: Shape where
EitherShape NoFields b = b
EitherShape a NoFields = a
EitherShape (NamedFields a) (NamedFields _) = NamedFields a
EitherShape (NamedFields a) (UnnamedField _) = NamedFields a
EitherShape (UnnamedField a) (NamedFields _) = UnnamedField a
EitherShape (UnnamedField a) (UnnamedField _) = UnnamedField a
isTagged :: forall f. GConstructors f => YamlOptions -> Bool
isTagged :: forall {k} (f :: k). GConstructors f => YamlOptions -> Bool
isTagged YamlOptions
opts = YamlOptions
opts.tagSingleConstructors Bool -> Bool -> Bool
|| forall (f :: k). GConstructors f => Int
forall {k} (f :: k). GConstructors f => Int
gConstructorCount @f Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
> Int
1
constructorTag :: YamlOptions -> String -> T.Text
constructorTag :: YamlOptions -> String -> Text
constructorTag YamlOptions
opts = String -> Text
T.pack (String -> Text) -> (String -> String) -> String -> Text
forall b c a. (b -> c) -> (a -> b) -> a -> c
. YamlOptions
opts.constructorTagModifier
constructorTagOf :: forall name. KnownSymbol name => YamlOptions -> T.Text
constructorTagOf :: forall (name :: Symbol). KnownSymbol name => YamlOptions -> Text
constructorTagOf YamlOptions
opts = YamlOptions -> String -> Text
constructorTag YamlOptions
opts (Proxy name -> String
forall (n :: Symbol) (proxy :: Symbol -> *).
KnownSymbol n =>
proxy n -> String
symbolVal (forall {k} (t :: k). Proxy t
forall (t :: Symbol). Proxy t
Proxy @name))
leftDefault :: Maybe ((f :+: g) p) -> Maybe (f p)
leftDefault :: forall {k} (f :: k -> *) (g :: k -> *) (p :: k).
Maybe ((:+:) f g p) -> Maybe (f p)
leftDefault Maybe ((:+:) f g p)
def =
Maybe ((:+:) f g p)
def Maybe ((:+:) f g p) -> ((:+:) f g p -> Maybe (f p)) -> Maybe (f p)
forall a b. Maybe a -> (a -> Maybe b) -> Maybe b
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= \case
L1 f p
x -> f p -> Maybe (f p)
forall a. a -> Maybe a
Just f p
x
R1 g p
_ -> Maybe (f p)
forall a. Maybe a
Nothing
rightDefault :: Maybe ((f :+: g) p) -> Maybe (g p)
rightDefault :: forall {k} (f :: k -> *) (g :: k -> *) (p :: k).
Maybe ((:+:) f g p) -> Maybe (g p)
rightDefault Maybe ((:+:) f g p)
def =
Maybe ((:+:) f g p)
def Maybe ((:+:) f g p) -> ((:+:) f g p -> Maybe (g p)) -> Maybe (g p)
forall a b. Maybe a -> (a -> Maybe b) -> Maybe b
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= \case
R1 g p
x -> g p -> Maybe (g p)
forall a. a -> Maybe a
Just g p
x
L1 f p
_ -> Maybe (g p)
forall a. Maybe a
Nothing
firstDefault :: Maybe ((f :*: g) p) -> Maybe (f p)
firstDefault :: forall {k} (f :: k -> *) (g :: k -> *) (p :: k).
Maybe ((:*:) f g p) -> Maybe (f p)
firstDefault = ((:*:) f g p -> f p) -> Maybe ((:*:) f g p) -> Maybe (f p)
forall a b. (a -> b) -> Maybe a -> Maybe b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap (\(f p
a :*: g p
_) -> f p
a)
secondDefault :: Maybe ((f :*: g) p) -> Maybe (g p)
secondDefault :: forall {k} (f :: k -> *) (g :: k -> *) (p :: k).
Maybe ((:*:) f g p) -> Maybe (g p)
secondDefault = ((:*:) f g p -> g p) -> Maybe ((:*:) f g p) -> Maybe (g p)
forall a b. (a -> b) -> Maybe a -> Maybe b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap (\(f p
_ :*: g p
b) -> g p
b)
class GFields f where
gNamed :: Bool
gArity :: Int
gNames :: YamlOptions -> [T.Text]
instance GFields U1 where
gNamed :: Bool
gNamed = Bool
False
gArity :: Int
gArity = Int
0
gNames :: YamlOptions -> [Text]
gNames YamlOptions
_ = []
instance (GFields f, GFields g) => GFields (f :*: g) where
gNamed :: Bool
gNamed = forall {k} (f :: k). GFields f => Bool
forall (f :: k -> *). GFields f => Bool
gNamed @f
gArity :: Int
gArity = forall {k} (f :: k). GFields f => Int
forall (f :: k -> *). GFields f => Int
gArity @f Int -> Int -> Int
forall a. Num a => a -> a -> a
+ forall {k} (f :: k). GFields f => Int
forall (f :: k -> *). GFields f => Int
gArity @g
gNames :: YamlOptions -> [Text]
gNames YamlOptions
opts = forall {k} (f :: k). GFields f => YamlOptions -> [Text]
forall (f :: k -> *). GFields f => YamlOptions -> [Text]
gNames @f YamlOptions
opts [Text] -> [Text] -> [Text]
forall a. [a] -> [a] -> [a]
++ forall {k} (f :: k). GFields f => YamlOptions -> [Text]
forall (f :: k -> *). GFields f => YamlOptions -> [Text]
gNames @g YamlOptions
opts
instance KnownSymbol name => GFields (S1 (MetaSel (Just name) u s d) f) where
gNamed :: Bool
gNamed = Bool
True
gArity :: Int
gArity = Int
1
gNames :: YamlOptions -> [Text]
gNames YamlOptions
opts = [forall (name :: Symbol). KnownSymbol name => YamlOptions -> Text
fieldKey @name YamlOptions
opts]
instance GFields (S1 (MetaSel Nothing u s d) f) where
gNamed :: Bool
gNamed = Bool
False
gArity :: Int
gArity = Int
1
gNames :: YamlOptions -> [Text]
gNames YamlOptions
_ = []
fieldKey :: forall name. KnownSymbol name => YamlOptions -> T.Text
fieldKey :: forall (name :: Symbol). KnownSymbol name => YamlOptions -> Text
fieldKey YamlOptions
opts = String -> Text
T.pack (YamlOptions
opts.fieldLabelModifier (Proxy name -> String
forall (n :: Symbol) (proxy :: Symbol -> *).
KnownSymbol n =>
proxy n -> String
symbolVal (forall {k} (t :: k). Proxy t
forall (t :: Symbol). Proxy t
Proxy @name)))
genericToYaml
:: forall a f
. ( Generic a
, GenericYamlOptions a
, GDatatype (Rep a)
, Constructors (Rep a) ~ f
, GConstructors f
, GEncoding (SumEncoding a) f
, GToConstructor f
)
=> a -> S.Node
genericToYaml :: forall a (f :: * -> *).
(Generic a, GenericYamlOptions a, GDatatype (Rep a),
Constructors (Rep a) ~ f, GConstructors f,
GEncoding (SumEncoding a) f, GToConstructor f) =>
a -> Node
genericToYaml a
x =
let enc :: SumEncodingKind
enc = forall {k} (e :: SumEncodingKind) (f :: k).
GEncoding e f =>
SumEncodingKind
forall (e :: SumEncodingKind) (f :: * -> *).
GEncoding e f =>
SumEncodingKind
gEncoding @(SumEncoding a) @f
!opts :: YamlOptions
opts = forall a. GenericYamlOptions a => YamlOptions
yamlOptions @a
in SumEncodingKind
enc
SumEncodingKind -> Node -> Node
forall a b. a -> b -> b
`seq` forall a. (GenericYamlOptions a, GDatatype (Rep a)) => ()
checkDefault @a
() -> Node -> Node
forall a b. a -> b -> b
`seq` YamlOptions
-> SumEncodingKind
-> Maybe (Constructors (Rep a) (ZonkAny 0))
-> Constructors (Rep a) (ZonkAny 0)
-> Node
forall {k} (f :: k -> *) (p :: k).
(GConstructors f, GToConstructor f) =>
YamlOptions -> SumEncodingKind -> Maybe (f p) -> f p -> Node
gToYaml YamlOptions
opts SumEncodingKind
enc (Rep a (ZonkAny 0) -> Constructors (Rep a) (ZonkAny 0)
forall p. Rep a p -> Constructors (Rep a) p
forall (r :: * -> *) p. GDatatype r => r p -> Constructors r p
gUnwrap (Rep a (ZonkAny 0) -> Constructors (Rep a) (ZonkAny 0))
-> (a -> Rep a (ZonkAny 0))
-> a
-> Constructors (Rep a) (ZonkAny 0)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. a -> Rep a (ZonkAny 0)
forall x. a -> Rep a x
forall a x. Generic a => a -> Rep a x
from (a -> Constructors (Rep a) (ZonkAny 0))
-> Maybe a -> Maybe (Constructors (Rep a) (ZonkAny 0))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. GenericYamlOptions a => Maybe a
yamlDefault @a) (Rep a (ZonkAny 0) -> Constructors (Rep a) (ZonkAny 0)
forall p. Rep a p -> Constructors (Rep a) p
forall (r :: * -> *) p. GDatatype r => r p -> Constructors r p
gUnwrap (a -> Rep a (ZonkAny 0)
forall x. a -> Rep a x
forall a x. Generic a => a -> Rep a x
from a
x))
{-# INLINE genericToYaml #-}
gToYaml
:: forall f p
. ( GConstructors f
, GToConstructor f
)
=> YamlOptions -> SumEncodingKind -> Maybe (f p) -> f p -> S.Node
gToYaml :: forall {k} (f :: k -> *) (p :: k).
(GConstructors f, GToConstructor f) =>
YamlOptions -> SumEncodingKind -> Maybe (f p) -> f p -> Node
gToYaml YamlOptions
opts SumEncodingKind
enc Maybe (f p)
def f p
x
| forall {k} (f :: k). GConstructors f => Bool
forall (f :: k -> *). GConstructors f => Bool
gNullary @f = Value -> Node
scalar (Text -> Value
String (YamlOptions -> f p -> Text
forall (p :: k). YamlOptions -> f p -> Text
forall {k} (f :: k -> *) (p :: k).
GToConstructor f =>
YamlOptions -> f p -> Text
gTag YamlOptions
opts f p
x))
| Bool
otherwise = YamlOptions -> Maybe SumEncodingKind -> Maybe (f p) -> f p -> Node
forall (p :: k).
YamlOptions -> Maybe SumEncodingKind -> Maybe (f p) -> f p -> Node
forall {k} (f :: k -> *) (p :: k).
GToConstructor f =>
YamlOptions -> Maybe SumEncodingKind -> Maybe (f p) -> f p -> Node
gToConstructor YamlOptions
opts (if forall {k} (f :: k). GConstructors f => YamlOptions -> Bool
forall (f :: k -> *). GConstructors f => YamlOptions -> Bool
isTagged @f YamlOptions
opts then SumEncodingKind -> Maybe SumEncodingKind
forall a. a -> Maybe a
Just SumEncodingKind
enc else Maybe SumEncodingKind
forall a. Maybe a
Nothing) Maybe (f p)
def f p
x
{-# INLINE gToYaml #-}
class GToConstructor f where
gTag :: YamlOptions -> f p -> T.Text
gToConstructor :: YamlOptions -> Maybe SumEncodingKind -> Maybe (f p) -> f p -> S.Node
gToUntaggedEntry :: S.Node -> f p -> Maybe (S.Node, S.Node)
instance GToConstructor V1 where
gTag :: forall (p :: k). YamlOptions -> V1 p -> Text
gTag YamlOptions
_ = \case {}
gToConstructor :: forall (p :: k).
YamlOptions
-> Maybe SumEncodingKind -> Maybe (V1 p) -> V1 p -> Node
gToConstructor YamlOptions
_ Maybe SumEncodingKind
_ Maybe (V1 p)
_ = \case {}
gToUntaggedEntry :: forall (p :: k). Node -> V1 p -> Maybe (Node, Node)
gToUntaggedEntry Node
_ = \case {}
instance (GToConstructor f, GToConstructor g) => GToConstructor (f :+: g) where
gTag :: forall (p :: k). YamlOptions -> (:+:) f g p -> Text
gTag YamlOptions
opts = \case
L1 f p
x -> YamlOptions -> f p -> Text
forall (p :: k). YamlOptions -> f p -> Text
forall {k} (f :: k -> *) (p :: k).
GToConstructor f =>
YamlOptions -> f p -> Text
gTag YamlOptions
opts f p
x
R1 g p
x -> YamlOptions -> g p -> Text
forall (p :: k). YamlOptions -> g p -> Text
forall {k} (f :: k -> *) (p :: k).
GToConstructor f =>
YamlOptions -> f p -> Text
gTag YamlOptions
opts g p
x
{-# INLINE gTag #-}
gToConstructor :: forall (p :: k).
YamlOptions
-> Maybe SumEncodingKind
-> Maybe ((:+:) f g p)
-> (:+:) f g p
-> Node
gToConstructor YamlOptions
opts Maybe SumEncodingKind
flat Maybe ((:+:) f g p)
def = \case
L1 f p
x -> YamlOptions -> Maybe SumEncodingKind -> Maybe (f p) -> f p -> Node
forall (p :: k).
YamlOptions -> Maybe SumEncodingKind -> Maybe (f p) -> f p -> Node
forall {k} (f :: k -> *) (p :: k).
GToConstructor f =>
YamlOptions -> Maybe SumEncodingKind -> Maybe (f p) -> f p -> Node
gToConstructor YamlOptions
opts Maybe SumEncodingKind
flat (Maybe ((:+:) f g p) -> Maybe (f p)
forall {k} (f :: k -> *) (g :: k -> *) (p :: k).
Maybe ((:+:) f g p) -> Maybe (f p)
leftDefault Maybe ((:+:) f g p)
def) f p
x
R1 g p
x -> YamlOptions -> Maybe SumEncodingKind -> Maybe (g p) -> g p -> Node
forall (p :: k).
YamlOptions -> Maybe SumEncodingKind -> Maybe (g p) -> g p -> Node
forall {k} (f :: k -> *) (p :: k).
GToConstructor f =>
YamlOptions -> Maybe SumEncodingKind -> Maybe (f p) -> f p -> Node
gToConstructor YamlOptions
opts Maybe SumEncodingKind
flat (Maybe ((:+:) f g p) -> Maybe (g p)
forall {k} (f :: k -> *) (g :: k -> *) (p :: k).
Maybe ((:+:) f g p) -> Maybe (g p)
rightDefault Maybe ((:+:) f g p)
def) g p
x
{-# INLINE gToConstructor #-}
gToUntaggedEntry :: forall (p :: k). Node -> (:+:) f g p -> Maybe (Node, Node)
gToUntaggedEntry Node
_ (:+:) f g p
_ = Maybe (Node, Node)
forall a. Maybe a
Nothing
instance
( KnownSymbol name
, GFields f
, GToFields f
)
=> GToConstructor (C1 (MetaCons name fixity isRecord) f)
where
gTag :: forall (p :: k).
YamlOptions -> C1 ('MetaCons name fixity isRecord) f p -> Text
gTag YamlOptions
opts C1 ('MetaCons name fixity isRecord) f p
_ = forall (name :: Symbol). KnownSymbol name => YamlOptions -> Text
constructorTagOf @name YamlOptions
opts
{-# INLINE gTag #-}
gToConstructor :: forall (p :: k).
YamlOptions
-> Maybe SumEncodingKind
-> Maybe (C1 ('MetaCons name fixity isRecord) f p)
-> C1 ('MetaCons name fixity isRecord) f p
-> Node
gToConstructor YamlOptions
opts Maybe SumEncodingKind
tagging Maybe (C1 ('MetaCons name fixity isRecord) f p)
def c :: C1 ('MetaCons name fixity isRecord) f p
c@(M1 f p
x) = case Maybe SumEncodingKind
tagging of
Just SumEncodingKind
SingleField
| forall {k} (f :: k). GFields f => Bool
forall (f :: k -> *). GFields f => Bool
gNamed @f ->
[(Node, Node)] -> Node
mapping [(Text -> Node
string (YamlOptions -> C1 ('MetaCons name fixity isRecord) f p -> Text
forall (p :: k).
YamlOptions -> C1 ('MetaCons name fixity isRecord) f p -> Text
forall {k} (f :: k -> *) (p :: k).
GToConstructor f =>
YamlOptions -> f p -> Text
gTag YamlOptions
opts C1 ('MetaCons name fixity isRecord) f p
c), [(Node, Node)] -> Node
mapping (YamlOptions -> Maybe (f p) -> f p -> [(Node, Node)]
forall (p :: k).
YamlOptions -> Maybe (f p) -> f p -> [(Node, Node)]
forall {k} (f :: k -> *) (p :: k).
GToFields f =>
YamlOptions -> Maybe (f p) -> f p -> [(Node, Node)]
gToEntries YamlOptions
opts (C1 ('MetaCons name fixity isRecord) f p -> f p
forall k i (c :: Meta) (f :: k -> *) (p :: k). M1 i c f p -> f p
unM1 (C1 ('MetaCons name fixity isRecord) f p -> f p)
-> Maybe (C1 ('MetaCons name fixity isRecord) f p) -> Maybe (f p)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Maybe (C1 ('MetaCons name fixity isRecord) f p)
def) f p
x))]
| Bool
otherwise -> case f p -> Maybe Node
forall (p :: k). f p -> Maybe Node
forall {k} (f :: k -> *) (p :: k). GToFields f => f p -> Maybe Node
gToValue f p
x of
Maybe Node
Nothing -> Text -> Node
string (YamlOptions -> C1 ('MetaCons name fixity isRecord) f p -> Text
forall (p :: k).
YamlOptions -> C1 ('MetaCons name fixity isRecord) f p -> Text
forall {k} (f :: k -> *) (p :: k).
GToConstructor f =>
YamlOptions -> f p -> Text
gTag YamlOptions
opts C1 ('MetaCons name fixity isRecord) f p
c)
Just Node
_ -> [(Node, Node)] -> Node
mapping [Node -> f p -> (Node, Node)
forall (p :: k). Node -> f p -> (Node, Node)
forall {k} (f :: k -> *) (p :: k).
GToFields f =>
Node -> f p -> (Node, Node)
gToEntry (Text -> Node
string (YamlOptions -> C1 ('MetaCons name fixity isRecord) f p -> Text
forall (p :: k).
YamlOptions -> C1 ('MetaCons name fixity isRecord) f p -> Text
forall {k} (f :: k -> *) (p :: k).
GToConstructor f =>
YamlOptions -> f p -> Text
gTag YamlOptions
opts C1 ('MetaCons name fixity isRecord) f p
c)) f p
x]
Just SumEncodingKind
enc
| forall {k} (f :: k). GFields f => Bool
forall (f :: k -> *). GFields f => Bool
gNamed @f -> [(Node, Node)] -> Node
mapping ([(Node, Node)] -> [(Node, Node)]
withTagEntry (YamlOptions -> Maybe (f p) -> f p -> [(Node, Node)]
forall (p :: k).
YamlOptions -> Maybe (f p) -> f p -> [(Node, Node)]
forall {k} (f :: k -> *) (p :: k).
GToFields f =>
YamlOptions -> Maybe (f p) -> f p -> [(Node, Node)]
gToEntries YamlOptions
opts (C1 ('MetaCons name fixity isRecord) f p -> f p
forall k i (c :: Meta) (f :: k -> *) (p :: k). M1 i c f p -> f p
unM1 (C1 ('MetaCons name fixity isRecord) f p -> f p)
-> Maybe (C1 ('MetaCons name fixity isRecord) f p) -> Maybe (f p)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Maybe (C1 ('MetaCons name fixity isRecord) f p)
def) f p
x))
| Bool
otherwise -> case f p -> Maybe Node
forall (p :: k). f p -> Maybe Node
forall {k} (f :: k -> *) (p :: k). GToFields f => f p -> Maybe Node
gToValue f p
x of
Maybe Node
Nothing -> [(Node, Node)] -> Node
mapping ([(Node, Node)] -> [(Node, Node)]
withTagEntry [])
Just Node
v
| SumEncodingKind
enc SumEncodingKind -> SumEncodingKind -> Bool
forall a. Eq a => a -> a -> Bool
== SumEncodingKind
TaggedFlat
, Just [(Node, Node)]
entries <- Node -> Maybe [(Node, Node)]
flatEntries Node
v ->
[(Node, Node)] -> Node
mapping ([(Node, Node)] -> [(Node, Node)]
withTagEntry [(Node, Node)]
entries)
| Bool
otherwise -> [(Node, Node)] -> Node
mapping ([(Node, Node)] -> [(Node, Node)]
withTagEntry [Node -> f p -> (Node, Node)
forall (p :: k). Node -> f p -> (Node, Node)
forall {k} (f :: k -> *) (p :: k).
GToFields f =>
Node -> f p -> (Node, Node)
gToEntry (Text -> Node
string YamlOptions
opts.contentsKey) f p
x])
Maybe SumEncodingKind
Nothing
| forall {k} (f :: k). GFields f => Bool
forall (f :: k -> *). GFields f => Bool
gNamed @f -> [(Node, Node)] -> Node
mapping (YamlOptions -> Maybe (f p) -> f p -> [(Node, Node)]
forall (p :: k).
YamlOptions -> Maybe (f p) -> f p -> [(Node, Node)]
forall {k} (f :: k -> *) (p :: k).
GToFields f =>
YamlOptions -> Maybe (f p) -> f p -> [(Node, Node)]
gToEntries YamlOptions
opts (C1 ('MetaCons name fixity isRecord) f p -> f p
forall k i (c :: Meta) (f :: k -> *) (p :: k). M1 i c f p -> f p
unM1 (C1 ('MetaCons name fixity isRecord) f p -> f p)
-> Maybe (C1 ('MetaCons name fixity isRecord) f p) -> Maybe (f p)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Maybe (C1 ('MetaCons name fixity isRecord) f p)
def) f p
x)
| Bool
otherwise -> Node -> Maybe Node -> Node
forall a. a -> Maybe a -> a
fromMaybe ([(Node, Node)] -> Node
mapping []) (f p -> Maybe Node
forall (p :: k). f p -> Maybe Node
forall {k} (f :: k -> *) (p :: k). GToFields f => f p -> Maybe Node
gToValue f p
x)
where
withTagEntry :: [(S.Node, S.Node)] -> [(S.Node, S.Node)]
withTagEntry :: [(Node, Node)] -> [(Node, Node)]
withTagEntry [(Node, Node)]
entries = (YamlOptions
opts.tagKey Text -> Text -> (Node, Node)
forall a. ToYaml a => Text -> a -> (Node, Node)
.= YamlOptions -> C1 ('MetaCons name fixity isRecord) f p -> Text
forall (p :: k).
YamlOptions -> C1 ('MetaCons name fixity isRecord) f p -> Text
forall {k} (f :: k -> *) (p :: k).
GToConstructor f =>
YamlOptions -> f p -> Text
gTag YamlOptions
opts C1 ('MetaCons name fixity isRecord) f p
c) (Node, Node) -> [(Node, Node)] -> [(Node, Node)]
forall a. a -> [a] -> [a]
: [(Node, Node)]
entries
flatEntries :: S.Node -> Maybe [(S.Node, S.Node)]
flatEntries :: Node -> Maybe [(Node, Node)]
flatEntries Node
v = case Node
v.content of
S.MappingContent CollectionStyle
_ [(Node, Node)]
kvs
| [(Node, Node)] -> Bool
forall a. [a] -> Bool
forall (t :: * -> *) a. Foldable t => t a -> Bool
null [(Node, Node)]
kvs -> Maybe [(Node, Node)]
forall a. Maybe a
Nothing
| Maybe Text -> Bool
forall a. Maybe a -> Bool
isJust Node
v.props.anchor -> Maybe [(Node, Node)]
forall a. Maybe a
Nothing
| Node
v.props.tag Tag -> Tag -> Bool
forall a. Eq a => a -> a -> Bool
/= Tag
S.NoTag -> Maybe [(Node, Node)]
forall a. Maybe a
Nothing
| ((Node, Node) -> Bool) -> [(Node, Node)] -> Bool
forall (t :: * -> *) a. Foldable t => (a -> Bool) -> t a -> Bool
any (\(Node
k, Node
_) -> Text -> Node -> Bool
isKey YamlOptions
opts.tagKey Node
k Bool -> Bool -> Bool
|| Text -> Node -> Bool
isKey YamlOptions
opts.contentsKey Node
k) [(Node, Node)]
kvs ->
Maybe [(Node, Node)]
forall a. Maybe a
Nothing
| Bool
otherwise -> [(Node, Node)] -> Maybe [(Node, Node)]
forall a. a -> Maybe a
Just [(Node, Node)]
kvs
Content
_ -> Maybe [(Node, Node)]
forall a. Maybe a
Nothing
{-# INLINE gToConstructor #-}
gToUntaggedEntry :: forall (p :: k).
Node
-> C1 ('MetaCons name fixity isRecord) f p -> Maybe (Node, Node)
gToUntaggedEntry Node
k (M1 f p
x)
| forall {k} (f :: k). GFields f => Bool
forall (f :: k -> *). GFields f => Bool
gNamed @f Bool -> Bool -> Bool
|| forall {k} (f :: k). GFields f => Int
forall (f :: k -> *). GFields f => Int
gArity @f Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
== Int
0 = Maybe (Node, Node)
forall a. Maybe a
Nothing
| Bool
otherwise = (Node, Node) -> Maybe (Node, Node)
forall a. a -> Maybe a
Just (Node -> f p -> (Node, Node)
forall (p :: k). Node -> f p -> (Node, Node)
forall {k} (f :: k -> *) (p :: k).
GToFields f =>
Node -> f p -> (Node, Node)
gToEntry Node
k f p
x)
class GToFields f where
gToEntries :: YamlOptions -> Maybe (f p) -> f p -> [(S.Node, S.Node)]
gToEntries YamlOptions
_ Maybe (f p)
_ f p
_ = []
gToValue :: f p -> Maybe S.Node
gToValue f p
_ = Maybe Node
forall a. Maybe a
Nothing
gToEntry :: S.Node -> f p -> (S.Node, S.Node)
gToEntry Node
k f p
x = (Node
k, Node -> Maybe Node -> Node
forall a. a -> Maybe a -> a
fromMaybe ([(Node, Node)] -> Node
mapping []) (f p -> Maybe Node
forall (p :: k). f p -> Maybe Node
forall {k} (f :: k -> *) (p :: k). GToFields f => f p -> Maybe Node
gToValue f p
x))
instance GToFields U1
instance (GToFields f, GToFields g) => GToFields (f :*: g) where
gToEntries :: forall (p :: k).
YamlOptions -> Maybe ((:*:) f g p) -> (:*:) f g p -> [(Node, Node)]
gToEntries YamlOptions
opts Maybe ((:*:) f g p)
def (f p
a :*: g p
b) =
YamlOptions -> Maybe (f p) -> f p -> [(Node, Node)]
forall (p :: k).
YamlOptions -> Maybe (f p) -> f p -> [(Node, Node)]
forall {k} (f :: k -> *) (p :: k).
GToFields f =>
YamlOptions -> Maybe (f p) -> f p -> [(Node, Node)]
gToEntries YamlOptions
opts (Maybe ((:*:) f g p) -> Maybe (f p)
forall {k} (f :: k -> *) (g :: k -> *) (p :: k).
Maybe ((:*:) f g p) -> Maybe (f p)
firstDefault Maybe ((:*:) f g p)
def) f p
a [(Node, Node)] -> [(Node, Node)] -> [(Node, Node)]
forall a. [a] -> [a] -> [a]
++ YamlOptions -> Maybe (g p) -> g p -> [(Node, Node)]
forall (p :: k).
YamlOptions -> Maybe (g p) -> g p -> [(Node, Node)]
forall {k} (f :: k -> *) (p :: k).
GToFields f =>
YamlOptions -> Maybe (f p) -> f p -> [(Node, Node)]
gToEntries YamlOptions
opts (Maybe ((:*:) f g p) -> Maybe (g p)
forall {k} (f :: k -> *) (g :: k -> *) (p :: k).
Maybe ((:*:) f g p) -> Maybe (g p)
secondDefault Maybe ((:*:) f g p)
def) g p
b
{-# INLINE gToEntries #-}
instance
( KnownSymbol name
, ToYaml a
)
=> GToFields (S1 (MetaSel (Just name) u s d) (Rec0 a))
where
gToEntries :: forall (p :: k).
YamlOptions
-> Maybe (S1 ('MetaSel ('Just name) u s d) (Rec0 a) p)
-> S1 ('MetaSel ('Just name) u s d) (Rec0 a) p
-> [(Node, Node)]
gToEntries YamlOptions
opts Maybe (S1 ('MetaSel ('Just name) u s d) (Rec0 a) p)
def (M1 (K1 a
x))
| YamlOptions
opts.omitNullFields
Bool -> Bool -> Bool
&& Node -> Bool
isNullNode ((Node, Node) -> Node
forall a b. (a, b) -> b
snd (Node, Node)
entry)
Bool -> Bool -> Bool
&& Bool
uncommented
Bool -> Bool -> Bool
&& Bool
unanchored
Bool -> Bool -> Bool
&& Bool
nullDefault =
[]
| Bool
otherwise = [(Node, Node)
entry]
where
entry :: (S.Node, S.Node)
entry :: (Node, Node)
entry = forall (name :: Symbol). KnownSymbol name => YamlOptions -> Text
fieldKey @name YamlOptions
opts Text -> a -> (Node, Node)
forall a. ToYaml a => Text -> a -> (Node, Node)
.= a
x
uncommented :: Bool
uncommented :: Bool
uncommented =
((Node, Node) -> Node
forall a b. (a, b) -> a
fst (Node, Node)
entry).comments Comments -> Comments -> Bool
forall a. Eq a => a -> a -> Bool
== Comments
S.noComments Bool -> Bool -> Bool
&& ((Node, Node) -> Node
forall a b. (a, b) -> b
snd (Node, Node)
entry).comments Comments -> Comments -> Bool
forall a. Eq a => a -> a -> Bool
== Comments
S.noComments
unanchored :: Bool
unanchored :: Bool
unanchored = Maybe Text -> Bool
forall a. Maybe a -> Bool
isNothing ((Node, Node) -> Node
forall a b. (a, b) -> b
snd (Node, Node)
entry).props.anchor
nullDefault :: Bool
nullDefault :: Bool
nullDefault = case Maybe (S1 ('MetaSel ('Just name) u s d) (Rec0 a) p)
def of
Just (M1 (K1 a
d)) -> a -> Bool
forall a. ToYaml a => a -> Bool
isNullDefault a
d
Maybe (S1 ('MetaSel ('Just name) u s d) (Rec0 a) p)
Nothing -> Bool
True
{-# INLINE gToEntries #-}
isNullDefault :: ToYaml a => a -> Bool
isNullDefault :: forall a. ToYaml a => a -> Bool
isNullDefault a
d = case a -> Node
forall a. ToYaml a => a -> Node
toYaml (a -> Node) -> Maybe a -> Maybe Node
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> a -> Maybe a
forall a. a -> Maybe a
defaultField a
d of
Just Node
n -> Node -> Bool
isNullNode Node
n Bool -> Bool -> Bool
&& Node
n.comments Comments -> Comments -> Bool
forall a. Eq a => a -> a -> Bool
== Comments
S.noComments
Maybe Node
Nothing -> Bool
False
{-# NOINLINE isNullDefault #-}
instance ToYaml a => GToFields (S1 (MetaSel Nothing u s d) (Rec0 a)) where
gToValue :: forall (p :: k).
S1 ('MetaSel 'Nothing u s d) (Rec0 a) p -> Maybe Node
gToValue (M1 (K1 a
x)) = Node -> Maybe Node
forall a. a -> Maybe a
Just (a -> Node
forall a. ToYaml a => a -> Node
toYaml a
x)
gToEntry :: forall (p :: k).
Node -> S1 ('MetaSel 'Nothing u s d) (Rec0 a) p -> (Node, Node)
gToEntry Node
k (M1 (K1 a
x)) = Node -> a -> (Node, Node)
forall a. ToYaml a => Node -> a -> (Node, Node)
toYamlField Node
k a
x
genericParseYaml
:: forall a f
. ( Generic a
, GenericYamlOptions a
, GDatatype (Rep a)
, Constructors (Rep a) ~ f
, GConstructors f
, GEncoding (SumEncoding a) f
, GFromConstructor f
)
=> S.Node -> Parser a
genericParseYaml :: forall a (f :: * -> *).
(Generic a, GenericYamlOptions a, GDatatype (Rep a),
Constructors (Rep a) ~ f, GConstructors f,
GEncoding (SumEncoding a) f, GFromConstructor f) =>
Node -> Parser a
genericParseYaml Node
n =
let enc :: SumEncodingKind
enc = forall {k} (e :: SumEncodingKind) (f :: k).
GEncoding e f =>
SumEncodingKind
forall (e :: SumEncodingKind) (f :: * -> *).
GEncoding e f =>
SumEncodingKind
gEncoding @(SumEncoding a) @f
in SumEncodingKind
enc
SumEncodingKind -> Parser a -> Parser a
forall a b. a -> b -> b
`seq` forall a. (GenericYamlOptions a, GDatatype (Rep a)) => ()
checkDefault @a
() -> Parser a -> Parser a
forall a b. a -> b -> b
`seq` YamlOptions
-> SumEncodingKind
-> Maybe (Constructors (Rep a) (ZonkAny 1))
-> (Constructors (Rep a) (ZonkAny 1) -> a)
-> Node
-> Parser a
forall {k} (f :: k -> *) (p :: k) a.
(GConstructors f, GFromConstructor f) =>
YamlOptions
-> SumEncodingKind -> Maybe (f p) -> (f p -> a) -> Node -> Parser a
gParseYaml
(forall a. GenericYamlOptions a => YamlOptions
yamlOptions @a)
SumEncodingKind
enc
(Rep a (ZonkAny 1) -> Constructors (Rep a) (ZonkAny 1)
forall p. Rep a p -> Constructors (Rep a) p
forall (r :: * -> *) p. GDatatype r => r p -> Constructors r p
gUnwrap (Rep a (ZonkAny 1) -> Constructors (Rep a) (ZonkAny 1))
-> (a -> Rep a (ZonkAny 1))
-> a
-> Constructors (Rep a) (ZonkAny 1)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. a -> Rep a (ZonkAny 1)
forall x. a -> Rep a x
forall a x. Generic a => a -> Rep a x
from (a -> Constructors (Rep a) (ZonkAny 1))
-> Maybe a -> Maybe (Constructors (Rep a) (ZonkAny 1))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. GenericYamlOptions a => Maybe a
yamlDefault @a)
(Rep a (ZonkAny 1) -> a
forall a x. Generic a => Rep a x -> a
forall x. Rep a x -> a
to (Rep a (ZonkAny 1) -> a)
-> (Constructors (Rep a) (ZonkAny 1) -> Rep a (ZonkAny 1))
-> Constructors (Rep a) (ZonkAny 1)
-> a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Constructors (Rep a) (ZonkAny 1) -> Rep a (ZonkAny 1)
forall p. Constructors (Rep a) p -> Rep a p
forall (r :: * -> *) p. GDatatype r => Constructors r p -> r p
gWrap)
Node
n
{-# INLINE genericParseYaml #-}
gParseYaml
:: forall f p a
. ( GConstructors f
, GFromConstructor f
)
=> YamlOptions -> SumEncodingKind -> Maybe (f p) -> (f p -> a) -> S.Node -> Parser a
gParseYaml :: forall {k} (f :: k -> *) (p :: k) a.
(GConstructors f, GFromConstructor f) =>
YamlOptions
-> SumEncodingKind -> Maybe (f p) -> (f p -> a) -> Node -> Parser a
gParseYaml YamlOptions
opts SumEncodingKind
enc Maybe (f p)
def f p -> a
k Node
n
| forall {k} (f :: k). GConstructors f => Bool
forall (f :: k -> *). GConstructors f => Bool
gNullary @f =
[Text] -> (Text -> Parser a) -> Node -> Parser a
forall a. [Text] -> (Text -> Parser a) -> Node -> Parser a
withName [Text]
tags (\Text
t -> Parser a -> Maybe (Parser a) -> Parser a
forall a. a -> Maybe a -> a
fromMaybe (Node -> String -> Text -> Parser a
unknown Node
n String
"value" Text
t) (YamlOptions -> (f p -> a) -> Node -> Text -> Maybe (Parser a)
forall (p :: k) a.
YamlOptions -> (f p -> a) -> Node -> Text -> Maybe (Parser a)
forall {k} (f :: k -> *) (p :: k) a.
GFromConstructor f =>
YamlOptions -> (f p -> a) -> Node -> Text -> Maybe (Parser a)
gFromTag YamlOptions
opts f p -> a
k Node
n Text
t)) Node
n
| forall {k} (f :: k). GConstructors f => YamlOptions -> Bool
forall (f :: k -> *). GConstructors f => YamlOptions -> Bool
isTagged @f YamlOptions
opts, SumEncodingKind
enc SumEncodingKind -> SumEncodingKind -> Bool
forall a. Eq a => a -> a -> Bool
== SumEncodingKind
SingleField = Parser a
single
| forall {k} (f :: k). GConstructors f => YamlOptions -> Bool
forall (f :: k -> *). GConstructors f => YamlOptions -> Bool
isTagged @f YamlOptions
opts = (Object -> Parser a) -> Node -> Parser a
forall a. (Object -> Parser a) -> Node -> Parser a
withMapping Object -> Parser a
tagged Node
n
| Bool
otherwise = YamlOptions -> Maybe (f p) -> (f p -> a) -> Node -> Parser a
forall (p :: k) a.
YamlOptions -> Maybe (f p) -> (f p -> a) -> Node -> Parser a
forall {k} (f :: k -> *) (p :: k) a.
GFromConstructor f =>
YamlOptions -> Maybe (f p) -> (f p -> a) -> Node -> Parser a
gFromUntagged YamlOptions
opts Maybe (f p)
def f p -> a
k Node
n
where
tagged :: Object -> Parser a
tagged :: Object -> Parser a
tagged Object
o = case Text -> Map Text (Node, Node) -> Maybe (Node, Node)
forall k a. Ord k => k -> Map k a -> Maybe a
M.lookup YamlOptions
opts.tagKey Object
o.index of
Maybe (Node, Node)
Nothing -> Object -> Text -> Parser a
forall a. Object -> Text -> Parser a
missingKey Object
o YamlOptions
opts.tagKey
Just (Node
_, Node
tn) -> do
t <- [Text] -> (Text -> Parser Text) -> Node -> Parser Text
forall a. [Text] -> (Text -> Parser a) -> Node -> Parser a
withName [Text]
tags Text -> Parser Text
forall a. a -> Parser a
forall (f :: * -> *) a. Applicative f => a -> f a
pure Node
tn
fromMaybe (unknown tn "tag" t) (gFromTagged opts (enc == TaggedFlat) def k t o)
single :: Parser a
single :: Parser a
single = case Node -> View
view Node
n of
StringView Text
t -> Parser a -> Maybe (Parser a) -> Parser a
forall a. a -> Maybe a -> a
fromMaybe (Text -> Parser a
withoutValue Text
t) (YamlOptions -> (f p -> a) -> Node -> Text -> Maybe (Parser a)
forall (p :: k) a.
YamlOptions -> (f p -> a) -> Node -> Text -> Maybe (Parser a)
forall {k} (f :: k -> *) (p :: k) a.
GFromConstructor f =>
YamlOptions -> (f p -> a) -> Node -> Text -> Maybe (Parser a)
gFromTag YamlOptions
opts f p -> a
k Node
n Text
t)
View
_ | S.MappingContent {} <- Node
n.content -> (Object -> Parser a) -> Node -> Parser a
forall a. (Object -> Parser a) -> Node -> Parser a
withMapping Object -> Parser a
singleEntry Node
n
View
_ | Just String
msg <- [Text] -> Node -> Maybe String
unquotedName [Text]
tags Node
n -> Node -> String -> Parser a
forall a. Node -> String -> Parser a
failAt Node
n String
msg
View
_ -> String -> Node -> Parser a
forall a. String -> Node -> Parser a
typeMismatch String
"a string or a mapping with one key" Node
n
singleEntry :: Object -> Parser a
singleEntry :: Object -> Parser a
singleEntry Object
o = case Object -> [(Node, Node)]
objectEntries Object
o of
[(Node
kn, Node
v)] -> do
t <- [Text] -> (Text -> Parser Text) -> Node -> Parser Text
forall a. [Text] -> (Text -> Parser a) -> Node -> Parser a
withName [Text]
tags Text -> Parser Text
forall a. a -> Parser a
forall (f :: * -> *) a. Applicative f => a -> f a
pure Node
kn
fromMaybe (unknown kn "constructor" t) (gFromSingle opts def k t (kn, v))
(Node, Node)
_ : (Node
kn, Node
_) : [(Node, Node)]
_ -> Node -> String -> Parser a
forall a. Node -> String -> Parser a
failAt Node
kn String
"expected a mapping with one key, but got a second key"
[] -> Node -> String -> Parser a
forall a. Node -> String -> Parser a
failAt Node
n String
"expected a mapping with one key, but got an empty mapping"
withoutValue :: T.Text -> Parser a
withoutValue :: Text -> Parser a
withoutValue Text
t
| Text
t Text -> [Text] -> Bool
forall a. Eq a => a -> [a] -> Bool
forall (t :: * -> *) a. (Foldable t, Eq a) => a -> t a -> Bool
`elem` [Text]
tags =
Node -> String -> Parser a
forall a. Node -> String -> Parser a
failAt Node
n (String -> Parser a) -> String -> Parser a
forall a b. (a -> b) -> a -> b
$
String
"expected a mapping with the key "
String -> String -> String
forall a. [a] -> [a] -> [a]
++ Text -> String
showText Text
t
String -> String -> String
forall a. [a] -> [a] -> [a]
++ String
", because the constructor has fields"
| Bool
otherwise = Node -> String -> Text -> Parser a
unknown Node
n String
"constructor" Text
t
unknown :: S.Node -> String -> T.Text -> Parser a
unknown :: Node -> String -> Text -> Parser a
unknown Node
node String
what = String -> [Text] -> Node -> Text -> Parser a
forall a. String -> [Text] -> Node -> Text -> Parser a
unknownName String
what [Text]
tags Node
node
tags :: [T.Text]
tags :: [Text]
tags = (String -> Text) -> [String] -> [Text]
forall a b. (a -> b) -> [a] -> [b]
map (YamlOptions -> String -> Text
constructorTag YamlOptions
opts) (forall {k} (f :: k). GConstructors f => [String]
forall (f :: k -> *). GConstructors f => [String]
gConstructorNames @f)
{-# INLINE gParseYaml #-}
class GFromConstructor f where
gFromTag :: YamlOptions -> (f p -> a) -> S.Node -> T.Text -> Maybe (Parser a)
gFromTagged
:: YamlOptions
-> Bool
-> Maybe (f p)
-> (f p -> a)
-> T.Text
-> Object
-> Maybe (Parser a)
gFromSingle
:: YamlOptions
-> Maybe (f p)
-> (f p -> a)
-> T.Text
-> (S.Node, S.Node)
-> Maybe (Parser a)
gFromUntagged :: YamlOptions -> Maybe (f p) -> (f p -> a) -> S.Node -> Parser a
gFromUntaggedEntry :: (f p -> a) -> (S.Node, S.Node) -> Maybe (Parser a)
instance GFromConstructor V1 where
gFromTag :: forall (p :: k) a.
YamlOptions -> (V1 p -> a) -> Node -> Text -> Maybe (Parser a)
gFromTag YamlOptions
_ V1 p -> a
_ Node
_ Text
_ = Maybe (Parser a)
forall a. Maybe a
Nothing
gFromTagged :: forall (p :: k) a.
YamlOptions
-> Bool
-> Maybe (V1 p)
-> (V1 p -> a)
-> Text
-> Object
-> Maybe (Parser a)
gFromTagged YamlOptions
_ Bool
_ Maybe (V1 p)
_ V1 p -> a
_ Text
_ Object
_ = Maybe (Parser a)
forall a. Maybe a
Nothing
gFromSingle :: forall (p :: k) a.
YamlOptions
-> Maybe (V1 p)
-> (V1 p -> a)
-> Text
-> (Node, Node)
-> Maybe (Parser a)
gFromSingle YamlOptions
_ Maybe (V1 p)
_ V1 p -> a
_ Text
_ (Node, Node)
_ = Maybe (Parser a)
forall a. Maybe a
Nothing
gFromUntagged :: forall (p :: k) a.
YamlOptions -> Maybe (V1 p) -> (V1 p -> a) -> Node -> Parser a
gFromUntagged YamlOptions
_ Maybe (V1 p)
_ V1 p -> a
_ Node
_ = String -> Parser a
forall a. String -> Parser a
forall (m :: * -> *) a. MonadFail m => String -> m a
fail String
"expected a type with constructors"
gFromUntaggedEntry :: forall (p :: k) a. (V1 p -> a) -> (Node, Node) -> Maybe (Parser a)
gFromUntaggedEntry V1 p -> a
_ (Node, Node)
_ = Maybe (Parser a)
forall a. Maybe a
Nothing
instance (GFromConstructor f, GFromConstructor g) => GFromConstructor (f :+: g) where
gFromTag :: forall (p :: k) a.
YamlOptions
-> ((:+:) f g p -> a) -> Node -> Text -> Maybe (Parser a)
gFromTag YamlOptions
opts (:+:) f g p -> a
k Node
n Text
t = YamlOptions -> (f p -> a) -> Node -> Text -> Maybe (Parser a)
forall (p :: k) a.
YamlOptions -> (f p -> a) -> Node -> Text -> Maybe (Parser a)
forall {k} (f :: k -> *) (p :: k) a.
GFromConstructor f =>
YamlOptions -> (f p -> a) -> Node -> Text -> Maybe (Parser a)
gFromTag YamlOptions
opts ((:+:) f g p -> a
k ((:+:) f g p -> a) -> (f p -> (:+:) f g p) -> f p -> a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. f p -> (:+:) f g p
forall k (f :: k -> *) (g :: k -> *) (p :: k). f p -> (:+:) f g p
L1) Node
n Text
t Maybe (Parser a) -> Maybe (Parser a) -> Maybe (Parser a)
forall a. Maybe a -> Maybe a -> Maybe a
forall (m :: * -> *) a. MonadPlus m => m a -> m a -> m a
`mplus` YamlOptions -> (g p -> a) -> Node -> Text -> Maybe (Parser a)
forall (p :: k) a.
YamlOptions -> (g p -> a) -> Node -> Text -> Maybe (Parser a)
forall {k} (f :: k -> *) (p :: k) a.
GFromConstructor f =>
YamlOptions -> (f p -> a) -> Node -> Text -> Maybe (Parser a)
gFromTag YamlOptions
opts ((:+:) f g p -> a
k ((:+:) f g p -> a) -> (g p -> (:+:) f g p) -> g p -> a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. g p -> (:+:) f g p
forall k (f :: k -> *) (g :: k -> *) (p :: k). g p -> (:+:) f g p
R1) Node
n Text
t
{-# INLINE gFromTag #-}
gFromTagged :: forall (p :: k) a.
YamlOptions
-> Bool
-> Maybe ((:+:) f g p)
-> ((:+:) f g p -> a)
-> Text
-> Object
-> Maybe (Parser a)
gFromTagged YamlOptions
opts Bool
flat Maybe ((:+:) f g p)
def (:+:) f g p -> a
k Text
t Object
o =
YamlOptions
-> Bool
-> Maybe (f p)
-> (f p -> a)
-> Text
-> Object
-> Maybe (Parser a)
forall (p :: k) a.
YamlOptions
-> Bool
-> Maybe (f p)
-> (f p -> a)
-> Text
-> Object
-> Maybe (Parser a)
forall {k} (f :: k -> *) (p :: k) a.
GFromConstructor f =>
YamlOptions
-> Bool
-> Maybe (f p)
-> (f p -> a)
-> Text
-> Object
-> Maybe (Parser a)
gFromTagged YamlOptions
opts Bool
flat (Maybe ((:+:) f g p) -> Maybe (f p)
forall {k} (f :: k -> *) (g :: k -> *) (p :: k).
Maybe ((:+:) f g p) -> Maybe (f p)
leftDefault Maybe ((:+:) f g p)
def) ((:+:) f g p -> a
k ((:+:) f g p -> a) -> (f p -> (:+:) f g p) -> f p -> a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. f p -> (:+:) f g p
forall k (f :: k -> *) (g :: k -> *) (p :: k). f p -> (:+:) f g p
L1) Text
t Object
o
Maybe (Parser a) -> Maybe (Parser a) -> Maybe (Parser a)
forall a. Maybe a -> Maybe a -> Maybe a
forall (m :: * -> *) a. MonadPlus m => m a -> m a -> m a
`mplus` YamlOptions
-> Bool
-> Maybe (g p)
-> (g p -> a)
-> Text
-> Object
-> Maybe (Parser a)
forall (p :: k) a.
YamlOptions
-> Bool
-> Maybe (g p)
-> (g p -> a)
-> Text
-> Object
-> Maybe (Parser a)
forall {k} (f :: k -> *) (p :: k) a.
GFromConstructor f =>
YamlOptions
-> Bool
-> Maybe (f p)
-> (f p -> a)
-> Text
-> Object
-> Maybe (Parser a)
gFromTagged YamlOptions
opts Bool
flat (Maybe ((:+:) f g p) -> Maybe (g p)
forall {k} (f :: k -> *) (g :: k -> *) (p :: k).
Maybe ((:+:) f g p) -> Maybe (g p)
rightDefault Maybe ((:+:) f g p)
def) ((:+:) f g p -> a
k ((:+:) f g p -> a) -> (g p -> (:+:) f g p) -> g p -> a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. g p -> (:+:) f g p
forall k (f :: k -> *) (g :: k -> *) (p :: k). g p -> (:+:) f g p
R1) Text
t Object
o
{-# INLINE gFromTagged #-}
gFromSingle :: forall (p :: k) a.
YamlOptions
-> Maybe ((:+:) f g p)
-> ((:+:) f g p -> a)
-> Text
-> (Node, Node)
-> Maybe (Parser a)
gFromSingle YamlOptions
opts Maybe ((:+:) f g p)
def (:+:) f g p -> a
k Text
t (Node, Node)
entry =
YamlOptions
-> Maybe (f p)
-> (f p -> a)
-> Text
-> (Node, Node)
-> Maybe (Parser a)
forall (p :: k) a.
YamlOptions
-> Maybe (f p)
-> (f p -> a)
-> Text
-> (Node, Node)
-> Maybe (Parser a)
forall {k} (f :: k -> *) (p :: k) a.
GFromConstructor f =>
YamlOptions
-> Maybe (f p)
-> (f p -> a)
-> Text
-> (Node, Node)
-> Maybe (Parser a)
gFromSingle YamlOptions
opts (Maybe ((:+:) f g p) -> Maybe (f p)
forall {k} (f :: k -> *) (g :: k -> *) (p :: k).
Maybe ((:+:) f g p) -> Maybe (f p)
leftDefault Maybe ((:+:) f g p)
def) ((:+:) f g p -> a
k ((:+:) f g p -> a) -> (f p -> (:+:) f g p) -> f p -> a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. f p -> (:+:) f g p
forall k (f :: k -> *) (g :: k -> *) (p :: k). f p -> (:+:) f g p
L1) Text
t (Node, Node)
entry
Maybe (Parser a) -> Maybe (Parser a) -> Maybe (Parser a)
forall a. Maybe a -> Maybe a -> Maybe a
forall (m :: * -> *) a. MonadPlus m => m a -> m a -> m a
`mplus` YamlOptions
-> Maybe (g p)
-> (g p -> a)
-> Text
-> (Node, Node)
-> Maybe (Parser a)
forall (p :: k) a.
YamlOptions
-> Maybe (g p)
-> (g p -> a)
-> Text
-> (Node, Node)
-> Maybe (Parser a)
forall {k} (f :: k -> *) (p :: k) a.
GFromConstructor f =>
YamlOptions
-> Maybe (f p)
-> (f p -> a)
-> Text
-> (Node, Node)
-> Maybe (Parser a)
gFromSingle YamlOptions
opts (Maybe ((:+:) f g p) -> Maybe (g p)
forall {k} (f :: k -> *) (g :: k -> *) (p :: k).
Maybe ((:+:) f g p) -> Maybe (g p)
rightDefault Maybe ((:+:) f g p)
def) ((:+:) f g p -> a
k ((:+:) f g p -> a) -> (g p -> (:+:) f g p) -> g p -> a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. g p -> (:+:) f g p
forall k (f :: k -> *) (g :: k -> *) (p :: k). g p -> (:+:) f g p
R1) Text
t (Node, Node)
entry
{-# INLINE gFromSingle #-}
gFromUntagged :: forall (p :: k) a.
YamlOptions
-> Maybe ((:+:) f g p) -> ((:+:) f g p -> a) -> Node -> Parser a
gFromUntagged YamlOptions
_ Maybe ((:+:) f g p)
_ (:+:) f g p -> a
_ Node
_ = String -> Parser a
forall a. String -> Parser a
forall (m :: * -> *) a. MonadFail m => String -> m a
fail String
"expected a tag"
gFromUntaggedEntry :: forall (p :: k) a.
((:+:) f g p -> a) -> (Node, Node) -> Maybe (Parser a)
gFromUntaggedEntry (:+:) f g p -> a
_ (Node, Node)
_ = Maybe (Parser a)
forall a. Maybe a
Nothing
instance
( KnownSymbol name
, GFields f
, GFromFields f
)
=> GFromConstructor (C1 (MetaCons name fixity isRecord) f)
where
gFromTag :: forall (p :: k) a.
YamlOptions
-> (C1 ('MetaCons name fixity isRecord) f p -> a)
-> Node
-> Text
-> Maybe (Parser a)
gFromTag YamlOptions
opts C1 ('MetaCons name fixity isRecord) f p -> a
k Node
n Text
t
| Text
t Text -> Text -> Bool
forall a. Eq a => a -> a -> Bool
== Text
tag Bool -> Bool -> Bool
&& forall {k} (f :: k). GFields f => Int
forall (f :: k -> *). GFields f => Int
gArity @f Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
== Int
0 = Parser a -> Maybe (Parser a)
forall a. a -> Maybe a
Just (C1 ('MetaCons name fixity isRecord) f p -> a
k (C1 ('MetaCons name fixity isRecord) f p -> a)
-> (f p -> C1 ('MetaCons name fixity isRecord) f p) -> f p -> a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. f p -> C1 ('MetaCons name fixity isRecord) f p
forall k i (c :: Meta) (f :: k -> *) (p :: k). f p -> M1 i c f p
M1 (f p -> a) -> Parser (f p) -> Parser a
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Node -> Parser (f p)
forall (p :: k). Node -> Parser (f p)
forall {k} (f :: k -> *) (p :: k).
GFromFields f =>
Node -> Parser (f p)
gFromValue Node
n)
| Bool
otherwise = Maybe (Parser a)
forall a. Maybe a
Nothing
where
tag :: T.Text
tag :: Text
tag = forall (name :: Symbol). KnownSymbol name => YamlOptions -> Text
constructorTagOf @name YamlOptions
opts
{-# INLINE gFromTag #-}
gFromTagged :: forall (p :: k) a.
YamlOptions
-> Bool
-> Maybe (C1 ('MetaCons name fixity isRecord) f p)
-> (C1 ('MetaCons name fixity isRecord) f p -> a)
-> Text
-> Object
-> Maybe (Parser a)
gFromTagged YamlOptions
opts Bool
flat Maybe (C1 ('MetaCons name fixity isRecord) f p)
def C1 ('MetaCons name fixity isRecord) f p -> a
k Text
t Object
o
| Text
t Text -> Text -> Bool
forall a. Eq a => a -> a -> Bool
== forall (name :: Symbol). KnownSymbol name => YamlOptions -> Text
constructorTagOf @name YamlOptions
opts =
Parser a -> Maybe (Parser a)
forall a. a -> Maybe a
Just (C1 ('MetaCons name fixity isRecord) f p -> a
k (C1 ('MetaCons name fixity isRecord) f p -> a)
-> (f p -> C1 ('MetaCons name fixity isRecord) f p) -> f p -> a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. f p -> C1 ('MetaCons name fixity isRecord) f p
forall k i (c :: Meta) (f :: k -> *) (p :: k). f p -> M1 i c f p
M1 (f p -> a) -> Parser (f p) -> Parser a
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> YamlOptions
-> Bool -> [Text] -> Maybe (f p) -> Object -> Parser (f p)
forall {k} (f :: k -> *) (p :: k).
(GFields f, GFromFields f) =>
YamlOptions
-> Bool -> [Text] -> Maybe (f p) -> Object -> Parser (f p)
fromObject YamlOptions
opts Bool
flat [YamlOptions
opts.tagKey] (C1 ('MetaCons name fixity isRecord) f p -> f p
forall k i (c :: Meta) (f :: k -> *) (p :: k). M1 i c f p -> f p
unM1 (C1 ('MetaCons name fixity isRecord) f p -> f p)
-> Maybe (C1 ('MetaCons name fixity isRecord) f p) -> Maybe (f p)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Maybe (C1 ('MetaCons name fixity isRecord) f p)
def) Object
o)
| Bool
otherwise = Maybe (Parser a)
forall a. Maybe a
Nothing
{-# INLINE gFromTagged #-}
gFromSingle :: forall (p :: k) a.
YamlOptions
-> Maybe (C1 ('MetaCons name fixity isRecord) f p)
-> (C1 ('MetaCons name fixity isRecord) f p -> a)
-> Text
-> (Node, Node)
-> Maybe (Parser a)
gFromSingle YamlOptions
opts Maybe (C1 ('MetaCons name fixity isRecord) f p)
def C1 ('MetaCons name fixity isRecord) f p -> a
k Text
t entry :: (Node, Node)
entry@(Node
kn, Node
v)
| Text
t Text -> Text -> Bool
forall a. Eq a => a -> a -> Bool
/= forall (name :: Symbol). KnownSymbol name => YamlOptions -> Text
constructorTagOf @name YamlOptions
opts = Maybe (Parser a)
forall a. Maybe a
Nothing
| forall {k} (f :: k). GFields f => Bool
forall (f :: k -> *). GFields f => Bool
gNamed @f =
Parser a -> Maybe (Parser a)
forall a. a -> Maybe a
Just ((Object -> Parser a) -> Node -> Parser a
forall a. (Object -> Parser a) -> Node -> Parser a
withMapping ((f p -> a) -> Parser (f p) -> Parser a
forall a b. (a -> b) -> Parser a -> Parser b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap (C1 ('MetaCons name fixity isRecord) f p -> a
k (C1 ('MetaCons name fixity isRecord) f p -> a)
-> (f p -> C1 ('MetaCons name fixity isRecord) f p) -> f p -> a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. f p -> C1 ('MetaCons name fixity isRecord) f p
forall k i (c :: Meta) (f :: k -> *) (p :: k). f p -> M1 i c f p
M1) (Parser (f p) -> Parser a)
-> (Object -> Parser (f p)) -> Object -> Parser a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. YamlOptions
-> Bool -> [Text] -> Maybe (f p) -> Object -> Parser (f p)
forall {k} (f :: k -> *) (p :: k).
(GFields f, GFromFields f) =>
YamlOptions
-> Bool -> [Text] -> Maybe (f p) -> Object -> Parser (f p)
fromObject YamlOptions
opts Bool
False [] (C1 ('MetaCons name fixity isRecord) f p -> f p
forall k i (c :: Meta) (f :: k -> *) (p :: k). M1 i c f p -> f p
unM1 (C1 ('MetaCons name fixity isRecord) f p -> f p)
-> Maybe (C1 ('MetaCons name fixity isRecord) f p) -> Maybe (f p)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Maybe (C1 ('MetaCons name fixity isRecord) f p)
def)) Node
v)
| forall {k} (f :: k). GFields f => Int
forall (f :: k -> *). GFields f => Int
gArity @f Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
== Int
0 =
Parser a -> Maybe (Parser a)
forall a. a -> Maybe a
Just (Parser a -> Maybe (Parser a))
-> (String -> Parser a) -> String -> Maybe (Parser a)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Node -> String -> Parser a
forall a. Node -> String -> Parser a
failAt Node
kn (String -> Maybe (Parser a)) -> String -> Maybe (Parser a)
forall a b. (a -> b) -> a -> b
$
String
"expected the string "
String -> String -> String
forall a. [a] -> [a] -> [a]
++ Text -> String
showText Text
t
String -> String -> String
forall a. [a] -> [a] -> [a]
++ String
", because the constructor has no fields"
| Bool
otherwise = Parser a -> Maybe (Parser a)
forall a. a -> Maybe a
Just (C1 ('MetaCons name fixity isRecord) f p -> a
k (C1 ('MetaCons name fixity isRecord) f p -> a)
-> (f p -> C1 ('MetaCons name fixity isRecord) f p) -> f p -> a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. f p -> C1 ('MetaCons name fixity isRecord) f p
forall k i (c :: Meta) (f :: k -> *) (p :: k). f p -> M1 i c f p
M1 (f p -> a) -> Parser (f p) -> Parser a
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Node, Node) -> Parser (f p)
forall (p :: k). (Node, Node) -> Parser (f p)
forall {k} (f :: k -> *) (p :: k).
GFromFields f =>
(Node, Node) -> Parser (f p)
gFromEntry (Node, Node)
entry)
{-# INLINE gFromSingle #-}
gFromUntagged :: forall (p :: k) a.
YamlOptions
-> Maybe (C1 ('MetaCons name fixity isRecord) f p)
-> (C1 ('MetaCons name fixity isRecord) f p -> a)
-> Node
-> Parser a
gFromUntagged YamlOptions
opts Maybe (C1 ('MetaCons name fixity isRecord) f p)
def C1 ('MetaCons name fixity isRecord) f p -> a
k Node
n
| forall {k} (f :: k). GFields f => Bool
forall (f :: k -> *). GFields f => Bool
gNamed @f Bool -> Bool -> Bool
|| forall {k} (f :: k). GFields f => Int
forall (f :: k -> *). GFields f => Int
gArity @f Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
== Int
0 =
(Object -> Parser a) -> Node -> Parser a
forall a. (Object -> Parser a) -> Node -> Parser a
withMapping ((f p -> a) -> Parser (f p) -> Parser a
forall a b. (a -> b) -> Parser a -> Parser b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap (C1 ('MetaCons name fixity isRecord) f p -> a
k (C1 ('MetaCons name fixity isRecord) f p -> a)
-> (f p -> C1 ('MetaCons name fixity isRecord) f p) -> f p -> a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. f p -> C1 ('MetaCons name fixity isRecord) f p
forall k i (c :: Meta) (f :: k -> *) (p :: k). f p -> M1 i c f p
M1) (Parser (f p) -> Parser a)
-> (Object -> Parser (f p)) -> Object -> Parser a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. YamlOptions
-> Bool -> [Text] -> Maybe (f p) -> Object -> Parser (f p)
forall {k} (f :: k -> *) (p :: k).
(GFields f, GFromFields f) =>
YamlOptions
-> Bool -> [Text] -> Maybe (f p) -> Object -> Parser (f p)
fromObject YamlOptions
opts Bool
False [] (C1 ('MetaCons name fixity isRecord) f p -> f p
forall k i (c :: Meta) (f :: k -> *) (p :: k). M1 i c f p -> f p
unM1 (C1 ('MetaCons name fixity isRecord) f p -> f p)
-> Maybe (C1 ('MetaCons name fixity isRecord) f p) -> Maybe (f p)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Maybe (C1 ('MetaCons name fixity isRecord) f p)
def)) Node
n
| Bool
otherwise = C1 ('MetaCons name fixity isRecord) f p -> a
k (C1 ('MetaCons name fixity isRecord) f p -> a)
-> (f p -> C1 ('MetaCons name fixity isRecord) f p) -> f p -> a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. f p -> C1 ('MetaCons name fixity isRecord) f p
forall k i (c :: Meta) (f :: k -> *) (p :: k). f p -> M1 i c f p
M1 (f p -> a) -> Parser (f p) -> Parser a
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Node -> Parser (f p)
forall (p :: k). Node -> Parser (f p)
forall {k} (f :: k -> *) (p :: k).
GFromFields f =>
Node -> Parser (f p)
gFromValue Node
n
{-# INLINE gFromUntagged #-}
gFromUntaggedEntry :: forall (p :: k) a.
(C1 ('MetaCons name fixity isRecord) f p -> a)
-> (Node, Node) -> Maybe (Parser a)
gFromUntaggedEntry C1 ('MetaCons name fixity isRecord) f p -> a
k (Node, Node)
entry
| forall {k} (f :: k). GFields f => Bool
forall (f :: k -> *). GFields f => Bool
gNamed @f Bool -> Bool -> Bool
|| forall {k} (f :: k). GFields f => Int
forall (f :: k -> *). GFields f => Int
gArity @f Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
== Int
0 = Maybe (Parser a)
forall a. Maybe a
Nothing
| Bool
otherwise = Parser a -> Maybe (Parser a)
forall a. a -> Maybe a
Just (C1 ('MetaCons name fixity isRecord) f p -> a
k (C1 ('MetaCons name fixity isRecord) f p -> a)
-> (f p -> C1 ('MetaCons name fixity isRecord) f p) -> f p -> a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. f p -> C1 ('MetaCons name fixity isRecord) f p
forall k i (c :: Meta) (f :: k -> *) (p :: k). f p -> M1 i c f p
M1 (f p -> a) -> Parser (f p) -> Parser a
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Node, Node) -> Parser (f p)
forall (p :: k). (Node, Node) -> Parser (f p)
forall {k} (f :: k -> *) (p :: k).
GFromFields f =>
(Node, Node) -> Parser (f p)
gFromEntry (Node, Node)
entry)
fromObject
:: forall f p
. ( GFields f
, GFromFields f
)
=> YamlOptions -> Bool -> [T.Text] -> Maybe (f p) -> Object -> Parser (f p)
fromObject :: forall {k} (f :: k -> *) (p :: k).
(GFields f, GFromFields f) =>
YamlOptions
-> Bool -> [Text] -> Maybe (f p) -> Object -> Parser (f p)
fromObject YamlOptions
opts Bool
flat [Text]
keys Maybe (f p)
def Object
o
| forall {k} (f :: k). GFields f => Bool
forall (f :: k -> *). GFields f => Bool
gNamed @f Bool -> Bool -> Bool
|| forall {k} (f :: k). GFields f => Int
forall (f :: k -> *). GFields f => Int
gArity @f Int -> Int -> Bool
forall a. Eq a => a -> a -> Bool
== Int
0 = [Text] -> Parser (f p) -> Parser (f p)
checked (forall {k} (f :: k). GFields f => YamlOptions -> [Text]
forall (f :: k -> *). GFields f => YamlOptions -> [Text]
gNames @f YamlOptions
opts) (YamlOptions -> Maybe (f p) -> Object -> Parser (f p)
forall (p :: k).
YamlOptions -> Maybe (f p) -> Object -> Parser (f p)
forall {k} (f :: k -> *) (p :: k).
GFromFields f =>
YamlOptions -> Maybe (f p) -> Object -> Parser (f p)
gFromObject YamlOptions
opts Maybe (f p)
def Object
o)
| Bool
flat
, Bool -> Bool
not ([(Node, Node)] -> Bool
forall a. [a] -> Bool
forall (t :: * -> *) a. Foldable t => t a -> Bool
null [(Node, Node)]
others)
, Bool -> Bool
not (((Node, Node) -> Bool) -> [(Node, Node)] -> Bool
forall (t :: * -> *) a. Foldable t => (a -> Bool) -> t a -> Bool
any (Text -> Node -> Bool
isKey YamlOptions
opts.contentsKey (Node -> Bool) -> ((Node, Node) -> Node) -> (Node, Node) -> Bool
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Node, Node) -> Node
forall a b. (a, b) -> a
fst) [(Node, Node)]
others) =
Parser (f p)
merged
| Bool
otherwise = [Text] -> Parser (f p) -> Parser (f p)
checked [YamlOptions
opts.contentsKey] (Parser (f p) -> Parser (f p)) -> Parser (f p) -> Parser (f p)
forall a b. (a -> b) -> a -> b
$ case Text -> Map Text (Node, Node) -> Maybe (Node, Node)
forall k a. Ord k => k -> Map k a -> Maybe a
M.lookup YamlOptions
opts.contentsKey Object
o.index of
Just (Node, Node)
entry -> (Node, Node) -> Parser (f p)
forall (p :: k). (Node, Node) -> Parser (f p)
forall {k} (f :: k -> *) (p :: k).
GFromFields f =>
(Node, Node) -> Parser (f p)
gFromEntry (Node, Node)
entry
Maybe (Node, Node)
Nothing
| Just f p
fields <- f p -> Maybe (f p)
forall (p :: k). f p -> Maybe (f p)
forall {k} (f :: k -> *) (p :: k).
GFromFields f =>
f p -> Maybe (f p)
gDefaultValue (f p -> Maybe (f p)) -> Maybe (f p) -> Maybe (f p)
forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
=<< Maybe (f p)
def -> f p -> Parser (f p)
forall a. a -> Parser a
forall (f :: * -> *) a. Applicative f => a -> f a
pure f p
fields
| Maybe (f p) -> Bool
forall a. Maybe a -> Bool
isJust Maybe (f p)
def, Bool -> Bool
not Bool
flat -> Object -> Text -> Parser (f p)
forall a. Object -> Text -> Parser a
missingKey Object
o YamlOptions
opts.contentsKey
| Bool
flat -> Parser (f p)
-> (f p -> Parser (f p)) -> Maybe (f p) -> Parser (f p)
forall b a. b -> (a -> b) -> Maybe a -> b
maybe Parser (f p)
onlyTag f p -> Parser (f p)
forall a. a -> Parser a
forall (f :: * -> *) a. Applicative f => a -> f a
pure ((Node -> Parser (f p)) -> Node -> Maybe (f p)
forall a. (Node -> Parser a) -> Node -> Maybe a
succeeds Node -> Parser (f p)
forall (p :: k). Node -> Parser (f p)
forall {k} (f :: k -> *) (p :: k).
GFromFields f =>
Node -> Parser (f p)
gFromValue Node
nullNode)
| Bool
otherwise ->
Parser (f p)
-> (f p -> Parser (f p)) -> Maybe (f p) -> Parser (f p)
forall b a. b -> (a -> b) -> Maybe a -> b
maybe (Object -> Text -> Parser (f p)
forall a. Object -> Text -> Parser a
missingKey Object
o YamlOptions
opts.contentsKey) f p -> Parser (f p)
forall a. a -> Parser a
forall (f :: * -> *) a. Applicative f => a -> f a
pure ((Node -> Parser (f p)) -> Node -> Maybe (f p)
forall a. (Node -> Parser a) -> Node -> Maybe a
succeeds Node -> Parser (f p)
forall (p :: k). Node -> Parser (f p)
forall {k} (f :: k -> *) (p :: k).
GFromFields f =>
Node -> Parser (f p)
gFromValue Node
nullNode)
where
checked :: [T.Text] -> Parser (f p) -> Parser (f p)
checked :: [Text] -> Parser (f p) -> Parser (f p)
checked [Text]
fields =
(Bool -> Parser () -> Parser ()
forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
when YamlOptions
opts.rejectUnknownFields ([Text] -> Object -> Parser ()
rejectUnknownKeys ([Text]
keys [Text] -> [Text] -> [Text]
forall a. [a] -> [a] -> [a]
++ [Text]
fields) Object
o) Parser () -> Parser (f p) -> Parser (f p)
forall a b. Parser a -> Parser b -> Parser b
forall (f :: * -> *) a b. Applicative f => f a -> f b -> f b
*>)
onlyTag :: Parser (f p)
onlyTag :: Parser (f p)
onlyTag =
Offset -> (Offset, String) -> Parser (f p) -> Parser (f p)
forall a. Offset -> (Offset, String) -> Parser a -> Parser a
withNote
(Object -> Node
objectNode Object
o).offset
( Offset -> (Node -> Offset) -> Maybe Node -> Offset
forall b a. b -> (a -> b) -> Maybe a -> b
maybe Offset
S.noOffset (.offset) Maybe Node
tag
, String
"the mapping has no key "
String -> String -> String
forall a. [a] -> [a] -> [a]
++ Text -> String
showText YamlOptions
opts.contentsKey
String -> String -> String
forall a. [a] -> [a] -> [a]
++ String
" and no other keys for the field of "
String -> String -> String
forall a. [a] -> [a] -> [a]
++ String -> (Node -> String) -> Maybe Node -> String
forall b a. b -> (a -> b) -> Maybe a -> b
maybe String
"" Node -> String
constructorName Maybe Node
tag
)
Parser (f p)
merged
where
tag :: Maybe S.Node
tag :: Maybe Node
tag = (Node, Node) -> Node
forall a b. (a, b) -> b
snd ((Node, Node) -> Node) -> Maybe (Node, Node) -> Maybe Node
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Text -> Map Text (Node, Node) -> Maybe (Node, Node)
forall k a. Ord k => k -> Map k a -> Maybe a
M.lookup YamlOptions
opts.tagKey Object
o.index
constructorName :: S.Node -> String
constructorName :: Node -> String
constructorName Node
n = case Node
n.content of
S.ScalarContent ScalarStyle
_ Text
t -> Text -> String
T.unpack Text
t
Content
_ -> String
""
merged :: Parser (f p)
merged :: Parser (f p)
merged =
let n :: Node
n = Object -> Node
objectNode Object
o
style :: CollectionStyle
style = case Node
n.content of
S.MappingContent CollectionStyle
s [(Node, Node)]
_ -> CollectionStyle
s
Content
_ -> CollectionStyle
S.Block
in Node -> Parser (f p)
forall (p :: k). Node -> Parser (f p)
forall {k} (f :: k -> *) (p :: k).
GFromFields f =>
Node -> Parser (f p)
gFromValue (Node -> Parser (f p)) -> Node -> Parser (f p)
forall a b. (a -> b) -> a -> b
$
S.Node
{ offset :: Offset
S.offset = Node
n.offset
, endOffset :: Offset
S.endOffset = Node
n.endOffset
, props :: Props
S.props = Props
S.noProps
, comments :: Comments
S.comments = Comments
S.noComments
, content :: Content
S.content = CollectionStyle -> [(Node, Node)] -> Content
S.MappingContent CollectionStyle
style [(Node, Node)]
others
}
others :: [(S.Node, S.Node)]
others :: [(Node, Node)]
others
| Object
o.duplicates = ((Node, Node) -> Bool) -> [(Node, Node)] -> [(Node, Node)]
forall a. (a -> Bool) -> [a] -> [a]
filter (\(Node
k, Node
_) -> Bool -> Bool
not ((Text -> Bool) -> [Text] -> Bool
forall (t :: * -> *) a. Foldable t => (a -> Bool) -> t a -> Bool
any (Text -> Node -> Bool
`isKey` Node
k) [Text]
keys)) (Object -> [(Node, Node)]
objectEntries Object
o)
| Bool
otherwise = (Text -> [(Node, Node)] -> [(Node, Node)])
-> [(Node, Node)] -> [Text] -> [(Node, Node)]
forall a b. (a -> b -> b) -> b -> [a] -> b
forall (t :: * -> *) a b.
Foldable t =>
(a -> b -> b) -> b -> t a -> b
foldr Text -> [(Node, Node)] -> [(Node, Node)]
removeKey (Object -> [(Node, Node)]
objectEntries Object
o) [Text]
keys
removeKey :: T.Text -> [(S.Node, S.Node)] -> [(S.Node, S.Node)]
removeKey :: Text -> [(Node, Node)] -> [(Node, Node)]
removeKey Text
key = \case
kv :: (Node, Node)
kv@(Node
k, Node
_) : [(Node, Node)]
kvs
| Text -> Node -> Bool
isKey Text
key Node
k -> [(Node, Node)]
kvs
| Bool
otherwise -> (Node, Node)
kv (Node, Node) -> [(Node, Node)] -> [(Node, Node)]
forall a. a -> [a] -> [a]
: Text -> [(Node, Node)] -> [(Node, Node)]
removeKey Text
key [(Node, Node)]
kvs
[] -> []
{-# INLINE fromObject #-}
class GFromFields f where
gFromObject :: YamlOptions -> Maybe (f p) -> Object -> Parser (f p)
gFromObject YamlOptions
_ Maybe (f p)
_ Object
o =
String -> Parser (f p)
forall a. String -> Parser a
forall (m :: * -> *) a. MonadFail m => String -> m a
fail (String -> Parser (f p)) -> String -> Parser (f p)
forall a b. (a -> b) -> a -> b
$ String
"expected a field without a name in " String -> String -> String
forall a. [a] -> [a] -> [a]
++ Node -> String
describeNode (Object -> Node
objectNode Object
o)
gFromValue :: S.Node -> Parser (f p)
gFromValue Node
n = String -> Parser (f p)
forall a. String -> Parser a
forall (m :: * -> *) a. MonadFail m => String -> m a
fail (String -> Parser (f p)) -> String -> Parser (f p)
forall a b. (a -> b) -> a -> b
$ String
"expected named fields in " String -> String -> String
forall a. [a] -> [a] -> [a]
++ Node -> String
describeNode Node
n
gFromEntry :: (S.Node, S.Node) -> Parser (f p)
gFromEntry (Node
_, Node
v) = Node -> Parser (f p)
forall (p :: k). Node -> Parser (f p)
forall {k} (f :: k -> *) (p :: k).
GFromFields f =>
Node -> Parser (f p)
gFromValue Node
v
gDefaultValue :: f p -> Maybe (f p)
gDefaultValue = f p -> Maybe (f p)
forall a. a -> Maybe a
Just
instance GFromFields U1 where
gFromObject :: forall (p :: k).
YamlOptions -> Maybe (U1 p) -> Object -> Parser (U1 p)
gFromObject YamlOptions
_ Maybe (U1 p)
_ Object
_ = U1 p -> Parser (U1 p)
forall a. a -> Parser a
forall (f :: * -> *) a. Applicative f => a -> f a
pure U1 p
forall k (p :: k). U1 p
U1
gFromValue :: forall (p :: k). Node -> Parser (U1 p)
gFromValue Node
_ = U1 p -> Parser (U1 p)
forall a. a -> Parser a
forall (f :: * -> *) a. Applicative f => a -> f a
pure U1 p
forall k (p :: k). U1 p
U1
instance (GFromFields f, GFromFields g) => GFromFields (f :*: g) where
gFromObject :: forall (p :: k).
YamlOptions
-> Maybe ((:*:) f g p) -> Object -> Parser ((:*:) f g p)
gFromObject YamlOptions
opts Maybe ((:*:) f g p)
def Object
o =
f p -> g p -> (:*:) f g p
forall k (f :: k -> *) (g :: k -> *) (p :: k).
f p -> g p -> (:*:) f g p
(:*:)
(f p -> g p -> (:*:) f g p)
-> Parser (f p) -> Parser (g p -> (:*:) f g p)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> YamlOptions -> Maybe (f p) -> Object -> Parser (f p)
forall (p :: k).
YamlOptions -> Maybe (f p) -> Object -> Parser (f p)
forall {k} (f :: k -> *) (p :: k).
GFromFields f =>
YamlOptions -> Maybe (f p) -> Object -> Parser (f p)
gFromObject YamlOptions
opts (Maybe ((:*:) f g p) -> Maybe (f p)
forall {k} (f :: k -> *) (g :: k -> *) (p :: k).
Maybe ((:*:) f g p) -> Maybe (f p)
firstDefault Maybe ((:*:) f g p)
def) Object
o
Parser (g p -> (:*:) f g p) -> Parser (g p) -> Parser ((:*:) f g p)
forall a b. Parser (a -> b) -> Parser a -> Parser b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> YamlOptions -> Maybe (g p) -> Object -> Parser (g p)
forall (p :: k).
YamlOptions -> Maybe (g p) -> Object -> Parser (g p)
forall {k} (f :: k -> *) (p :: k).
GFromFields f =>
YamlOptions -> Maybe (f p) -> Object -> Parser (f p)
gFromObject YamlOptions
opts (Maybe ((:*:) f g p) -> Maybe (g p)
forall {k} (f :: k -> *) (g :: k -> *) (p :: k).
Maybe ((:*:) f g p) -> Maybe (g p)
secondDefault Maybe ((:*:) f g p)
def) Object
o
{-# INLINE gFromObject #-}
instance
( KnownSymbol name
, FromYaml a
)
=> GFromFields (S1 (MetaSel (Just name) u s d) (Rec0 a))
where
gFromObject :: forall (p :: k).
YamlOptions
-> Maybe (S1 ('MetaSel ('Just name) u s d) (Rec0 a) p)
-> Object
-> Parser (S1 ('MetaSel ('Just name) u s d) (Rec0 a) p)
gFromObject YamlOptions
opts Maybe (S1 ('MetaSel ('Just name) u s d) (Rec0 a) p)
def Object
o =
Rec0 a p -> S1 ('MetaSel ('Just name) u s d) (Rec0 a) p
forall k i (c :: Meta) (f :: k -> *) (p :: k). f p -> M1 i c f p
M1 (Rec0 a p -> S1 ('MetaSel ('Just name) u s d) (Rec0 a) p)
-> (a -> Rec0 a p)
-> a
-> S1 ('MetaSel ('Just name) u s d) (Rec0 a) p
forall b c a. (b -> c) -> (a -> b) -> a -> c
. a -> Rec0 a p
forall k i c (p :: k). c -> K1 i c p
K1 (a -> S1 ('MetaSel ('Just name) u s d) (Rec0 a) p)
-> Parser a -> Parser (S1 ('MetaSel ('Just name) u s d) (Rec0 a) p)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> case Text -> Map Text (Node, Node) -> Maybe (Node, Node)
forall k a. Ord k => k -> Map k a -> Maybe a
M.lookup Text
key Object
o.index of
Just (Node, Node)
entry -> (Node, Node) -> Parser a
forall a. FromYaml a => (Node, Node) -> Parser a
parseEntry (Node, Node)
entry
Maybe (Node, Node)
Nothing -> case Maybe (S1 ('MetaSel ('Just name) u s d) (Rec0 a) p)
def of
Just (M1 (K1 a
d))
| Just a
x <- a -> Maybe a
forall a. a -> Maybe a
defaultField a
d -> a
x a -> Parser (Maybe (Node, Node)) -> Parser a
forall a b. a -> Parser b -> Parser a
forall (f :: * -> *) a b. Functor f => a -> f b -> f a
<$ Object -> Text -> Parser (Maybe (Node, Node))
findKey Object
o Text
key
| Bool
otherwise -> Object -> Text -> Parser a
forall a. Object -> Text -> Parser a
missingKey Object
o Text
key
Maybe (S1 ('MetaSel ('Just name) u s d) (Rec0 a) p)
Nothing ->
Parser a -> (a -> Parser a) -> Maybe a -> Parser a
forall b a. b -> (a -> b) -> Maybe a -> b
maybe (Object -> Text -> Parser a
forall a. Object -> Text -> Parser a
missingKey Object
o Text
key) (a -> Parser (Maybe (Node, Node)) -> Parser a
forall a b. a -> Parser b -> Parser a
forall (f :: * -> *) a b. Functor f => a -> f b -> f a
<$ Object -> Text -> Parser (Maybe (Node, Node))
findKey Object
o Text
key) ((Node -> Parser a) -> Node -> Maybe a
forall a. (Node -> Parser a) -> Node -> Maybe a
succeeds Node -> Parser a
forall a. FromYaml a => Node -> Parser a
parseYaml Node
nullNode)
where
key :: T.Text
key :: Text
key = forall (name :: Symbol). KnownSymbol name => YamlOptions -> Text
fieldKey @name YamlOptions
opts
{-# INLINE gFromObject #-}
instance FromYaml a => GFromFields (S1 (MetaSel Nothing u s d) (Rec0 a)) where
gFromValue :: forall (p :: k).
Node -> Parser (S1 ('MetaSel 'Nothing u s d) (Rec0 a) p)
gFromValue Node
n = Rec0 a p -> M1 S ('MetaSel 'Nothing u s d) (Rec0 a) p
forall k i (c :: Meta) (f :: k -> *) (p :: k). f p -> M1 i c f p
M1 (Rec0 a p -> M1 S ('MetaSel 'Nothing u s d) (Rec0 a) p)
-> (a -> Rec0 a p)
-> a
-> M1 S ('MetaSel 'Nothing u s d) (Rec0 a) p
forall b c a. (b -> c) -> (a -> b) -> a -> c
. a -> Rec0 a p
forall k i c (p :: k). c -> K1 i c p
K1 (a -> M1 S ('MetaSel 'Nothing u s d) (Rec0 a) p)
-> Parser a -> Parser (M1 S ('MetaSel 'Nothing u s d) (Rec0 a) p)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Node -> Parser a) -> Node -> Parser a
forall a. (Node -> Parser a) -> Node -> Parser a
parseNode Node -> Parser a
forall a. FromYaml a => Node -> Parser a
parseYaml Node
n
gFromEntry :: forall (p :: k).
(Node, Node) -> Parser (S1 ('MetaSel 'Nothing u s d) (Rec0 a) p)
gFromEntry (Node, Node)
entry = Rec0 a p -> M1 S ('MetaSel 'Nothing u s d) (Rec0 a) p
forall k i (c :: Meta) (f :: k -> *) (p :: k). f p -> M1 i c f p
M1 (Rec0 a p -> M1 S ('MetaSel 'Nothing u s d) (Rec0 a) p)
-> (a -> Rec0 a p)
-> a
-> M1 S ('MetaSel 'Nothing u s d) (Rec0 a) p
forall b c a. (b -> c) -> (a -> b) -> a -> c
. a -> Rec0 a p
forall k i c (p :: k). c -> K1 i c p
K1 (a -> M1 S ('MetaSel 'Nothing u s d) (Rec0 a) p)
-> Parser a -> Parser (M1 S ('MetaSel 'Nothing u s d) (Rec0 a) p)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Node, Node) -> Parser a
forall a. FromYaml a => (Node, Node) -> Parser a
parseEntry (Node, Node)
entry
gDefaultValue :: forall (p :: k).
S1 ('MetaSel 'Nothing u s d) (Rec0 a) p
-> Maybe (S1 ('MetaSel 'Nothing u s d) (Rec0 a) p)
gDefaultValue (M1 (K1 a
x)) = K1 R a p -> M1 S ('MetaSel 'Nothing u s d) (Rec0 a) p
forall k i (c :: Meta) (f :: k -> *) (p :: k). f p -> M1 i c f p
M1 (K1 R a p -> M1 S ('MetaSel 'Nothing u s d) (Rec0 a) p)
-> (a -> K1 R a p)
-> a
-> M1 S ('MetaSel 'Nothing u s d) (Rec0 a) p
forall b c a. (b -> c) -> (a -> b) -> a -> c
. a -> K1 R a p
forall k i c (p :: k). c -> K1 i c p
K1 (a -> M1 S ('MetaSel 'Nothing u s d) (Rec0 a) p)
-> Maybe a -> Maybe (M1 S ('MetaSel 'Nothing u s d) (Rec0 a) p)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> a -> Maybe a
forall a. a -> Maybe a
defaultField a
x
isKey :: T.Text -> S.Node -> Bool
isKey :: Text -> Node -> Bool
isKey Text
key Node
k = case Node -> Maybe Text
stringValue Node
k of
Just Text
t -> Text
t Text -> Text -> Bool
forall a. Eq a => a -> a -> Bool
== Text
key
Maybe Text
_ -> Bool
False