packages feed

argo 0.2022.2.2 → 0.2022.2.23

raw patch · 14 files changed

+1149/−1093 lines, 14 filesPVP: major bump suggested

API removals or changes: PVP suggests a major version bump

API changes (from Hackage documentation)

- Argo: schema :: QuasiQuoter
- Argo.Class.HasCodec: basicCodec :: forall a. Typeable a => Schema -> (a -> Value) -> (Value -> Maybe a) -> Value a
- Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Argo.Class.HasCodec.HasCodec b, Argo.Class.HasCodec.HasCodec c, Argo.Class.HasCodec.HasCodec d, Argo.Class.HasCodec.HasCodec e, Argo.Class.HasCodec.HasCodec f, Argo.Class.HasCodec.HasCodec g, Argo.Class.HasCodec.HasCodec h, Data.Typeable.Internal.Typeable a, Data.Typeable.Internal.Typeable b, Data.Typeable.Internal.Typeable c, Data.Typeable.Internal.Typeable d, Data.Typeable.Internal.Typeable e, Data.Typeable.Internal.Typeable f, Data.Typeable.Internal.Typeable g, Data.Typeable.Internal.Typeable h) => Argo.Class.HasCodec.HasCodec (a, b, c, d, e, f, g, h)
- Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Argo.Class.HasCodec.HasCodec b, Argo.Class.HasCodec.HasCodec c, Argo.Class.HasCodec.HasCodec d, Argo.Class.HasCodec.HasCodec e, Argo.Class.HasCodec.HasCodec f, Argo.Class.HasCodec.HasCodec g, Data.Typeable.Internal.Typeable a, Data.Typeable.Internal.Typeable b, Data.Typeable.Internal.Typeable c, Data.Typeable.Internal.Typeable d, Data.Typeable.Internal.Typeable e, Data.Typeable.Internal.Typeable f, Data.Typeable.Internal.Typeable g) => Argo.Class.HasCodec.HasCodec (a, b, c, d, e, f, g)
- Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Argo.Class.HasCodec.HasCodec b, Argo.Class.HasCodec.HasCodec c, Argo.Class.HasCodec.HasCodec d, Argo.Class.HasCodec.HasCodec e, Argo.Class.HasCodec.HasCodec f, Data.Typeable.Internal.Typeable a, Data.Typeable.Internal.Typeable b, Data.Typeable.Internal.Typeable c, Data.Typeable.Internal.Typeable d, Data.Typeable.Internal.Typeable e, Data.Typeable.Internal.Typeable f) => Argo.Class.HasCodec.HasCodec (a, b, c, d, e, f)
- Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Argo.Class.HasCodec.HasCodec b, Argo.Class.HasCodec.HasCodec c, Argo.Class.HasCodec.HasCodec d, Argo.Class.HasCodec.HasCodec e, Data.Typeable.Internal.Typeable a, Data.Typeable.Internal.Typeable b, Data.Typeable.Internal.Typeable c, Data.Typeable.Internal.Typeable d, Data.Typeable.Internal.Typeable e) => Argo.Class.HasCodec.HasCodec (a, b, c, d, e)
- Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Argo.Class.HasCodec.HasCodec b, Argo.Class.HasCodec.HasCodec c, Argo.Class.HasCodec.HasCodec d, Data.Typeable.Internal.Typeable a, Data.Typeable.Internal.Typeable b, Data.Typeable.Internal.Typeable c, Data.Typeable.Internal.Typeable d) => Argo.Class.HasCodec.HasCodec (a, b, c, d)
- Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Argo.Class.HasCodec.HasCodec b, Argo.Class.HasCodec.HasCodec c, Data.Typeable.Internal.Typeable a, Data.Typeable.Internal.Typeable b, Data.Typeable.Internal.Typeable c) => Argo.Class.HasCodec.HasCodec (a, b, c)
- Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Argo.Class.HasCodec.HasCodec b, Data.Typeable.Internal.Typeable a, Data.Typeable.Internal.Typeable b) => Argo.Class.HasCodec.HasCodec (Data.Either.Either a b)
- Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Argo.Class.HasCodec.HasCodec b, Data.Typeable.Internal.Typeable a, Data.Typeable.Internal.Typeable b) => Argo.Class.HasCodec.HasCodec (a, b)
- Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Data.Typeable.Internal.Typeable a) => Argo.Class.HasCodec.HasCodec (Argo.Json.Array.Array a)
- Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Data.Typeable.Internal.Typeable a) => Argo.Class.HasCodec.HasCodec (Argo.Json.Object.Object a)
- Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Data.Typeable.Internal.Typeable a) => Argo.Class.HasCodec.HasCodec (Data.Map.Internal.Map Argo.Json.Name.Name a)
- Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Data.Typeable.Internal.Typeable a) => Argo.Class.HasCodec.HasCodec (Data.Map.Internal.Map Argo.Json.String.String a)
- Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Data.Typeable.Internal.Typeable a) => Argo.Class.HasCodec.HasCodec (Data.Map.Internal.Map Argo.Vendor.Text.LazyText a)
- Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Data.Typeable.Internal.Typeable a) => Argo.Class.HasCodec.HasCodec (Data.Map.Internal.Map Data.Text.Internal.Text a)
- Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Data.Typeable.Internal.Typeable a) => Argo.Class.HasCodec.HasCodec (Data.Map.Internal.Map GHC.Base.String a)
- Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Data.Typeable.Internal.Typeable a) => Argo.Class.HasCodec.HasCodec (GHC.Base.NonEmpty a)
- Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Data.Typeable.Internal.Typeable a) => Argo.Class.HasCodec.HasCodec (GHC.Maybe.Maybe a)
- Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Data.Typeable.Internal.Typeable a) => Argo.Class.HasCodec.HasCodec [a]
- Argo.Codec.Value: ref :: Either Schema Identifier -> Value
- Argo.QuasiQuoter: schema :: QuasiQuoter
- Argo.Schema.Schema: Schema :: Value -> Schema
- Argo.Schema.Schema: fromValue :: Value -> Schema
- Argo.Schema.Schema: identified :: Identifier -> Schema -> (Maybe Identifier, Schema)
- Argo.Schema.Schema: newtype Schema
- Argo.Schema.Schema: toValue :: Schema -> Value
+ Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Argo.Class.HasCodec.HasCodec b) => Argo.Class.HasCodec.HasCodec (Data.Either.Either a b)
+ Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Argo.Class.HasCodec.HasCodec b) => Argo.Class.HasCodec.HasCodec (a, b)
+ Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Argo.Class.HasCodec.HasCodec b, Argo.Class.HasCodec.HasCodec c) => Argo.Class.HasCodec.HasCodec (a, b, c)
+ Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Argo.Class.HasCodec.HasCodec b, Argo.Class.HasCodec.HasCodec c, Argo.Class.HasCodec.HasCodec d) => Argo.Class.HasCodec.HasCodec (a, b, c, d)
+ Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Argo.Class.HasCodec.HasCodec b, Argo.Class.HasCodec.HasCodec c, Argo.Class.HasCodec.HasCodec d, Argo.Class.HasCodec.HasCodec e) => Argo.Class.HasCodec.HasCodec (a, b, c, d, e)
+ Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Argo.Class.HasCodec.HasCodec b, Argo.Class.HasCodec.HasCodec c, Argo.Class.HasCodec.HasCodec d, Argo.Class.HasCodec.HasCodec e, Argo.Class.HasCodec.HasCodec f) => Argo.Class.HasCodec.HasCodec (a, b, c, d, e, f)
+ Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Argo.Class.HasCodec.HasCodec b, Argo.Class.HasCodec.HasCodec c, Argo.Class.HasCodec.HasCodec d, Argo.Class.HasCodec.HasCodec e, Argo.Class.HasCodec.HasCodec f, Argo.Class.HasCodec.HasCodec g) => Argo.Class.HasCodec.HasCodec (a, b, c, d, e, f, g)
+ Argo.Class.HasCodec: instance (Argo.Class.HasCodec.HasCodec a, Argo.Class.HasCodec.HasCodec b, Argo.Class.HasCodec.HasCodec c, Argo.Class.HasCodec.HasCodec d, Argo.Class.HasCodec.HasCodec e, Argo.Class.HasCodec.HasCodec f, Argo.Class.HasCodec.HasCodec g, Argo.Class.HasCodec.HasCodec h) => Argo.Class.HasCodec.HasCodec (a, b, c, d, e, f, g, h)
+ Argo.Class.HasCodec: instance Argo.Class.HasCodec.HasCodec Argo.Json.Name.Name
+ Argo.Class.HasCodec: instance Argo.Class.HasCodec.HasCodec Argo.Schema.Identifier.Identifier
+ Argo.Class.HasCodec: instance Argo.Class.HasCodec.HasCodec a => Argo.Class.HasCodec.HasCodec (Argo.Json.Array.Array a)
+ Argo.Class.HasCodec: instance Argo.Class.HasCodec.HasCodec a => Argo.Class.HasCodec.HasCodec (Argo.Json.Object.Object a)
+ Argo.Class.HasCodec: instance Argo.Class.HasCodec.HasCodec a => Argo.Class.HasCodec.HasCodec (Argo.Type.Nullable.Nullable a)
+ Argo.Class.HasCodec: instance Argo.Class.HasCodec.HasCodec a => Argo.Class.HasCodec.HasCodec (Data.Map.Internal.Map Argo.Json.Name.Name a)
+ Argo.Class.HasCodec: instance Argo.Class.HasCodec.HasCodec a => Argo.Class.HasCodec.HasCodec (Data.Map.Internal.Map Argo.Json.String.String a)
+ Argo.Class.HasCodec: instance Argo.Class.HasCodec.HasCodec a => Argo.Class.HasCodec.HasCodec (Data.Map.Internal.Map Argo.Vendor.Text.LazyText a)
+ Argo.Class.HasCodec: instance Argo.Class.HasCodec.HasCodec a => Argo.Class.HasCodec.HasCodec (Data.Map.Internal.Map Data.Text.Internal.Text a)
+ Argo.Class.HasCodec: instance Argo.Class.HasCodec.HasCodec a => Argo.Class.HasCodec.HasCodec (Data.Map.Internal.Map GHC.Base.String a)
+ Argo.Class.HasCodec: instance Argo.Class.HasCodec.HasCodec a => Argo.Class.HasCodec.HasCodec (GHC.Base.NonEmpty a)
+ Argo.Class.HasCodec: instance Argo.Class.HasCodec.HasCodec a => Argo.Class.HasCodec.HasCodec (GHC.Maybe.Maybe a)
+ Argo.Class.HasCodec: instance Argo.Class.HasCodec.HasCodec a => Argo.Class.HasCodec.HasCodec [a]
+ Argo.Class.HasCodec: integralCodec :: forall a. (Bits a, Bounded a, Integral a, Typeable a) => Value a
+ Argo.Class.HasCodec: name :: String -> Name
+ Argo.Class.HasCodec: nullable :: Typeable a => Value a -> Value (Nullable a)
+ Argo.Class.HasCodec: optionalNullable :: Typeable a => Name -> Value a -> Object (Maybe a)
+ Argo.Class.HasCodec: valueCodec :: forall a. Typeable a => Schema -> (a -> Value) -> (Value -> Maybe a) -> Value a
+ Argo.Codec.Value: typeName :: Typeable a => Proxy a -> String
+ Argo.Codec.Value: withIdentifier :: Identifier -> Value a -> Value a
+ Argo.Schema.Schema: Array :: Maybe Natural -> Maybe Natural -> Either Schema (NonEmpty Schema) -> Maybe Schema -> Schema
+ Argo.Schema.Schema: Boolean :: Schema
+ Argo.Schema.Schema: Const :: Value -> Schema
+ Argo.Schema.Schema: False :: Schema
+ Argo.Schema.Schema: Integer :: Maybe Integer -> Maybe Integer -> Schema
+ Argo.Schema.Schema: Null :: Schema
+ Argo.Schema.Schema: Number :: Schema
+ Argo.Schema.Schema: Object :: [(Name, Schema)] -> [Name] -> Maybe Schema -> Schema
+ Argo.Schema.Schema: OneOf :: [Schema] -> Schema
+ Argo.Schema.Schema: Ref :: Identifier -> Schema
+ Argo.Schema.Schema: String :: Maybe Natural -> Maybe Natural -> Schema
+ Argo.Schema.Schema: True :: Schema
+ Argo.Schema.Schema: data Schema
+ Argo.Schema.Schema: maybeRef :: (Maybe Identifier, Schema) -> Schema
+ Argo.Schema.Schema: member :: String -> a -> Member a
+ Argo.Schema.Schema: withIdentifier :: Identifier -> Schema -> (Maybe Identifier, Schema)
+ Argo.Type.Nullable: Nullable :: Maybe a -> Nullable a
+ Argo.Type.Nullable: fromMaybe :: Maybe a -> Nullable a
+ Argo.Type.Nullable: instance GHC.Classes.Eq a => GHC.Classes.Eq (Argo.Type.Nullable.Nullable a)
+ Argo.Type.Nullable: instance GHC.Show.Show a => GHC.Show.Show (Argo.Type.Nullable.Nullable a)
+ Argo.Type.Nullable: just :: a -> Nullable a
+ Argo.Type.Nullable: newtype Nullable a
+ Argo.Type.Nullable: nothing :: Nullable a
+ Argo.Type.Nullable: toMaybe :: Nullable a -> Maybe a
+ Argo.Type.Optional: Optional :: Maybe a -> Optional a
+ Argo.Type.Optional: fromMaybe :: Maybe a -> Optional a
+ Argo.Type.Optional: instance GHC.Classes.Eq a => GHC.Classes.Eq (Argo.Type.Optional.Optional a)
+ Argo.Type.Optional: instance GHC.Show.Show a => GHC.Show.Show (Argo.Type.Optional.Optional a)
+ Argo.Type.Optional: just :: a -> Optional a
+ Argo.Type.Optional: newtype Optional a
+ Argo.Type.Optional: nothing :: Optional a
+ Argo.Type.Optional: toMaybe :: Optional a -> Maybe a
+ Argo.Type.Permission: instance Control.DeepSeq.NFData Argo.Type.Permission.Permission
+ Argo.Type.Permission: instance GHC.Generics.Generic Argo.Type.Permission.Permission
+ Argo.Type.Permission: instance Language.Haskell.TH.Syntax.Lift Argo.Type.Permission.Permission
+ Argo.Type.Permission: toBool :: Permission -> Bool
- Argo: class HasCodec a
+ Argo: class Typeable a => HasCodec a
- Argo.Class.HasCodec: class HasCodec a
+ Argo.Class.HasCodec: class Typeable a => HasCodec a
- Argo.Codec.Object: optional :: Name -> Value a -> Object (Maybe a)
+ Argo.Codec.Object: optional :: Name -> Value a -> Object (Optional a)
- Argo.Codec.Value: getRef :: Value a -> AccumT (Map Identifier Schema) Identity (Either Schema Identifier)
+ Argo.Codec.Value: getRef :: Value a -> AccumT (Map Identifier Schema) Identity Schema

Files

argo.cabal view
@@ -1,7 +1,7 @@ cabal-version: 2.2  name: argo-version: 0.2022.2.2+version: 0.2022.2.23  build-type: Simple category: JSON@@ -98,6 +98,8 @@         Argo.Type.Encoder         Argo.Type.Flag         Argo.Type.Indent+        Argo.Type.Nullable+        Argo.Type.Optional         Argo.Type.Permission         Argo.Type.Settings     hs-source-dirs: source/library
source/library/Argo.hs view
@@ -16,7 +16,6 @@     , HasCodec.HasCodec(codec)     , QuasiQuoter.value     , QuasiQuoter.pointer-    , QuasiQuoter.schema     , Pointer.Pointer(Pointer)     , Token.Token(Token)     , Pointer.evaluate
source/library/Argo/Class/HasCodec.hs view
@@ -19,11 +19,14 @@ import qualified Argo.Json.String as String import qualified Argo.Json.Value as Value import qualified Argo.Pointer.Pointer as Pointer+import qualified Argo.Schema.Identifier as Identifier import qualified Argo.Schema.Schema as Schema import qualified Argo.Type.Config as Config import qualified Argo.Type.Decimal as Decimal import qualified Argo.Type.Decoder as Decoder import qualified Argo.Type.Encoder as Encoder+import qualified Argo.Type.Nullable as Nullable+import qualified Argo.Type.Optional as Optional import qualified Argo.Type.Permission as Permission import qualified Argo.Vendor.Builder as Builder import qualified Argo.Vendor.ByteString as ByteString@@ -34,73 +37,50 @@ import qualified Data.Functor.Identity as Identity import qualified Data.Int as Int import qualified Data.List.NonEmpty as NonEmpty+import qualified Data.Maybe as Maybe import qualified Data.Typeable as Typeable import qualified Data.Word as Word import qualified Numeric.Natural as Natural -class HasCodec a where+class Typeable.Typeable a => HasCodec a where     codec :: Codec.Value a  instance HasCodec Value.Value where-    codec = basicCodec Schema.true id Just+    codec = valueCodec Schema.true id Just  instance HasCodec Null.Null where     codec =-        let-            schema = Schema.fromValue . Value.Object $ Object.fromList-                [ Member.fromTuple-                      ( Name.fromString . String.fromText $ Text.pack "type"-                      , Value.String . String.fromText $ Text.pack "null"-                      )-                ]+        let schema = Schema.Null         in-            basicCodec schema Value.Null $ \value -> case value of+            valueCodec schema Value.Null $ \value -> case value of                 Value.Null null_ -> Just null_                 _ -> Nothing  instance HasCodec Boolean.Boolean where     codec =-        let-            schema = Schema.fromValue . Value.Object $ Object.fromList-                [ Member.fromTuple-                      ( Name.fromString . String.fromText $ Text.pack "type"-                      , Value.String . String.fromText $ Text.pack "boolean"-                      )-                ]+        let schema = Schema.Boolean         in-            basicCodec schema Value.Boolean $ \value -> case value of+            valueCodec schema Value.Boolean $ \value -> case value of                 Value.Boolean boolean -> Just boolean                 _ -> Nothing  instance HasCodec Number.Number where     codec =-        let-            schema = Schema.fromValue . Value.Object $ Object.fromList-                [ Member.fromTuple-                      ( Name.fromString . String.fromText $ Text.pack "type"-                      , Value.String . String.fromText $ Text.pack "number"-                      )-                ]+        let schema = Schema.Number         in-            basicCodec schema Value.Number $ \value -> case value of+            valueCodec schema Value.Number $ \value -> case value of                 Value.Number number -> Just number                 _ -> Nothing  instance HasCodec String.String where     codec =-        let-            schema = Schema.fromValue . Value.Object $ Object.fromList-                [ Member.fromTuple-                      ( Name.fromString . String.fromText $ Text.pack "type"-                      , Value.String . String.fromText $ Text.pack "string"-                      )-                ]+        let schema = Schema.String Nothing Nothing         in-            basicCodec schema Value.String $ \value -> case value of+            valueCodec schema Value.String $ \value -> case value of                 Value.String string -> Just string                 _ -> Nothing -instance (HasCodec a, Typeable.Typeable a) => HasCodec (Array.Array a) where+instance HasCodec a => HasCodec (Array.Array a) where     codec = Codec.identified Codec.Codec         { Codec.decode = do             array <- castValue "Array" $ \value -> case value of@@ -119,25 +99,14 @@             . Array.toList         , Codec.schema = do             ref <- Codec.getRef (codec :: Codec.Value a)-            pure-                . Schema.unidentified-                . Schema.fromValue-                . Value.Object-                $ Object.fromList-                      [ Member.fromTuple-                          ( Name.fromString . String.fromText $ Text.pack-                              "type"-                          , Value.String . String.fromText $ Text.pack "array"-                          )-                      , Member.fromTuple-                          ( Name.fromString . String.fromText $ Text.pack-                              "items"-                          , Codec.ref ref-                          )-                      ]+            pure . Schema.unidentified $ Schema.Array+                Nothing+                Nothing+                (Left ref)+                Nothing         } -instance (HasCodec a, Typeable.Typeable a) => HasCodec (Object.Object a) where+instance HasCodec a => HasCodec (Object.Object a) where     codec = Codec.identified Codec.Codec         { Codec.decode = do             object <- castValue "Object" $ \value -> case value of@@ -162,35 +131,19 @@             . Object.toList         , Codec.schema = do             ref <- Codec.getRef (codec :: Codec.Value a)-            pure-                . Schema.unidentified-                . Schema.fromValue-                . Value.Object-                $ Object.fromList-                      [ Member.fromTuple-                          ( Name.fromString . String.fromText $ Text.pack-                              "type"-                          , Value.String . String.fromText $ Text.pack "object"-                          )-                      , Member.fromTuple-                          ( Name.fromString . String.fromText $ Text.pack-                              "additionalProperties"-                          , Codec.ref ref-                          )-                      ]+            pure . Schema.unidentified . Schema.Object [] [] $ Just ref         } -instance (HasCodec a, Typeable.Typeable a) => HasCodec (Maybe a) where+instance HasCodec a => HasCodec (Nullable.Nullable a) where+    codec = nullable codec++instance HasCodec a => HasCodec (Maybe a) where     codec =-        Codec.identified-            $ Codec.mapMaybe (Just . Just) id codec-            <|> Codec.map (const Nothing) (const $ Null.fromUnit ()) codec+        Codec.identified $ Codec.map Nullable.toMaybe Nullable.fromMaybe codec  instance     ( HasCodec a     , HasCodec b-    , Typeable.Typeable a-    , Typeable.Typeable b     ) => HasCodec (Either a b) where     codec =         Codec.identified@@ -210,8 +163,6 @@ instance     ( HasCodec a     , HasCodec b-    , Typeable.Typeable a-    , Typeable.Typeable b     ) => HasCodec (a, b) where     codec =         Codec.identified@@ -224,9 +175,6 @@     ( HasCodec a     , HasCodec b     , HasCodec c-    , Typeable.Typeable a-    , Typeable.Typeable b-    , Typeable.Typeable c     ) => HasCodec (a, b, c) where     codec =         Codec.identified@@ -241,10 +189,6 @@     , HasCodec b     , HasCodec c     , HasCodec d-    , Typeable.Typeable a-    , Typeable.Typeable b-    , Typeable.Typeable c-    , Typeable.Typeable d     ) => HasCodec (a, b, c, d) where     codec =         Codec.identified@@ -261,11 +205,6 @@     , HasCodec c     , HasCodec d     , HasCodec e-    , Typeable.Typeable a-    , Typeable.Typeable b-    , Typeable.Typeable c-    , Typeable.Typeable d-    , Typeable.Typeable e     ) => HasCodec (a, b, c, d, e) where     codec =         Codec.identified@@ -284,12 +223,6 @@     , HasCodec d     , HasCodec e     , HasCodec f-    , Typeable.Typeable a-    , Typeable.Typeable b-    , Typeable.Typeable c-    , Typeable.Typeable d-    , Typeable.Typeable e-    , Typeable.Typeable f     ) => HasCodec (a, b, c, d, e, f) where     codec =         Codec.identified@@ -310,13 +243,6 @@     , HasCodec e     , HasCodec f     , HasCodec g-    , Typeable.Typeable a-    , Typeable.Typeable b-    , Typeable.Typeable c-    , Typeable.Typeable d-    , Typeable.Typeable e-    , Typeable.Typeable f-    , Typeable.Typeable g     ) => HasCodec (a, b, c, d, e, f, g) where     codec =         Codec.identified@@ -353,14 +279,6 @@     , HasCodec f     , HasCodec g     , HasCodec h-    , Typeable.Typeable a-    , Typeable.Typeable b-    , Typeable.Typeable c-    , Typeable.Typeable d-    , Typeable.Typeable e-    , Typeable.Typeable f-    , Typeable.Typeable g-    , Typeable.Typeable h     ) => HasCodec (a, b, c, d, e, f, g, h) where     codec =         Codec.identified@@ -401,34 +319,34 @@ instance HasCodec Text.Text where     codec = Codec.identified $ Codec.map String.toText String.fromText codec -instance {-# OVERLAPPABLE #-} (HasCodec a, Typeable.Typeable a) => HasCodec [a] where+instance {-# OVERLAPPABLE #-} HasCodec a => HasCodec [a] where     codec = Codec.identified $ Codec.map Array.toList Array.fromList codec -instance (HasCodec a, Typeable.Typeable a) => HasCodec (Map.Map Name.Name a) where+instance HasCodec a => HasCodec (Map.Map Name.Name a) where     codec = Codec.identified $ Codec.map         (Map.fromList . fmap Member.toTuple . Object.toList)         (Object.fromList . fmap Member.fromTuple . Map.toList)         codec -instance (HasCodec a, Typeable.Typeable a) => HasCodec (Map.Map String.String a) where+instance HasCodec a => HasCodec (Map.Map String.String a) where     codec = Codec.identified $ Codec.map         (Map.mapKeys Name.toString)         (Map.mapKeys Name.fromString)         codec -instance (HasCodec a, Typeable.Typeable a) => HasCodec (Map.Map Text.Text a) where+instance HasCodec a => HasCodec (Map.Map Text.Text a) where     codec = Codec.identified $ Codec.map         (Map.mapKeys String.toText)         (Map.mapKeys String.fromText)         codec -instance (HasCodec a, Typeable.Typeable a) => HasCodec (Map.Map Text.LazyText a) where+instance HasCodec a => HasCodec (Map.Map Text.LazyText a) where     codec = Codec.identified $ Codec.map         (Map.mapKeys Text.fromStrict)         (Map.mapKeys Text.toStrict)         codec -instance (HasCodec a, Typeable.Typeable a) => HasCodec (Map.Map String a) where+instance HasCodec a => HasCodec (Map.Map String a) where     codec = Codec.identified         $ Codec.map (Map.mapKeys Text.unpack) (Map.mapKeys Text.pack) codec @@ -437,33 +355,7 @@  instance HasCodec Char where     codec =-        let-            schema =-                Schema.unidentified-                    . Schema.fromValue-                    . Value.Object-                    $ Object.fromList-                          [ Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "type"-                              , Value.String . String.fromText $ Text.pack-                                  "string"-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "minLength"-                              , Value.Number-                              . Number.fromDecimal-                              $ Decimal.fromInteger 1-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "maxLength"-                              , Value.Number-                              . Number.fromDecimal-                              $ Decimal.fromInteger 1-                              )-                          ]+        let schema = Schema.unidentified $ Schema.String (Just 1) (Just 1)         in             Codec.identified $ Codec.mapMaybe                 (\x -> case Text.uncons x of@@ -476,35 +368,16 @@ instance HasCodec Text.LazyText where     codec = Codec.identified $ Codec.map Text.fromStrict Text.toStrict codec -instance (HasCodec a, Typeable.Typeable a) => HasCodec (NonEmpty.NonEmpty a) where+instance HasCodec a => HasCodec (NonEmpty.NonEmpty a) where     codec =         let             schema = do-                (_, itemSchema) <- Codec.schema (codec :: Codec.Value a)-                pure-                    . Schema.unidentified-                    . Schema.fromValue-                    . Value.Object-                    $ Object.fromList-                          [ Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "type"-                              , Value.String . String.fromText $ Text.pack-                                  "array"-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "items"-                              , Schema.toValue itemSchema-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "minItems"-                              , Value.Number-                              . Number.fromDecimal-                              $ Decimal.fromInteger 1-                              )-                          ]+                itemSchema <- Codec.schema (codec :: Codec.Value a)+                pure . Schema.unidentified $ Schema.Array+                    (Just 1)+                    Nothing+                    (Left $ Schema.maybeRef itemSchema)+                    Nothing         in             Codec.identified $ Codec.mapMaybe                 NonEmpty.nonEmpty@@ -513,19 +386,7 @@  instance HasCodec Integer where     codec =-        let-            schema =-                Schema.unidentified-                    . Schema.fromValue-                    . Value.Object-                    $ Object.fromList-                          [ Member.fromTuple-                                ( Name.fromString . String.fromText $ Text.pack-                                    "type"-                                , Value.String . String.fromText $ Text.pack-                                    "integer"-                                )-                          ]+        let schema = Schema.unidentified $ Schema.Integer Nothing Nothing         in             Codec.identified $ Codec.mapMaybe                 Decimal.toInteger@@ -533,413 +394,45 @@                 codec { Codec.schema = pure schema }  instance HasCodec Int where-    codec =-        let-            from = Bits.toIntegralSized :: Integer -> Maybe Int-            into = fromIntegral :: Int -> Integer-            schema =-                Schema.unidentified-                    . Schema.fromValue-                    . Value.Object-                    $ Object.fromList-                          [ Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "type"-                              , Value.String . String.fromText $ Text.pack-                                  "integer"-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "minimum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (minBound :: Int)-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "maximum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (maxBound :: Int)-                              )-                          ]-        in Codec.identified $ Codec.mapMaybe-            from-            (Just . into)-            codec { Codec.schema = pure schema }+    codec = integralCodec  instance HasCodec Int.Int8 where-    codec =-        let-            from = Bits.toIntegralSized :: Integer -> Maybe Int.Int8-            into = fromIntegral :: Int.Int8 -> Integer-            schema =-                Schema.unidentified-                    . Schema.fromValue-                    . Value.Object-                    $ Object.fromList-                          [ Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "type"-                              , Value.String . String.fromText $ Text.pack-                                  "integer"-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "minimum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (minBound :: Int.Int8)-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "maximum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (maxBound :: Int.Int8)-                              )-                          ]-        in Codec.identified $ Codec.mapMaybe-            from-            (Just . into)-            codec { Codec.schema = pure schema }+    codec = integralCodec  instance HasCodec Int.Int16 where-    codec =-        let-            from = Bits.toIntegralSized :: Integer -> Maybe Int.Int16-            into = fromIntegral :: Int.Int16 -> Integer-            schema =-                Schema.unidentified-                    . Schema.fromValue-                    . Value.Object-                    $ Object.fromList-                          [ Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "type"-                              , Value.String . String.fromText $ Text.pack-                                  "integer"-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "minimum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (minBound :: Int.Int16)-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "maximum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (maxBound :: Int.Int16)-                              )-                          ]-        in Codec.identified $ Codec.mapMaybe-            from-            (Just . into)-            codec { Codec.schema = pure schema }+    codec = integralCodec  instance HasCodec Int.Int32 where-    codec =-        let-            from = Bits.toIntegralSized :: Integer -> Maybe Int.Int32-            into = fromIntegral :: Int.Int32 -> Integer-            schema =-                Schema.unidentified-                    . Schema.fromValue-                    . Value.Object-                    $ Object.fromList-                          [ Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "type"-                              , Value.String . String.fromText $ Text.pack-                                  "integer"-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "minimum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (minBound :: Int.Int32)-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "maximum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (maxBound :: Int.Int32)-                              )-                          ]-        in Codec.identified $ Codec.mapMaybe-            from-            (Just . into)-            codec { Codec.schema = pure schema }+    codec = integralCodec  instance HasCodec Int.Int64 where-    codec =-        let-            from = Bits.toIntegralSized :: Integer -> Maybe Int.Int64-            into = fromIntegral :: Int.Int64 -> Integer-            schema =-                Schema.unidentified-                    . Schema.fromValue-                    . Value.Object-                    $ Object.fromList-                          [ Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "type"-                              , Value.String . String.fromText $ Text.pack-                                  "integer"-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "minimum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (minBound :: Int.Int64)-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "maximum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (maxBound :: Int.Int64)-                              )-                          ]-        in Codec.identified $ Codec.mapMaybe-            from-            (Just . into)-            codec { Codec.schema = pure schema }+    codec = integralCodec  instance HasCodec Natural.Natural where     codec =         let             from = Bits.toIntegralSized :: Integer -> Maybe Natural.Natural             into = fromIntegral :: Natural.Natural -> Integer-            schema =-                Schema.unidentified-                    . Schema.fromValue-                    . Value.Object-                    $ Object.fromList-                          [ Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "type"-                              , Value.String . String.fromText $ Text.pack-                                  "integer"-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "minimum"-                              , Value.Number-                              . Number.fromDecimal-                              $ Decimal.fromInteger 0-                              )-                          ]+            schema = Schema.unidentified $ Schema.Integer (Just 0) Nothing         in Codec.identified $ Codec.mapMaybe             from             (Just . into)             codec { Codec.schema = pure schema }  instance HasCodec Word where-    codec =-        let-            from = Bits.toIntegralSized :: Integer -> Maybe Word-            into = fromIntegral :: Word -> Integer-            schema =-                Schema.unidentified-                    . Schema.fromValue-                    . Value.Object-                    $ Object.fromList-                          [ Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "type"-                              , Value.String . String.fromText $ Text.pack-                                  "integer"-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "minimum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (minBound :: Word)-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "maximum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (maxBound :: Word)-                              )-                          ]-        in Codec.identified $ Codec.mapMaybe-            from-            (Just . into)-            codec { Codec.schema = pure schema }+    codec = integralCodec  instance HasCodec Word.Word8 where-    codec =-        let-            from = Bits.toIntegralSized :: Integer -> Maybe Word.Word8-            into = fromIntegral :: Word.Word8 -> Integer-            schema =-                Schema.unidentified-                    . Schema.fromValue-                    . Value.Object-                    $ Object.fromList-                          [ Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "type"-                              , Value.String . String.fromText $ Text.pack-                                  "integer"-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "minimum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (minBound :: Word.Word8)-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "maximum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (maxBound :: Word.Word8)-                              )-                          ]-        in Codec.identified $ Codec.mapMaybe-            from-            (Just . into)-            codec { Codec.schema = pure schema }+    codec = integralCodec  instance HasCodec Word.Word16 where-    codec =-        let-            from = Bits.toIntegralSized :: Integer -> Maybe Word.Word16-            into = fromIntegral :: Word.Word16 -> Integer-            schema =-                Schema.unidentified-                    . Schema.fromValue-                    . Value.Object-                    $ Object.fromList-                          [ Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "type"-                              , Value.String . String.fromText $ Text.pack-                                  "integer"-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "minimum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (minBound :: Word.Word16)-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "maximum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (maxBound :: Word.Word16)-                              )-                          ]-        in Codec.identified $ Codec.mapMaybe-            from-            (Just . into)-            codec { Codec.schema = pure schema }+    codec = integralCodec  instance HasCodec Word.Word32 where-    codec =-        let-            from = Bits.toIntegralSized :: Integer -> Maybe Word.Word32-            into = fromIntegral :: Word.Word32 -> Integer-            schema =-                Schema.unidentified-                    . Schema.fromValue-                    . Value.Object-                    $ Object.fromList-                          [ Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "type"-                              , Value.String . String.fromText $ Text.pack-                                  "integer"-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "minimum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (minBound :: Word.Word32)-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "maximum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (maxBound :: Word.Word32)-                              )-                          ]-        in Codec.identified $ Codec.mapMaybe-            from-            (Just . into)-            codec { Codec.schema = pure schema }+    codec = integralCodec  instance HasCodec Word.Word64 where-    codec =-        let-            from = Bits.toIntegralSized :: Integer -> Maybe Word.Word64-            into = fromIntegral :: Word.Word64 -> Integer-            schema =-                Schema.unidentified-                    . Schema.fromValue-                    . Value.Object-                    $ Object.fromList-                          [ Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "type"-                              , Value.String . String.fromText $ Text.pack-                                  "integer"-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "minimum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (minBound :: Word.Word64)-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "maximum"-                              , Value.Number-                              . Number.fromDecimal-                              . Decimal.fromInteger-                              $ toInteger (maxBound :: Word.Word64)-                              )-                          ]-        in Codec.identified $ Codec.mapMaybe-            from-            (Just . into)-            codec { Codec.schema = pure schema }+    codec = integralCodec  instance HasCodec Float where     codec = Codec.identified $ Codec.mapMaybe@@ -968,19 +461,295 @@         )         codec +instance HasCodec Identifier.Identifier where+    codec =+        let prefix = Text.pack "#/definitions/"+        in+            Codec.identified $ Codec.mapMaybe+                (fmap Identifier.fromText . Text.stripPrefix prefix)+                (Just . mappend prefix . Identifier.toText)+                codec++instance HasCodec Name.Name where+    codec = Codec.identified $ Codec.map Name.fromString Name.toString codec+ instance HasCodec Schema.Schema where-    codec = Codec.identified $ Codec.map Schema.fromValue Schema.toValue codec+    codec =+        let+            trueCodec =+                Codec.mapMaybe+                        (const $ Just Schema.True)+                        (\x -> case x of+                            Schema.True -> Just ()+                            _ -> Nothing+                        )+                    . Codec.literalCodec+                    . Value.Boolean+                    $ Boolean.fromBool True+            falseCodec =+                Codec.mapMaybe+                        (const $ Just Schema.False)+                        (\x -> case x of+                            Schema.False -> Just ()+                            _ -> Nothing+                        )+                    . Codec.literalCodec+                    . Value.Boolean+                    $ Boolean.fromBool False+            constCodec =+                Codec.mapMaybe+                        (Just . Schema.Const)+                        (\x -> case x of+                            Schema.Const y -> Just y+                            _ -> Nothing+                        )+                    . Codec.fromObjectCodec Permission.Forbid+                    $ Codec.required (name "const") codec+            nullCodec =+                Codec.mapMaybe+                        (const $ Just Schema.Null)+                        (\x -> case x of+                            Schema.Null -> Just ()+                            _ -> Nothing+                        )+                    . Codec.fromObjectCodec Permission.Forbid+                    . Codec.required (name "type")+                    . Codec.literalCodec+                    . Value.String+                    . String.fromText+                    $ Text.pack "null"+            booleanCodec =+                Codec.mapMaybe+                        (const $ Just Schema.Boolean)+                        (\x -> case x of+                            Schema.Boolean -> Just ()+                            _ -> Nothing+                        )+                    . Codec.fromObjectCodec Permission.Forbid+                    . Codec.required (name "type")+                    . Codec.literalCodec+                    . Value.String+                    . String.fromText+                    $ Text.pack "boolean"+            numberCodec =+                Codec.mapMaybe+                        (const $ Just Schema.Number)+                        (\x -> case x of+                            Schema.Number -> Just ()+                            _ -> Nothing+                        )+                    . Codec.fromObjectCodec Permission.Forbid+                    . Codec.required (name "type")+                    . Codec.literalCodec+                    . Value.String+                    . String.fromText+                    $ Text.pack "number"+            integerCodec =+                Codec.mapMaybe+                        (\(_, y, z) -> Just $ Schema.Integer+                            (Optional.toMaybe y)+                            (Optional.toMaybe z)+                        )+                        (\x -> case x of+                            Schema.Integer y z ->+                                Just+                                    ( ()+                                    , Optional.fromMaybe y+                                    , Optional.fromMaybe z+                                    )+                            _ -> Nothing+                        )+                    . Codec.fromObjectCodec Permission.Forbid+                    $ (,,)+                    <$> Codec.project+                            (\(a, _, _) -> a)+                            (Codec.required (name "type")+                            . Codec.literalCodec+                            . Value.String+                            . String.fromText+                            $ Text.pack "integer"+                            )+                    <*> Codec.project+                            (\(_, b, _) -> b)+                            (Codec.optional (name "minimum") codec)+                    <*> Codec.project+                            (\(_, _, c) -> c)+                            (Codec.optional (name "maximum") codec)+            stringCodec =+                Codec.mapMaybe+                        (\(_, y, z) -> Just $ Schema.String+                            (Optional.toMaybe y)+                            (Optional.toMaybe z)+                        )+                        (\x -> case x of+                            Schema.String y z ->+                                Just+                                    ( ()+                                    , Optional.fromMaybe y+                                    , Optional.fromMaybe z+                                    )+                            _ -> Nothing+                        )+                    . Codec.fromObjectCodec Permission.Forbid+                    $ (,,)+                    <$> Codec.project+                            (\(a, _, _) -> a)+                            (Codec.required (name "type")+                            . Codec.literalCodec+                            . Value.String+                            . String.fromText+                            $ Text.pack "string"+                            )+                    <*> Codec.project+                            (\(_, b, _) -> b)+                            (Codec.optional (name "minLength") codec)+                    <*> Codec.project+                            (\(_, _, c) -> c)+                            (Codec.optional (name "maxLength") codec)+            arrayCodec =+                Codec.mapMaybe+                        (\(_, lo, hi, e, m) -> Just $ Schema.Array+                            (Optional.toMaybe lo)+                            (Optional.toMaybe hi)+                            e+                            (Optional.toMaybe m)+                        )+                        (\x -> case x of+                            Schema.Array lo hi e m -> Just+                                ( ()+                                , Optional.fromMaybe lo+                                , Optional.fromMaybe hi+                                , e+                                , Optional.fromMaybe m+                                )+                            _ -> Nothing+                        )+                    . Codec.fromObjectCodec Permission.Forbid+                    $ (,,,,)+                    <$> Codec.project+                            (\(a, _, _, _, _) -> a)+                            (Codec.required (name "type")+                            . Codec.literalCodec+                            . Value.String+                            . String.fromText+                            $ Text.pack "array"+                            )+                    <*> Codec.project+                            (\(_, b, _, _, _) -> b)+                            (Codec.optional (name "minItems") codec)+                    <*> Codec.project+                            (\(_, _, c, _, _) -> c)+                            (Codec.optional (name "maxItems") codec)+                    <*> Codec.project+                            (\(_, _, _, d, _) -> d)+                            (Codec.required (name "items")+                            . Codec.withIdentifier+                                  (Identifier.fromText+                                  $ Text.pack "OneOf Schema [Schema]"+                                  )+                            $ Codec.mapMaybe+                                  (Just . Left)+                                  (either Just $ const Nothing)+                                  codec+                            <|> Codec.mapMaybe+                                    (Just . Right)+                                    (either (const Nothing) Just)+                                    codec+                            )+                    <*> Codec.project+                            (\(_, _, _, _, e) -> e)+                            (Codec.optional (name "additionalItems") codec)+            objectCodec =+                Codec.mapMaybe+                        (\(_, ps, rs, m) -> Just $ Schema.Object+                            (fmap Member.toTuple+                            . foldMap Object.toList+                            $ Optional.toMaybe ps+                            )+                            (Maybe.fromMaybe [] $ Optional.toMaybe rs)+                            (Optional.toMaybe m)+                        )+                        (\x -> case x of+                            Schema.Object ps rs m -> Just+                                ( ()+                                , if null ps+                                    then Optional.nothing+                                    else Optional.just . Object.fromList $ fmap+                                        Member.fromTuple+                                        ps+                                , if null rs+                                    then Optional.nothing+                                    else Optional.just rs+                                , Optional.fromMaybe m+                                )+                            _ -> Nothing+                        )+                    . Codec.fromObjectCodec Permission.Forbid+                    $ (,,,)+                    <$> Codec.project+                            (\(a, _, _, _) -> a)+                            (Codec.required (name "type")+                            . Codec.literalCodec+                            . Value.String+                            . String.fromText+                            $ Text.pack "object"+                            )+                    <*> Codec.project+                            (\(_, b, _, _) -> b)+                            (Codec.optional (name "properties") codec)+                    <*> Codec.project+                            (\(_, _, c, _) -> c)+                            (Codec.optional (name "required") codec)+                    <*> Codec.project+                            (\(_, _, _, d) -> d)+                            (Codec.optional (name "additionalProperties") codec+                            )+            refCodec =+                Codec.mapMaybe+                        (Just . Schema.Ref)+                        (\x -> case x of+                            Schema.Ref y -> Just y+                            _ -> Nothing+                        )+                    . Codec.fromObjectCodec Permission.Forbid+                    $ Codec.required (name "$ref") codec+            oneOfCodec =+                Codec.mapMaybe+                        (Just . Schema.OneOf)+                        (\x -> case x of+                            Schema.OneOf y -> Just y+                            _ -> Nothing+                        )+                    . Codec.fromObjectCodec Permission.Forbid+                    $ Codec.required (name "oneOf") codec+        in+            Codec.identified+            $ trueCodec+            <|> falseCodec+            <|> constCodec+            <|> nullCodec+            <|> booleanCodec+            <|> numberCodec+            <|> integerCodec+            <|> stringCodec+            <|> arrayCodec+            <|> objectCodec+            <|> refCodec+            <|> oneOfCodec -basicCodec+name :: String -> Name.Name+name = Name.fromString . String.fromText . Text.pack++valueCodec     :: forall a      . Typeable.Typeable a     => Schema.Schema     -> (a -> Value.Value)     -> (Value.Value -> Maybe a)     -> Codec.Value a-basicCodec schema toValue fromValue = Codec.identified Codec.Codec+valueCodec schema toValue fromValue = Codec.identified Codec.Codec     { Codec.decode = castValue-        (show $ Typeable.typeRep (Typeable.Proxy :: Typeable.Proxy a))+        (Codec.typeName (Typeable.Proxy :: Typeable.Proxy a))         fromValue     , Codec.encode = Codec.tap $ Trans.lift . Trans.put . toValue     , Codec.schema = pure $ Schema.unidentified schema@@ -1010,3 +779,40 @@             Value.Array _ -> "Array"             Value.Object _ -> "Object"     in "expected " <> expected <> " but got " <> actual++integralCodec+    :: forall a+     . (Bits.Bits a, Bounded a, Integral a, Typeable.Typeable a)+    => Codec.Value a+integralCodec =+    let+        from = Bits.toIntegralSized :: Integer -> Maybe a+        into = fromIntegral :: a -> Integer+        schema = Schema.unidentified $ Schema.Integer+            (Just $ toInteger (minBound :: a))+            (Just $ toInteger (maxBound :: a))+    in Codec.identified $ Codec.mapMaybe+        from+        (Just . into)+        codec { Codec.schema = pure schema }++optionalNullable+    :: Typeable.Typeable a+    => Name.Name+    -> Codec.Value a+    -> Codec.Object (Maybe a)+optionalNullable k =+    Codec.map+            (maybe Nothing Nullable.toMaybe . Optional.toMaybe)+            (Optional.fromMaybe . fmap Nullable.just)+        . Codec.optional k+        . nullable++nullable+    :: Typeable.Typeable a+    => Codec.Value a+    -> Codec.Value (Nullable.Nullable a)+nullable c =+    Codec.identified+        $ Codec.mapMaybe (Just . Nullable.just) Nullable.toMaybe c+        <|> Codec.map (const Nullable.nothing) (const $ Null.fromUnit ()) codec
source/library/Argo/Codec/Array.hs view
@@ -4,19 +4,14 @@ import qualified Argo.Codec.List as Codec import qualified Argo.Codec.Value as Codec import qualified Argo.Json.Array as Array-import qualified Argo.Json.Boolean as Boolean-import qualified Argo.Json.Member as Member-import qualified Argo.Json.Name as Name-import qualified Argo.Json.Object as Object-import qualified Argo.Json.String as String import qualified Argo.Json.Value as Value import qualified Argo.Schema.Identifier as Identifier import qualified Argo.Schema.Schema as Schema import qualified Argo.Type.Permission as Permission import qualified Argo.Vendor.Map as Map-import qualified Argo.Vendor.Text as Text import qualified Argo.Vendor.Transformers as Trans import qualified Data.Functor.Identity as Identity+import qualified Data.List.NonEmpty as NonEmpty  type Array a     = Codec.List@@ -33,34 +28,18 @@     Codec.fromListCodec             (\permission schemasM -> do                 schemas <- schemasM-                pure-                    . Schema.unidentified-                    . Schema.fromValue-                    . Value.Object-                    $ Object.fromList-                          [ Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "type"-                              , Value.String . String.fromText $ Text.pack-                                  "array"-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "items"-                              , Value.Array . Array.fromList $ fmap-                                  (Schema.toValue . snd)-                                  schemas-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "additionalItems"-                              , Value.Boolean-                              . Boolean.fromBool-                              $ case permission of-                                    Permission.Allow -> True-                                    Permission.Forbid -> False-                              )-                          ]+                pure . Schema.unidentified $ Schema.Array+                    (Just . fromIntegral $ length schemas)+                    (case permission of+                        Permission.Allow -> Nothing+                        Permission.Forbid ->+                            Just . fromIntegral $ length schemas+                    )+                    (case NonEmpty.nonEmpty $ fmap Schema.maybeRef schemas of+                        Nothing -> Left Schema.False+                        Just xs -> Right xs+                    )+                    Nothing             )         $ Codec.map Array.toList Array.fromList Codec.arrayCodec @@ -78,10 +57,5 @@     , Codec.encode = \x -> do         Trans.tell [Codec.encodeWith c x]         pure x-    , Codec.schema =-        pure-        . Schema.unidentified-        . Schema.fromValue-        . Codec.ref-        <$> Codec.getRef c+    , Codec.schema = pure . Schema.unidentified <$> Codec.getRef c     }
source/library/Argo/Codec/Object.hs view
@@ -3,16 +3,14 @@ import qualified Argo.Codec.Codec as Codec import qualified Argo.Codec.List as Codec import qualified Argo.Codec.Value as Codec-import qualified Argo.Json.Array as Array-import qualified Argo.Json.Boolean as Boolean import qualified Argo.Json.Member as Member import qualified Argo.Json.Name as Name-import qualified Argo.Json.Null as Null import qualified Argo.Json.Object as Object import qualified Argo.Json.String as String import qualified Argo.Json.Value as Value import qualified Argo.Schema.Identifier as Identifier import qualified Argo.Schema.Schema as Schema+import qualified Argo.Type.Optional as Optional import qualified Argo.Type.Permission as Permission import qualified Argo.Vendor.Map as Map import qualified Argo.Vendor.Text as Text@@ -42,45 +40,18 @@                 schemas <- schemasM                 pure                     . Schema.unidentified-                    . Schema.fromValue-                    . Value.Object-                    $ Object.fromList-                          [ Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "type"-                              , Value.String . String.fromText $ Text.pack-                                  "object"-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "properties"-                              , Value.Object . Object.fromList $ fmap-                                  (\((k, _), (_, s)) ->-                                      Member.fromTuple (k, Schema.toValue s)-                                  )-                                  schemas-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "required"-                              , Value.Array . Array.fromList $ Maybe.mapMaybe-                                  (\((k, r), _) -> if r-                                      then Just . Value.String $ Name.toString-                                          k-                                      else Nothing-                                  )-                                  schemas-                              )-                          , Member.fromTuple-                              ( Name.fromString . String.fromText $ Text.pack-                                  "additionalProperties"-                              , Value.Boolean-                              . Boolean.fromBool-                              $ case permission of-                                    Permission.Allow -> True-                                    Permission.Forbid -> False-                              )-                          ]+                    . Schema.Object+                          (fmap+                              (\((k, _), s) -> (k, Schema.maybeRef s))+                              schemas+                          )+                          (Maybe.mapMaybe+                              (\((k, r), _) -> if r then Just k else Nothing)+                              schemas+                          )+                    $ case permission of+                          Permission.Allow -> Nothing+                          Permission.Forbid -> Just Schema.False             )         $ Codec.map Object.toList Object.fromList Codec.objectCodec @@ -88,7 +59,7 @@ required k c = Codec.Codec     { Codec.decode = do         m <- Codec.decode (optional k c)-        case m of+        case Optional.toMaybe m of             Nothing ->                 Trans.lift                     . Trans.throwE@@ -96,42 +67,30 @@                     <> show k             Just x -> pure x     , Codec.encode = \x -> do-        Monad.void . Codec.encode (optional k c) $ Just x+        Monad.void . Codec.encode (optional k c) $ Optional.just x         pure x     , Codec.schema =-        pure-        . (,) (k, True)-        . Schema.unidentified-        . Schema.fromValue-        . Codec.ref-        <$> Codec.getRef c+        pure . (,) (k, True) . Schema.unidentified <$> Codec.getRef c     } -optional :: Name.Name -> Codec.Value a -> Object (Maybe a)+optional :: Name.Name -> Codec.Value a -> Object (Optional.Optional a) optional k c = Codec.Codec     { Codec.decode = do         xs <- Trans.get         case List.partition (\(Member.Member j _) -> j == k) xs of             (Member.Member _ x : _, ys) -> case Codec.decodeWith c x of-                Left y -> if x == Value.Null (Null.fromUnit ())-                    then pure Nothing-                    else Trans.lift $ Trans.throwE y+                Left y -> Trans.lift $ Trans.throwE y                 Right y -> do                     Trans.put ys-                    pure $ Just y-            _ -> pure Nothing+                    pure $ Optional.just y+            _ -> pure Optional.nothing     , Codec.encode = \x -> do-        case x of+        case Optional.toMaybe x of             Nothing -> pure ()             Just y -> Trans.tell [Member.Member k $ Codec.encodeWith c y]         pure x     , Codec.schema =-        pure-        . (,) (k, False)-        . Schema.unidentified-        . Schema.fromValue-        . Codec.ref-        <$> Codec.getRef c+        pure . (,) (k, False) . Schema.unidentified <$> Codec.getRef c     }  tagged :: String -> Codec.Value a -> Codec.Value a
source/library/Argo/Codec/Value.hs view
@@ -4,11 +4,8 @@  import qualified Argo.Codec.Codec as Codec import qualified Argo.Json.Array as Array-import qualified Argo.Json.Member as Member-import qualified Argo.Json.Name as Name import qualified Argo.Json.Null as Null import qualified Argo.Json.Object as Object-import qualified Argo.Json.String as String import qualified Argo.Json.Value as Value import qualified Argo.Schema.Identifier as Identifier import qualified Argo.Schema.Schema as Schema@@ -86,32 +83,31 @@             <> " but got "             <> show actual     , Codec.encode = const . Trans.lift $ Trans.put expected-    , Codec.schema =-        pure-        . Schema.unidentified-        . Schema.fromValue-        . Value.Object-        $ Object.fromList-              [ Member.fromTuple-                    ( Name.fromString . String.fromText $ Text.pack "const"-                    , expected-                    )-              ]+    , Codec.schema = pure . Schema.unidentified $ Schema.Const expected     }  identified :: forall a . Typeable.Typeable a => Value a -> Value a-identified c =+identified = withIdentifier . Identifier.fromText . Text.pack $ typeName+    (Typeable.Proxy :: Typeable.Proxy a)++withIdentifier :: Identifier.Identifier -> Value a -> Value a+withIdentifier identifier codec =     let-        i = Identifier.fromText . Text.pack . show $ Typeable.typeRep-            (Typeable.Proxy :: Typeable.Proxy a)-    in c { Codec.schema = Schema.identified i . snd <$> Codec.schema c }+        newSchema = do+            (_, schema) <- Codec.schema codec+            Trans.add $ Map.singleton identifier schema+            pure $ Schema.withIdentifier identifier schema+    in codec { Codec.schema = newSchema } +typeName :: Typeable.Typeable a => Typeable.Proxy a -> String+typeName = show . Typeable.typeRep+ getRef     :: Value a     -> Trans.AccumT            (Map.Map Identifier.Identifier Schema.Schema)            Identity.Identity-           (Either Schema.Schema Identifier.Identifier)+           Schema.Schema getRef codec = do     let         (maybeIdentifier, schema) =@@ -119,23 +115,10 @@                 (Codec.schema codec)                 Map.empty     case maybeIdentifier of-        Nothing -> pure $ Left schema+        Nothing -> pure schema         Just identifier -> do             schemas <- Trans.look             Monad.unless (Map.member identifier schemas) $ do                 Trans.add $ Map.singleton identifier schema                 Monad.void $ Codec.schema codec-            pure $ Right identifier--ref :: Either Schema.Schema Identifier.Identifier -> Value.Value-ref e = case e of-    Left s -> Schema.toValue s-    Right i -> Value.Object $ Object.fromList-        [ Member.fromTuple-              ( Name.fromString . String.fromText $ Text.pack "$ref"-              , Value.String-              . String.fromText-              . mappend (Text.pack "#/definitions/")-              $ Identifier.toText i-              )-        ]+            pure $ Schema.Ref identifier
source/library/Argo/QuasiQuoter.hs view
@@ -2,7 +2,6 @@  import qualified Argo.Decode as Decode import qualified Argo.Json.Value as Value-import qualified Argo.Schema.Schema as Schema import qualified Argo.Vendor.TemplateHaskell as TH import qualified Argo.Vendor.Text as Text @@ -11,15 +10,6 @@     { TH.quoteExp =         either fail TH.lift         . Decode.decodePointer-        . Text.encodeUtf8-        . Text.pack-    }--schema :: TH.QuasiQuoter-schema = defaultQuasiQuoter-    { TH.quoteExp =-        either fail (TH.lift . Schema.fromValue)-        . Decode.decode         . Text.encodeUtf8         . Text.pack     }
source/library/Argo/Schema/Identifier.hs view
@@ -18,7 +18,7 @@     fromString = fromText . String.fromString  instance Semigroup Identifier where-    x <> y = fromText $ toText x <> toText y -- TODO: remove this+    x <> y = fromText $ toText x <> toText y  fromText :: Text.Text -> Identifier fromText = Identifier
source/library/Argo/Schema/Schema.hs view
@@ -4,51 +4,65 @@  module Argo.Schema.Schema where -import qualified Argo.Json.Array as Array-import qualified Argo.Json.Boolean as Boolean import qualified Argo.Json.Member as Member import qualified Argo.Json.Name as Name-import qualified Argo.Json.Object as Object import qualified Argo.Json.String as String import qualified Argo.Json.Value as Value import qualified Argo.Schema.Identifier as Identifier import qualified Argo.Vendor.DeepSeq as DeepSeq import qualified Argo.Vendor.TemplateHaskell as TH import qualified Argo.Vendor.Text as Text+import qualified Data.List.NonEmpty as NonEmpty import qualified GHC.Generics as Generics+import qualified Numeric.Natural as Natural  -- | A JSON Schema. -- <https://datatracker.ietf.org/doc/html/draft-handrews-json-schema-01>-newtype Schema-    = Schema Value.Value+data Schema+    = Array+        (Maybe Natural.Natural)+        (Maybe Natural.Natural)+        (Either Schema (NonEmpty.NonEmpty Schema))+        (Maybe Schema)+    | Boolean+    | Const Value.Value+    | False+    | Integer (Maybe Integer) (Maybe Integer)+    | Null+    | Number+    | Object [(Name.Name, Schema)] [Name.Name] (Maybe Schema)+    | OneOf [Schema]+    | Ref Identifier.Identifier+    | String (Maybe Natural.Natural) (Maybe Natural.Natural)+    | True     deriving (Eq, Generics.Generic, TH.Lift, DeepSeq.NFData, Show)  instance Semigroup Schema where-    x <> y = fromValue . Value.Object $ Object.fromList-        [ Member.fromTuple-              ( Name.fromString . String.fromText $ Text.pack "oneOf"-              , Value.Array $ Array.fromList [toValue x, toValue y]-              )-        ]+    x <> y = case (x, y) of+        (OneOf xs, OneOf ys) -> OneOf $ xs <> ys+        (OneOf xs, _) -> OneOf $ y : xs+        (_, OneOf ys) -> OneOf $ x : ys+        (_, _) -> OneOf [x, y]  instance Monoid Schema where-    mempty = true+    mempty = Argo.Schema.Schema.True -fromValue :: Value.Value -> Schema-fromValue = Schema+member :: String -> a -> Member.Member a+member k v =+    Member.fromTuple (Name.fromString . String.fromText $ Text.pack k, v) -toValue :: Schema -> Value.Value-toValue (Schema x) = x+maybeRef :: (Maybe Identifier.Identifier, Schema) -> Schema+maybeRef (m, s) = maybe s Ref m  false :: Schema-false = fromValue . Value.Boolean $ Boolean.fromBool False+false = Argo.Schema.Schema.False  true :: Schema-true = fromValue . Value.Boolean $ Boolean.fromBool True+true = Argo.Schema.Schema.True  unidentified :: Schema -> (Maybe Identifier.Identifier, Schema) unidentified s = (Nothing, s) -identified+withIdentifier     :: Identifier.Identifier -> Schema -> (Maybe Identifier.Identifier, Schema)-identified i s = (Just i, s)+withIdentifier i s = (Just i, s)
+ source/library/Argo/Type/Nullable.hs view
@@ -0,0 +1,17 @@+module Argo.Type.Nullable where++newtype Nullable a+    = Nullable (Maybe a)+    deriving (Eq, Show)++fromMaybe :: Maybe a -> Nullable a+fromMaybe = Nullable++toMaybe :: Nullable a -> Maybe a+toMaybe (Nullable x) = x++nothing :: Nullable a+nothing = fromMaybe Nothing++just :: a -> Nullable a+just = fromMaybe . Just
+ source/library/Argo/Type/Optional.hs view
@@ -0,0 +1,17 @@+module Argo.Type.Optional where++newtype Optional a+    = Optional (Maybe a)+    deriving (Eq, Show)++fromMaybe :: Maybe a -> Optional a+fromMaybe = Optional++toMaybe :: Optional a -> Maybe a+toMaybe (Optional x) = x++nothing :: Optional a+nothing = fromMaybe Nothing++just :: a -> Optional a+just = fromMaybe . Just
source/library/Argo/Type/Permission.hs view
@@ -1,6 +1,19 @@+{-# LANGUAGE DeriveAnyClass #-}+{-# LANGUAGE DeriveGeneric #-}+{-# LANGUAGE DeriveLift #-}+ module Argo.Type.Permission where +import qualified Argo.Vendor.DeepSeq as DeepSeq+import qualified Argo.Vendor.TemplateHaskell as TH+import qualified GHC.Generics as Generics+ data Permission     = Allow     | Forbid-    deriving (Eq, Show)+    deriving (Eq, Generics.Generic, TH.Lift, DeepSeq.NFData, Show)++toBool :: Permission -> Bool+toBool x = case x of+    Allow -> True+    Forbid -> False
source/library/Argo/Vendor/Text.hs view
@@ -8,6 +8,7 @@     , Text.null     , Text.pack     , Text.singleton+    , Text.stripPrefix     , LazyText.toStrict     , Text.uncons     , Text.unpack
source/test-suite/Main.hs view
@@ -7,6 +7,7 @@ import Test.Tasty.QuickCheck ((===))  import qualified Argo+import qualified Argo.Class.HasCodec as HasCodec import qualified Argo.Codec.Codec as Codec import qualified Argo.Codec.Object as Codec import qualified Argo.Codec.Value as Codec@@ -20,6 +21,8 @@ import qualified Argo.Schema.Identifier as Identifier import qualified Argo.Schema.Schema as Schema import qualified Argo.Type.Decimal as Decimal+import qualified Argo.Type.Nullable as Nullable+import qualified Argo.Type.Optional as Optional import qualified Argo.Type.Permission as Permission import qualified Control.Monad.Trans.Accum as Accum import qualified Data.ByteString as ByteString@@ -31,6 +34,7 @@ import qualified Data.Text as Text import qualified Data.Text.Lazy as LazyText import qualified Data.Word as Word+import qualified GHC.Stack as Stack import qualified Numeric.Natural as Natural import qualified Test.Tasty as Tasty import qualified Test.Tasty.HUnit as Tasty@@ -627,10 +631,10 @@                     (Argo.Array [Argo.String "", Argo.Boolean False])                 @?= Right ("" :: Text.Text, False)         , Tasty.testCase "encode record" $ do-            Codec.encodeWith Argo.codec (Record False Nothing)+            Codec.encodeWith Argo.codec (Record False Optional.nothing)                 @?= Argo.Object                         [Argo.Member (Argo.Name "bool") $ Argo.Boolean False]-            Codec.encodeWith Argo.codec (Record False $ Just "")+            Codec.encodeWith Argo.codec (Record False $ Optional.just "")                 @?= Argo.Object                         [ Argo.Member (Argo.Name "bool") $ Argo.Boolean False                         , Argo.Member (Argo.Name "text") $ Argo.String ""@@ -641,7 +645,7 @@                     (Argo.Object                         [Argo.Member (Argo.Name "bool") $ Argo.Boolean False]                     )-                @?= Right (Record False Nothing)+                @?= Right (Record False Optional.nothing)             Codec.decodeWith                     Argo.codec                     (Argo.Object@@ -649,7 +653,7 @@                         , Argo.Member (Argo.Name "text") $ Argo.String ""                         ]                     )-                @?= Right (Record False $ Just "")+                @?= Right (Record False $ Optional.just "")         ]     , Tasty.testGroup "Pointer"         $ let pointer = Argo.Pointer . fmap Argo.Token@@ -737,111 +741,142 @@     , Tasty.testGroup         "Schema"         [ Tasty.testCase "value" $ do-            let expected = schemafy (Just "Value") [Argo.schema| true |]-                actual = Codec.schema (Argo.codec :: Codec.Value Argo.Value)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Value")+                [Argo.value| true |]+                (Codec.schema (Argo.codec :: Codec.Value Argo.Value))         , Tasty.testCase "null" $ do-            let expected =-                    schemafy (Just "Null") [Argo.schema| { "type": "null" } |]-                actual = Codec.schema (Argo.codec :: Codec.Value Null.Null)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Null")+                [Argo.value| { "type": "null" } |]+                (Codec.schema (Argo.codec :: Codec.Value Null.Null))         , Tasty.testCase "boolean" $ do-            let expected = schemafy-                    (Just "Boolean")-                    [Argo.schema| { "type": "boolean" } |]-                actual =-                    Codec.schema (Argo.codec :: Codec.Value Boolean.Boolean)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Boolean")+                [Argo.value| { "type": "boolean" } |]+                (Codec.schema (Argo.codec :: Codec.Value Boolean.Boolean))         , Tasty.testCase "number" $ do-            let expected = schemafy-                    (Just "Number")-                    [Argo.schema| { "type": "number" } |]-                actual =-                    Codec.schema (Argo.codec :: Codec.Value Number.Number)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Number")+                [Argo.value| { "type": "number" } |]+                (Codec.schema (Argo.codec :: Codec.Value Number.Number))         , Tasty.testCase "string" $ do-            let expected = schemafy-                    (Just "String")-                    [Argo.schema| { "type": "string" } |]-                actual =-                    Codec.schema (Argo.codec :: Codec.Value String.String)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "String")+                [Argo.value| { "type": "string" } |]+                (Codec.schema (Argo.codec :: Codec.Value String.String))         , Tasty.testCase "array boolean" $ do-            let expected = schemafy-                    (Just "Array Boolean")-                    [Argo.schema| { "type": "array", "items": { "$ref": "#/definitions/Boolean" } } |]-                actual =-                    Codec.schema-                        (Argo.codec :: Codec.Value-                              (Array.Array Boolean.Boolean)-                        )-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Array Boolean")+                [Argo.value| {+                    "type": "array",+                    "items": { "$ref": "#/definitions/Boolean" }+                } |]+                (Codec.schema+                    (Argo.codec :: Codec.Value (Array.Array Boolean.Boolean))+                )         , Tasty.testCase "object boolean" $ do-            let expected = schemafy-                    (Just "Object Boolean")-                    [Argo.schema| { "type": "object", "additionalProperties": { "$ref": "#/definitions/Boolean" } } |]-                actual =-                    Codec.schema-                        (Argo.codec :: Codec.Value-                              (Object.Object Boolean.Boolean)-                        )-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Object Boolean")+                [Argo.value| {+                    "type": "object",+                    "additionalProperties": { "$ref": "#/definitions/Boolean" }+                } |]+                (Codec.schema+                    (Argo.codec :: Codec.Value (Object.Object Boolean.Boolean))+                )         , Tasty.testCase "maybe boolean" $ do-            let expected = schemafy-                    (Just "Maybe Boolean")-                    [Argo.schema| { "oneOf": [ { "type": "boolean" }, { "type": "null" } ] } |]-                actual = Codec.schema+            schemaTest+                (Just "Maybe Boolean")+                [Argo.value| { "oneOf": [+                    { "type": "boolean" },+                    { "type": "null" }+                ] } |]+                (Codec.schema                     (Argo.codec :: Codec.Value (Maybe Boolean.Boolean))-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+                )         , Tasty.testCase "either boolean number" $ do-            let expected = schemafy-                    (Just "Either Boolean Number")-                    [Argo.schema| { "oneOf": [ { "type": "object", "properties": { "type": { "const": "Left" }, "value": { "$ref": "#/definitions/Boolean" } }, "required": [ "type", "value" ], "additionalProperties": false }, { "type": "object", "properties": { "type": { "const": "Right" }, "value": { "$ref": "#/definitions/Number" } }, "required": [ "type", "value" ], "additionalProperties": false } ] } |]-                actual =-                    Codec.schema-                        (Argo.codec :: Codec.Value-                              (Either Boolean.Boolean Number.Number)-                        )-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Either Boolean Number")+                [Argo.value| { "oneOf": [+                    {+                        "type": "object",+                        "properties": {+                            "type": { "const": "Left" },+                            "value": { "$ref": "#/definitions/Boolean" }+                        },+                        "required": [ "type", "value" ],+                        "additionalProperties": false },+                    {+                        "type": "object",+                        "properties": {+                            "type": { "const": "Right" },+                            "value": { "$ref": "#/definitions/Number" }+                        },+                        "required": [ "type", "value" ],+                        "additionalProperties": false+                    }+                ] } |]+                (Codec.schema+                    (Argo.codec :: Codec.Value+                          (Either Boolean.Boolean Number.Number)+                    )+                )         , Tasty.testCase "()" $ do-            let expected = schemafy-                    (Just "()")-                    [Argo.schema| { "type": "array", "items": [], "additionalItems": false } |]-                actual = Codec.schema (Argo.codec :: Codec.Value ())-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "()")+                [Argo.value| {+                    "type": "array",+                    "minItems": 0,+                    "maxItems": 0,+                    "items": false+                } |]+                (Codec.schema (Argo.codec :: Codec.Value ()))         , Tasty.testCase "2-tuple" $ do-            let expected = schemafy-                    (Just "(Value,Null)")-                    [Argo.schema| { "type": "array", "items":-                        [ { "$ref": "#/definitions/Value" }-                        , { "$ref": "#/definitions/Null" }-                        ], "additionalItems": false } |]-                actual = Codec.schema+            schemaTest+                (Just "(Value,Null)")+                [Argo.value| {+                    "type": "array",+                    "minItems": 2,+                    "maxItems": 2,+                    "items": [+                        { "$ref": "#/definitions/Value" },+                        { "$ref": "#/definitions/Null" }+                    ] } |]+                (Codec.schema                     (Argo.codec :: Codec.Value (Argo.Value, Null.Null))-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+                )         , Tasty.testCase "3-tuple" $ do-            let expected = schemafy-                    (Just "(Value,Null,Boolean)")-                    [Argo.schema| { "type": "array", "items":-                        [ { "$ref": "#/definitions/Value" }-                        , { "$ref": "#/definitions/Null" }-                        , { "$ref": "#/definitions/Boolean" }-                        ], "additionalItems": false } |]-                actual = Codec.schema+            schemaTest+                (Just "(Value,Null,Boolean)")+                [Argo.value| {+                    "type": "array",+                    "minItems": 3,+                    "maxItems": 3,+                    "items": [+                        { "$ref": "#/definitions/Value" },+                        { "$ref": "#/definitions/Null" },+                        { "$ref": "#/definitions/Boolean" }+                    ] } |]+                (Codec.schema                     (Argo.codec :: Codec.Value                           (Argo.Value, Null.Null, Boolean.Boolean)                     )-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+                )         , Tasty.testCase "4-tuple" $ do-            let expected = schemafy-                    (Just "(Value,Null,Boolean,Number)")-                    [Argo.schema| { "type": "array", "items":-                        [ { "$ref": "#/definitions/Value" }-                        , { "$ref": "#/definitions/Null" }-                        , { "$ref": "#/definitions/Boolean" }-                        , { "$ref": "#/definitions/Number" }-                        ], "additionalItems": false } |]-                actual = Codec.schema+            schemaTest+                (Just "(Value,Null,Boolean,Number)")+                [Argo.value| {+                    "type": "array",+                    "minItems": 4,+                    "maxItems": 4,+                    "items": [+                        { "$ref": "#/definitions/Value" },+                        { "$ref": "#/definitions/Null" },+                        { "$ref": "#/definitions/Boolean" },+                        { "$ref": "#/definitions/Number" }+                    ] } |]+                (Codec.schema                     (Argo.codec :: Codec.Value                           ( Argo.Value                           , Null.Null@@ -849,18 +884,22 @@                           , Number.Number                           )                     )-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+                )         , Tasty.testCase "5-tuple" $ do-            let expected = schemafy-                    (Just "(Value,Null,Boolean,Number,Integer)")-                    [Argo.schema| { "type": "array", "items":-                        [ { "$ref": "#/definitions/Value" }-                        , { "$ref": "#/definitions/Null" }-                        , { "$ref": "#/definitions/Boolean" }-                        , { "$ref": "#/definitions/Number" }-                        , { "$ref": "#/definitions/Integer" }-                        ], "additionalItems": false } |]-                actual = Codec.schema+            schemaTest+                (Just "(Value,Null,Boolean,Number,Integer)")+                [Argo.value| {+                    "type": "array",+                    "minItems": 5,+                    "maxItems": 5,+                    "items": [+                        { "$ref": "#/definitions/Value" },+                        { "$ref": "#/definitions/Null" },+                        { "$ref": "#/definitions/Boolean" },+                        { "$ref": "#/definitions/Number" },+                        { "$ref": "#/definitions/Integer" }+                    ] } |]+                (Codec.schema                     (Argo.codec :: Codec.Value                           ( Argo.Value                           , Null.Null@@ -869,19 +908,23 @@                           , Integer                           )                     )-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+                )         , Tasty.testCase "6-tuple" $ do-            let expected = schemafy-                    (Just "(Value,Null,Boolean,Number,Integer,String)")-                    [Argo.schema| { "type": "array", "items":-                        [ { "$ref": "#/definitions/Value" }-                        , { "$ref": "#/definitions/Null" }-                        , { "$ref": "#/definitions/Boolean" }-                        , { "$ref": "#/definitions/Number" }-                        , { "$ref": "#/definitions/Integer" }-                        , { "$ref": "#/definitions/String" }-                        ], "additionalItems": false } |]-                actual = Codec.schema+            schemaTest+                (Just "(Value,Null,Boolean,Number,Integer,String)")+                [Argo.value| {+                    "type": "array",+                    "minItems": 6,+                    "maxItems": 6,+                    "items": [+                        { "$ref": "#/definitions/Value" },+                        { "$ref": "#/definitions/Null" },+                        { "$ref": "#/definitions/Boolean" },+                        { "$ref": "#/definitions/Number" },+                        { "$ref": "#/definitions/Integer" },+                        { "$ref": "#/definitions/String" }+                    ] } |]+                (Codec.schema                     (Argo.codec :: Codec.Value                           ( Argo.Value                           , Null.Null@@ -891,20 +934,24 @@                           , String.String                           )                     )-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+                )         , Tasty.testCase "7-tuple" $ do-            let expected = schemafy-                    (Just "(Value,Null,Boolean,Number,Integer,String,())")-                    [Argo.schema| { "type": "array", "items":-                        [ { "$ref": "#/definitions/Value" }-                        , { "$ref": "#/definitions/Null" }-                        , { "$ref": "#/definitions/Boolean" }-                        , { "$ref": "#/definitions/Number" }-                        , { "$ref": "#/definitions/Integer" }-                        , { "$ref": "#/definitions/String" }-                        , { "$ref": "#/definitions/()" }-                        ], "additionalItems": false } |]-                actual = Codec.schema+            schemaTest+                (Just "(Value,Null,Boolean,Number,Integer,String,())")+                [Argo.value| {+                    "type": "array",+                    "minItems": 7,+                    "maxItems": 7,+                    "items": [+                        { "$ref": "#/definitions/Value" },+                        { "$ref": "#/definitions/Null" },+                        { "$ref": "#/definitions/Boolean" },+                        { "$ref": "#/definitions/Number" },+                        { "$ref": "#/definitions/Integer" },+                        { "$ref": "#/definitions/String" },+                        { "$ref": "#/definitions/()" }+                    ] } |]+                (Codec.schema                     (Argo.codec :: Codec.Value                           ( Argo.Value                           , Null.Null@@ -915,21 +962,25 @@                           , ()                           )                     )-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+                )         , Tasty.testCase "8-tuple" $ do-            let expected = schemafy-                    (Just "(Value,Null,Boolean,Number,Integer,String,(),Char)")-                    [Argo.schema| { "type": "array", "items":-                        [ { "$ref": "#/definitions/Value" }-                        , { "$ref": "#/definitions/Null" }-                        , { "$ref": "#/definitions/Boolean" }-                        , { "$ref": "#/definitions/Number" }-                        , { "$ref": "#/definitions/Integer" }-                        , { "$ref": "#/definitions/String" }-                        , { "$ref": "#/definitions/()" }-                        , { "$ref": "#/definitions/Char" }-                        ], "additionalItems": false } |]-                actual = Codec.schema+            schemaTest+                (Just "(Value,Null,Boolean,Number,Integer,String,(),Char)")+                [Argo.value| {+                    "type": "array",+                    "minItems": 8,+                    "maxItems": 8,+                    "items": [+                        { "$ref": "#/definitions/Value" },+                        { "$ref": "#/definitions/Null" },+                        { "$ref": "#/definitions/Boolean" },+                        { "$ref": "#/definitions/Number" },+                        { "$ref": "#/definitions/Integer" },+                        { "$ref": "#/definitions/String" },+                        { "$ref": "#/definitions/()" },+                        { "$ref": "#/definitions/Char" }+                    ] } |]+                (Codec.schema                     (Argo.codec :: Codec.Value                           ( Argo.Value                           , Null.Null@@ -941,251 +992,411 @@                           , Char                           )                     )-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+                )         , Tasty.testCase "bool" $ do-            let expected = schemafy-                    (Just "Bool")-                    [Argo.schema| { "type": "boolean" } |]-                actual = Codec.schema (Argo.codec :: Codec.Value Bool)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Bool")+                [Argo.value| { "type": "boolean" } |]+                (Codec.schema (Argo.codec :: Codec.Value Bool))         , Tasty.testCase "decimal" $ do-            let expected = schemafy-                    (Just "Decimal")-                    [Argo.schema| { "type": "number" } |]-                actual =-                    Codec.schema (Argo.codec :: Codec.Value Decimal.Decimal)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Decimal")+                [Argo.value| { "type": "number" } |]+                (Codec.schema (Argo.codec :: Codec.Value Decimal.Decimal))         , Tasty.testCase "text" $ do-            let expected = schemafy-                    (Just "Text")-                    [Argo.schema| { "type": "string" } |]-                actual = Codec.schema (Argo.codec :: Codec.Value Text.Text)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Text")+                [Argo.value| { "type": "string" } |]+                (Codec.schema (Argo.codec :: Codec.Value Text.Text))         , Tasty.testCase "list boolean" $ do-            let expected = schemafy-                    (Just "[Boolean]")-                    [Argo.schema| { "type": "array", "items": { "$ref": "#/definitions/Boolean" } } |]-                actual =-                    Codec.schema (Argo.codec :: Codec.Value [Boolean.Boolean])-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "[Boolean]")+                [Argo.value| {+                    "type": "array",+                    "items": { "$ref": "#/definitions/Boolean" }+                } |]+                (Codec.schema (Argo.codec :: Codec.Value [Boolean.Boolean]))         , Tasty.testCase "map name boolean" $ do-            let expected = schemafy-                    (Just "Map Name Boolean")-                    [Argo.schema| { "type": "object", "additionalProperties": { "$ref": "#/definitions/Boolean" } } |]-                actual =-                    Codec.schema-                        (Argo.codec :: Codec.Value-                              (Map.Map Name.Name Boolean.Boolean)-                        )-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Map Name Boolean")+                [Argo.value| {+                    "type": "object",+                    "additionalProperties": { "$ref": "#/definitions/Boolean" }+                } |]+                (Codec.schema+                    (Argo.codec :: Codec.Value+                          (Map.Map Name.Name Boolean.Boolean)+                    )+                )         , Tasty.testCase "map (argo) string boolean" $ do-            let expected = schemafy-                    (Just "Map String Boolean")-                    [Argo.schema| { "type": "object", "additionalProperties": { "$ref": "#/definitions/Boolean" } } |]-                actual = Codec.schema+            schemaTest+                (Just "Map String Boolean")+                [Argo.value| {+                    "type": "object",+                    "additionalProperties": { "$ref": "#/definitions/Boolean" }+                } |]+                (Codec.schema                     (Argo.codec :: Codec.Value                           (Map.Map String.String Boolean.Boolean)                     )-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+                )         , Tasty.testCase "map (strict) text boolean" $ do-            let expected = schemafy-                    (Just "Map Text Boolean")-                    [Argo.schema| { "type": "object", "additionalProperties": { "$ref": "#/definitions/Boolean" } } |]-                actual =-                    Codec.schema-                        (Argo.codec :: Codec.Value-                              (Map.Map Text.Text Boolean.Boolean)-                        )-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Map Text Boolean")+                [Argo.value| {+                    "type": "object",+                    "additionalProperties": { "$ref": "#/definitions/Boolean" }+                } |]+                (Codec.schema+                    (Argo.codec :: Codec.Value+                          (Map.Map Text.Text Boolean.Boolean)+                    )+                )         , Tasty.testCase "map (lazy) text boolean" $ do-            let expected = schemafy-                    (Just "Map Text Boolean")-                    [Argo.schema| { "type": "object", "additionalProperties": { "$ref": "#/definitions/Boolean" } } |]-                actual = Codec.schema+            schemaTest+                (Just "Map Text Boolean")+                [Argo.value| {+                    "type": "object",+                    "additionalProperties": { "$ref": "#/definitions/Boolean" }+                } |]+                (Codec.schema                     (Argo.codec :: Codec.Value                           (Map.Map LazyText.Text Boolean.Boolean)                     )-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+                )         , Tasty.testCase "map (base) string boolean" $ do-            let expected = schemafy-                    (Just "Map [Char] Boolean")-                    [Argo.schema| { "type": "object", "additionalProperties": { "$ref": "#/definitions/Boolean" } } |]-                actual =-                    Codec.schema-                        (Argo.codec :: Codec.Value-                              (Map.Map String Boolean.Boolean)-                        )-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Map [Char] Boolean")+                [Argo.value| {+                    "type": "object",+                    "additionalProperties": { "$ref": "#/definitions/Boolean" }+                } |]+                (Codec.schema+                    (Argo.codec :: Codec.Value (Map.Map String Boolean.Boolean)+                    )+                )         , Tasty.testCase "string" $ do-            let expected = schemafy-                    (Just "[Char]")-                    [Argo.schema| { "type": "string" } |]-                actual = Codec.schema (Argo.codec :: Codec.Value String)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "[Char]")+                [Argo.value| { "type": "string" } |]+                (Codec.schema (Argo.codec :: Codec.Value String))         , Tasty.testCase "char" $ do-            let expected = schemafy-                    (Just "Char")-                    [Argo.schema| { "type": "string", "minLength": 1, "maxLength": 1 } |]-                actual = Codec.schema (Argo.codec :: Codec.Value Char)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Char")+                [Argo.value| {+                    "type": "string",+                    "minLength": 1,+                    "maxLength": 1+                } |]+                (Codec.schema (Argo.codec :: Codec.Value Char))         , Tasty.testCase "lazy text" $ do-            let expected = schemafy-                    (Just "Text")-                    [Argo.schema| { "type": "string" } |]-                actual =-                    Codec.schema (Argo.codec :: Codec.Value LazyText.Text)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Text")+                [Argo.value| { "type": "string" } |]+                (Codec.schema (Argo.codec :: Codec.Value LazyText.Text))         , Tasty.testCase "non-empty boolean" $ do-            let expected = schemafy-                    (Just "NonEmpty Boolean")-                    [Argo.schema| { "type": "array", "items": { "type": "boolean" }, "minItems": 1 } |]-                actual = Codec.schema+            schemaTest+                (Just "NonEmpty Boolean")+                [Argo.value| {+                    "type": "array",+                    "minItems": 1,+                    "items": { "$ref": "#/definitions/Boolean" }+                } |]+                (Codec.schema                     (Argo.codec :: Codec.Value (NonEmpty Boolean.Boolean))-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+                )         , Tasty.testCase "integer" $ do-            let expected = schemafy-                    (Just "Integer")-                    [Argo.schema| { "type": "integer" } |]-                actual = Codec.schema (Argo.codec :: Codec.Value Integer)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Integer")+                [Argo.value| { "type": "integer" } |]+                (Codec.schema (Argo.codec :: Codec.Value Integer))         , Tasty.testCase "int" $ do-            let expected = schemafy-                    (Just "Int")-                    [Argo.schema| { "type": "integer", "minimum": -9223372036854775808, "maximum": 9223372036854775807 } |]-                actual = Codec.schema (Argo.codec :: Codec.Value Int)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Int")+                [Argo.value| {+                    "type": "integer",+                    "minimum": -9223372036854775808,+                    "maximum": 9223372036854775807+                } |]+                (Codec.schema (Argo.codec :: Codec.Value Int))         , Tasty.testCase "int8" $ do-            let expected = schemafy-                    (Just "Int8")-                    [Argo.schema| { "type": "integer", "minimum": -128, "maximum": 127 } |]-                actual = Codec.schema (Argo.codec :: Codec.Value Int.Int8)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Int8")+                [Argo.value| {+                    "type": "integer",+                    "minimum": -128,+                    "maximum": 127+                } |]+                (Codec.schema (Argo.codec :: Codec.Value Int.Int8))         , Tasty.testCase "int16" $ do-            let expected = schemafy-                    (Just "Int16")-                    [Argo.schema| { "type": "integer", "minimum": -32768, "maximum": 32767 } |]-                actual = Codec.schema (Argo.codec :: Codec.Value Int.Int16)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Int16")+                [Argo.value| {+                    "type": "integer",+                    "minimum": -32768,+                    "maximum": 32767+                } |]+                (Codec.schema (Argo.codec :: Codec.Value Int.Int16))         , Tasty.testCase "int32" $ do-            let expected = schemafy-                    (Just "Int32")-                    [Argo.schema| { "type": "integer", "minimum": -2147483648, "maximum": 2147483647 } |]-                actual = Codec.schema (Argo.codec :: Codec.Value Int.Int32)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Int32")+                [Argo.value| {+                    "type": "integer",+                    "minimum": -2147483648,+                    "maximum": 2147483647+                } |]+                (Codec.schema (Argo.codec :: Codec.Value Int.Int32))         , Tasty.testCase "int64" $ do-            let expected = schemafy-                    (Just "Int64")-                    [Argo.schema| { "type": "integer", "minimum": -9223372036854775808, "maximum": 9223372036854775807 } |]-                actual = Codec.schema (Argo.codec :: Codec.Value Int.Int64)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Int64")+                [Argo.value| {+                    "type": "integer",+                    "minimum": -9223372036854775808,+                    "maximum": 9223372036854775807+                } |]+                (Codec.schema (Argo.codec :: Codec.Value Int.Int64))         , Tasty.testCase "natural" $ do-            let expected = schemafy-                    (Just "Natural")-                    [Argo.schema| { "type": "integer", "minimum": 0 } |]-                actual =-                    Codec.schema (Argo.codec :: Codec.Value Natural.Natural)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Natural")+                [Argo.value| {+                    "type": "integer",+                    "minimum": 0+                } |]+                (Codec.schema (Argo.codec :: Codec.Value Natural.Natural))         , Tasty.testCase "word" $ do-            let expected = schemafy-                    (Just "Word")-                    [Argo.schema| { "type": "integer", "minimum": 0, "maximum": 18446744073709551615 } |]-                actual = Codec.schema (Argo.codec :: Codec.Value Word)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Word")+                [Argo.value| {+                    "type": "integer",+                    "minimum": 0,+                    "maximum": 18446744073709551615+                } |]+                (Codec.schema (Argo.codec :: Codec.Value Word))         , Tasty.testCase "word8" $ do-            let expected = schemafy-                    (Just "Word8")-                    [Argo.schema| { "type": "integer", "minimum": 0, "maximum": 255 } |]-                actual = Codec.schema (Argo.codec :: Codec.Value Word.Word8)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Word8")+                [Argo.value| {+                    "type": "integer",+                    "minimum": 0,+                    "maximum": 255+                } |]+                (Codec.schema (Argo.codec :: Codec.Value Word.Word8))         , Tasty.testCase "word16" $ do-            let expected = schemafy-                    (Just "Word16")-                    [Argo.schema| { "type": "integer", "minimum": 0, "maximum": 65535 } |]-                actual = Codec.schema (Argo.codec :: Codec.Value Word.Word16)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Word16")+                [Argo.value| {+                    "type": "integer",+                    "minimum": 0,+                    "maximum": 65535+                } |]+                (Codec.schema (Argo.codec :: Codec.Value Word.Word16))         , Tasty.testCase "word32" $ do-            let expected = schemafy-                    (Just "Word32")-                    [Argo.schema| { "type": "integer", "minimum": 0, "maximum": 4294967295 } |]-                actual = Codec.schema (Argo.codec :: Codec.Value Word.Word32)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Word32")+                [Argo.value| {+                    "type": "integer",+                    "minimum": 0,+                    "maximum": 4294967295+                } |]+                (Codec.schema (Argo.codec :: Codec.Value Word.Word32))         , Tasty.testCase "word64" $ do-            let expected = schemafy-                    (Just "Word64")-                    [Argo.schema| { "type": "integer", "minimum": 0, "maximum": 18446744073709551615 } |]-                actual = Codec.schema (Argo.codec :: Codec.Value Word.Word64)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Word64")+                [Argo.value| {+                    "type": "integer",+                    "minimum": 0,+                    "maximum": 18446744073709551615+                } |]+                (Codec.schema (Argo.codec :: Codec.Value Word.Word64))         , Tasty.testCase "float" $ do-            let expected = schemafy-                    (Just "Float")-                    [Argo.schema| { "type": "number" } |]-                actual = Codec.schema (Argo.codec :: Codec.Value Float)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Float")+                [Argo.value| { "type": "number" } |]+                (Codec.schema (Argo.codec :: Codec.Value Float))         , Tasty.testCase "double" $ do-            let expected = schemafy-                    (Just "Double")-                    [Argo.schema| { "type": "number" } |]-                actual = Codec.schema (Argo.codec :: Codec.Value Double)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Double")+                [Argo.value| { "type": "number" } |]+                (Codec.schema (Argo.codec :: Codec.Value Double))         , Tasty.testCase "pointer" $ do-            let expected = schemafy-                    (Just "Pointer")-                    [Argo.schema| { "type": "string" } |]-                actual = Codec.schema (Argo.codec :: Codec.Value Argo.Pointer)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Pointer")+                [Argo.value| { "type": "string" } |]+                (Codec.schema (Argo.codec :: Codec.Value Argo.Pointer))         , Tasty.testCase "schema" $ do-            let expected = schemafy (Just "Schema") [Argo.schema| true |]-                actual =-                    Codec.schema (Argo.codec :: Codec.Value Schema.Schema)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                (Just "Schema")+                [Argo.value| { "oneOf": [+                    {+                        "type": "object",+                        "properties": { "oneOf": { "$ref": "#/definitions/[Schema]" } },+                        "required": [ "oneOf" ],+                        "additionalProperties": false+                    },+                    {+                        "type": "object",+                        "properties": { "$ref": { "$ref": "#/definitions/Identifier" } },+                        "required": [ "$ref" ],+                        "additionalProperties": false+                    },+                    {+                        "type": "object",+                        "properties": {+                            "type": { "const": "object" },+                            "properties": { "$ref": "#/definitions/Object Schema" },+                            "required": { "$ref": "#/definitions/[Name]" },+                            "additionalProperties": { "$ref": "#/definitions/Schema" }+                        },+                        "required": [ "type" ],+                        "additionalProperties": false+                    },+                    {+                        "type": "object",+                        "properties": {+                            "type": { "const": "array" },+                            "minItems": { "$ref": "#/definitions/Natural" },+                            "maxItems": { "$ref": "#/definitions/Natural" },+                            "items": { "$ref": "#/definitions/OneOf Schema [Schema]" },+                            "additionalItems": { "$ref": "#/definitions/Schema" }+                        },+                        "required": [ "type", "items" ],+                        "additionalProperties": false+                    },+                    {+                        "type": "object",+                        "properties": {+                            "type": { "const": "string" },+                            "minLength": { "$ref": "#/definitions/Natural" },+                            "maxLength": { "$ref": "#/definitions/Natural" }+                        },+                        "required": [ "type" ],+                        "additionalProperties": false+                    },+                    {+                        "type": "object",+                        "properties": {+                            "type": { "const": "integer" },+                            "minimum": { "$ref": "#/definitions/Integer" },+                            "maximum": { "$ref": "#/definitions/Integer" }+                        },+                        "required": [ "type" ],+                        "additionalProperties": false+                    },+                    {+                        "type": "object",+                        "properties": { "type": { "const": "number" } },+                        "required": [ "type" ],+                        "additionalProperties": false+                    },+                    {+                        "type": "object",+                        "properties": { "type": { "const": "boolean" } },+                        "required": [ "type" ],+                        "additionalProperties": false+                    },+                    {+                        "type": "object",+                        "properties": { "type": { "const": "null" } },+                        "required": [ "type" ],+                        "additionalProperties": false+                    },+                    {+                        "type": "object",+                        "properties": { "const": { "$ref": "#/definitions/Value" } },+                        "required": [ "const" ],+                        "additionalProperties": false+                    },+                    {+                        "const": true+                    },+                    {+                        "const": false+                    }+                ] } |]+                (Codec.schema (Argo.codec :: Codec.Value Schema.Schema))         , Tasty.testCase "record" $ do-            let expected = schemafy-                    Nothing-                    [Argo.schema| { "type": "object", "properties": { "bool": { "$ref": "#/definitions/Bool" }, "text": { "$ref": "#/definitions/Text" } }, "required": [ "bool" ], "additionalProperties": true } |]-                actual = Codec.schema (Argo.codec :: Codec.Value Record)-            Accum.evalAccumT actual mempty @?= Accum.evalAccumT expected mempty+            schemaTest+                Nothing+                [Argo.value| {+                    "type": "object",+                    "properties": {+                        "bool": { "$ref": "#/definitions/Bool" },+                        "text": { "$ref": "#/definitions/Text" }+                    },+                    "required": [ "bool" ]+                } |]+                (Codec.schema (Argo.codec :: Codec.Value Record))         ]     , Tasty.testGroup "T1"         $ let codec = Argo.codec :: Codec.Value T1           in               [ Tasty.testCase "schema" $ do-                  let expected = schemafy-                          Nothing-                          [Argo.schema|-                            {-                                "type": "object",-                                "properties": {-                                    "t1c1f1": { "$ref": "#/definitions/Float" },-                                    "t1c1f2": { "$ref": "#/definitions/Maybe Float" },-                                    "t1c1f3": { "$ref": "#/definitions/Float" },-                                    "t1c1f4": { "$ref": "#/definitions/Maybe Float" }-                                },-                                "required": [ "t1c1f1", "t1c1f2" ],-                                "additionalProperties": true-                            }-                        |]-                      actual = Codec.schema codec-                  Accum.evalAccumT actual mempty-                      @?= Accum.evalAccumT expected mempty+                  schemaTest+                      Nothing+                      [Argo.value|+                        {+                            "type": "object",+                            "properties": {+                                "t1c1f1": { "$ref": "#/definitions/Float" },+                                "t1c1f2": { "$ref": "#/definitions/Nullable Float" },+                                "t1c1f3": { "$ref": "#/definitions/Float" },+                                "t1c1f4": { "$ref": "#/definitions/Nullable Float" }+                            },+                            "required": [ "t1c1f1", "t1c1f2" ]+                        }+                    |]+                      (Codec.schema codec)               , Tasty.testCase "decode" $ do                   hush (Argo.decode "{ \"t1c1f1\": 0 }")                       @?= (Nothing :: Maybe T1)                   Argo.decode "{ \"t1c1f1\": 0, \"t1c1f2\": null }"-                      @?= Right (T1C1 0 Nothing Nothing Nothing)+                      @?= Right+                              (T1C1+                                  0+                                  Nullable.nothing+                                  Optional.nothing+                                  Optional.nothing+                              )                   Argo.decode "{ \"t1c1f1\": 1, \"t1c1f2\": 0 }"-                      @?= Right (T1C1 1 (Just 0) Nothing Nothing)-                  Argo.decode-                          "{ \"t1c1f1\": 2, \"t1c1f2\": null, \"t1c1f3\": null }"-                      @?= Right (T1C1 2 Nothing Nothing Nothing)+                      @?= Right+                              (T1C1+                                  1+                                  (Nullable.just 0)+                                  Optional.nothing+                                  Optional.nothing+                              )+                  hush+                          (Argo.decode+                              "{ \"t1c1f1\": 2, \"t1c1f2\": null, \"t1c1f3\": null }"+                          )+                      @?= (Nothing :: Maybe T1)                   Argo.decode                           "{ \"t1c1f1\": 3, \"t1c1f2\": null, \"t1c1f3\": 0 }"-                      @?= Right (T1C1 3 Nothing (Just 0) Nothing)+                      @?= Right+                              (T1C1+                                  3+                                  Nullable.nothing+                                  (Optional.just 0)+                                  Optional.nothing+                              )                   Argo.decode                           "{ \"t1c1f1\": 4, \"t1c1f2\": null, \"t1c1f4\": null }"-                      @?= Right (T1C1 4 Nothing Nothing (Just Nothing))+                      @?= Right+                              (T1C1+                                  4+                                  Nullable.nothing+                                  Optional.nothing+                                  (Optional.just Nullable.nothing)+                              )                   Argo.decode                           "{ \"t1c1f1\": 5, \"t1c1f2\": null, \"t1c1f4\": 0 }"-                      @?= Right (T1C1 5 Nothing Nothing (Just (Just 0)))+                      @?= Right+                              (T1C1+                                  5+                                  Nullable.nothing+                                  Optional.nothing+                                  (Optional.just $ Nullable.just 0)+                              )                   hush (Argo.decode "{ \"t1c1f1\": 6, \"t1c1f2\": [] }")                       @?= (Nothing :: Maybe T1)                   hush@@ -1203,28 +1414,84 @@                       encode =                           Builder.toLazyByteString . Argo.encode :: T1                               -> LazyByteString.ByteString-                  encode (T1C1 0 Nothing Nothing Nothing)+                  encode+                          (T1C1+                              0+                              Nullable.nothing+                              Optional.nothing+                              Optional.nothing+                          )                       @?= "{\"t1c1f1\":0,\"t1c1f2\":null}"-                  encode (T1C1 1 (Just 0) Nothing Nothing)+                  encode+                          (T1C1+                              1+                              (Nullable.just 0)+                              Optional.nothing+                              Optional.nothing+                          )                       @?= "{\"t1c1f1\":1,\"t1c1f2\":0}"-                  encode (T1C1 2 Nothing (Just 0) Nothing)+                  encode+                          (T1C1+                              2+                              Nullable.nothing+                              (Optional.just 0)+                              Optional.nothing+                          )                       @?= "{\"t1c1f1\":2,\"t1c1f2\":null,\"t1c1f3\":0}"-                  encode (T1C1 3 Nothing Nothing (Just Nothing))+                  encode+                          (T1C1+                              3+                              Nullable.nothing+                              Optional.nothing+                              (Optional.just Nullable.nothing)+                          )                       @?= "{\"t1c1f1\":3,\"t1c1f2\":null,\"t1c1f4\":null}"-                  encode (T1C1 4 Nothing Nothing (Just (Just 0)))+                  encode+                          (T1C1+                              4+                              Nullable.nothing+                              Optional.nothing+                              (Optional.just $ Nullable.just 0)+                          )                       @?= "{\"t1c1f1\":4,\"t1c1f2\":null,\"t1c1f4\":0}"               ]     , Tasty.testCase "T2" $ do-        let schema = [Argo.schema|-                { "type": "object"-                , "properties": { "t2c1f1": { "$ref": "#/definitions/T2" } }-                , "required": []-                , "additionalProperties": true+        let schema = [Argo.value| {+                "type": "object",+                "properties": { "t2c1f1": { "$ref": "#/definitions/T2" } },+                "additionalProperties": false+            } |]+            ((i, s), m) = Accum.runAccum+                (Codec.schema (Argo.codec :: Codec.Value T2))+                Map.empty+        i @?= Just "T2"+        toValue s @?= schema+        fmap toValue m @?= Map.singleton "T2" schema+    , Tasty.testGroup+        "T3"+        [ Tasty.testCase "schema" $ do+            schemaTest+                Nothing+                [Argo.value| {+                    "type": "object",+                    "properties": {+                        "t3c1f1": { "$ref": "#/definitions/Nullable Float" }+                    },+                    "additionalProperties": false                 } |]-            expected = schemafy (Just "T2") schema-            actual = Codec.schema (Argo.codec :: Codec.Value T2)-        Accum.runAccum actual mempty-            @?= (Accum.evalAccum expected mempty, Map.singleton "T2" schema)+                (Codec.schema (Argo.codec :: Codec.Value T3))+        , Tasty.testCase "decode" $ do+            Argo.decode "{}" @?= Right (T3C1 Nothing)+            Argo.decode "{ \"t3c1f1\": null }" @?= Right (T3C1 Nothing)+            Argo.decode "{ \"t3c1f1\": 0 }" @?= Right (T3C1 $ Just 0)+        , Tasty.testCase "encode" $ do+            let+                encode =+                    Builder.toLazyByteString . Argo.encode :: T3+                        -> LazyByteString.ByteString+            encode (T3C1 Nothing) @?= "{}"+            encode (T3C1 $ Just 0) @?= "{\"t3c1f1\":0}"+        ]     ]  fromValue :: Argo.HasCodec a => Argo.Value -> Either String a@@ -1237,21 +1504,21 @@ number s = Argo.Number . Argo.Decimal s  newtype T2 = T2C1-    { t2c1f1 :: Maybe T2+    { t2c1f1 :: Optional.Optional T2     } deriving (Eq, Show)  instance Argo.HasCodec T2 where     codec =         Codec.identified-            . Codec.fromObjectCodec Permission.Allow+            . Codec.fromObjectCodec Permission.Forbid             $ T2C1             <$> Codec.project t2c1f1 (Codec.optional "t2c1f1" Argo.codec)  data T1 = T1C1     { t1c1f1 :: Float-    , t1c1f2 :: Maybe Float-    , t1c1f3 :: Maybe Float-    , t1c1f4 :: Maybe (Maybe Float)+    , t1c1f2 :: Nullable.Nullable Float+    , t1c1f3 :: Optional.Optional Float+    , t1c1f4 :: Optional.Optional (Nullable.Nullable Float)     }     deriving (Eq, Show) @@ -1264,9 +1531,19 @@             <*> Codec.project t1c1f3 (Codec.optional "t1c1f3" Argo.codec)             <*> Codec.project t1c1f4 (Codec.optional "t1c1f4" Argo.codec) +newtype T3 = T3C1+    { t3c1f1 :: Maybe Float+    }+    deriving (Eq, Show)++instance Argo.HasCodec T3 where+    codec = Codec.fromObjectCodec Permission.Forbid $ T3C1 <$> Codec.project+        t3c1f1+        (HasCodec.optionalNullable "t3c1f1" Argo.codec)+ data Record = Record     { recordBool :: Bool-    , recordText :: Maybe Text.Text+    , recordText :: Optional.Optional Text.Text     }     deriving (Eq, Show) @@ -1301,11 +1578,15 @@ hush :: Either String a -> Maybe a hush = either (const Nothing) Just -schemafy-    :: Maybe Identifier.Identifier-    -> Schema.Schema+schemaTest+    :: Stack.HasCallStack+    => Maybe Identifier.Identifier+    -> Argo.Value     -> Accum.AccumT            (Map.Map Identifier.Identifier Schema.Schema)            Identity.Identity            (Maybe Identifier.Identifier, Schema.Schema)-schemafy m = pure . maybe Schema.unidentified Schema.identified m+    -> Tasty.Assertion+schemaTest maybeIdentifier value schema =+    fmap toValue (Accum.evalAccum schema Map.empty)+        @?= (maybeIdentifier, value)