{-# LANGUAGE DeriveGeneric #-}
{-# LANGUAGE FlexibleInstances #-}
{-# LANGUAGE InstanceSigs #-}
{-# LANGUAGE LambdaCase #-}
{-# LANGUAGE TypeFamilies #-}

module Cardano.Api.Governance.Metadata.DrepRegistration
  ( -- * DRep off-chain metadata

    -- | This module implements validation of metadata for DRep registration and
    -- update actions, as specified bt the CIP-119 (https://cips.cardano.org/cip/CIP-0119).
    --
    -- The constraints implemented in this module can be tested against a JSON
    -- 'ByteString' by using the function 'validateGovActionAnchorData' in
    -- "Cardano.Api.Governance.Metadata.Validation" with the parameter 'DrepRegistrationMetadata'.
    CIP119 (..)
  )
where

import           Cardano.Api.Governance.Metadata.Parsers (textWithMaxLength)
import           Cardano.Api.Governance.Metadata.Validation (Authors, Body, GovActionMetadata (..),
                   HashAlgorithm)

import           Data.Aeson (FromJSON, withObject, (.:), (.:?))
import qualified Data.Aeson as Aeson
import           Data.Aeson.Types (Parser)
import           Data.Text (Text)
import           GHC.Generics (Generic)

data CIP119 = DrepRegistrationMetadata

instance FromJSON (GovActionMetadata CIP119) where
  parseJSON :: Aeson.Value -> Parser (GovActionMetadata CIP119)
  parseJSON :: Value -> Parser (GovActionMetadata CIP119)
parseJSON = String
-> (Object -> Parser (GovActionMetadata CIP119))
-> Value
-> Parser (GovActionMetadata CIP119)
forall a. String -> (Object -> Parser a) -> Value -> Parser a
withObject String
"CIP119Common" ((Object -> Parser (GovActionMetadata CIP119))
 -> Value -> Parser (GovActionMetadata CIP119))
-> (Object -> Parser (GovActionMetadata CIP119))
-> Value
-> Parser (GovActionMetadata CIP119)
forall a b. (a -> b) -> a -> b
$ \Object
v ->
    HashAlgorithm CIP119
-> Authors CIP119 -> Body CIP119 -> GovActionMetadata CIP119
forall cip.
HashAlgorithm cip
-> Authors cip -> Body cip -> GovActionMetadata cip
GovActionMetadata
      (HashAlgorithm CIP119
 -> Authors CIP119 -> Body CIP119 -> GovActionMetadata CIP119)
-> Parser (HashAlgorithm CIP119)
-> Parser
     (Authors CIP119 -> Body CIP119 -> GovActionMetadata CIP119)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Object
v Object -> Key -> Parser (HashAlgorithm CIP119)
forall a. FromJSON a => Object -> Key -> Parser a
.: Key
"hashAlgorithm"
      Parser (Authors CIP119 -> Body CIP119 -> GovActionMetadata CIP119)
-> Parser (Authors CIP119)
-> Parser (Body CIP119 -> GovActionMetadata CIP119)
forall a b. Parser (a -> b) -> Parser a -> Parser b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Authors CIP119 -> Parser (Authors CIP119)
forall a. a -> Parser a
forall (f :: * -> *) a. Applicative f => a -> f a
pure Authors CIP119
Absent
      Parser (Body CIP119 -> GovActionMetadata CIP119)
-> Parser (Body CIP119) -> Parser (GovActionMetadata CIP119)
forall a b. Parser (a -> b) -> Parser a -> Parser b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Object
v Object -> Key -> Parser (Body CIP119)
forall a. FromJSON a => Object -> Key -> Parser a
.: Key
"body"

-- Hash Algorithm (Enum)
data instance HashAlgorithm CIP119 = Blake2b256
  deriving (Int -> HashAlgorithm CIP119 -> ShowS
[HashAlgorithm CIP119] -> ShowS
HashAlgorithm CIP119 -> String
(Int -> HashAlgorithm CIP119 -> ShowS)
-> (HashAlgorithm CIP119 -> String)
-> ([HashAlgorithm CIP119] -> ShowS)
-> Show (HashAlgorithm CIP119)
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> HashAlgorithm CIP119 -> ShowS
showsPrec :: Int -> HashAlgorithm CIP119 -> ShowS
$cshow :: HashAlgorithm CIP119 -> String
show :: HashAlgorithm CIP119 -> String
$cshowList :: [HashAlgorithm CIP119] -> ShowS
showList :: [HashAlgorithm CIP119] -> ShowS
Show, (forall x. HashAlgorithm CIP119 -> Rep (HashAlgorithm CIP119) x)
-> (forall x. Rep (HashAlgorithm CIP119) x -> HashAlgorithm CIP119)
-> Generic (HashAlgorithm CIP119)
forall x. Rep (HashAlgorithm CIP119) x -> HashAlgorithm CIP119
forall x. HashAlgorithm CIP119 -> Rep (HashAlgorithm CIP119) x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. HashAlgorithm CIP119 -> Rep (HashAlgorithm CIP119) x
from :: forall x. HashAlgorithm CIP119 -> Rep (HashAlgorithm CIP119) x
$cto :: forall x. Rep (HashAlgorithm CIP119) x -> HashAlgorithm CIP119
to :: forall x. Rep (HashAlgorithm CIP119) x -> HashAlgorithm CIP119
Generic)

instance FromJSON (HashAlgorithm CIP119) where
  parseJSON :: Aeson.Value -> Parser (HashAlgorithm CIP119)
  parseJSON :: Value -> Parser (HashAlgorithm CIP119)
parseJSON = String
-> (Text -> Parser (HashAlgorithm CIP119))
-> Value
-> Parser (HashAlgorithm CIP119)
forall a. String -> (Text -> Parser a) -> Value -> Parser a
Aeson.withText String
"HashAlgorithm" ((Text -> Parser (HashAlgorithm CIP119))
 -> Value -> Parser (HashAlgorithm CIP119))
-> (Text -> Parser (HashAlgorithm CIP119))
-> Value
-> Parser (HashAlgorithm CIP119)
forall a b. (a -> b) -> a -> b
$
    \case
      Text
"blake2b-256" -> HashAlgorithm CIP119 -> Parser (HashAlgorithm CIP119)
forall a. a -> Parser a
forall (m :: * -> *) a. Monad m => a -> m a
return HashAlgorithm CIP119
Blake2b256
      Text
_ -> String -> Parser (HashAlgorithm CIP119)
forall a. String -> Parser a
forall (m :: * -> *) a. MonadFail m => String -> m a
fail String
"Invalid hashAlgorithm, it must be: blake2b-256"

-- Body of the metadata document
data instance Body CIP119 = Body
  { Body CIP119 -> Maybe Text
paymentAddress :: Maybe Text
  , Body CIP119 -> Text
givenName :: Text
  , Body CIP119 -> Maybe ImageObject
image :: Maybe ImageObject
  , Body CIP119 -> Maybe Text
objectives :: Maybe Text
  , Body CIP119 -> Maybe Text
motivations :: Maybe Text
  , Body CIP119 -> Maybe Text
qualifications :: Maybe Text
  , Body CIP119 -> Maybe DoNotList
doNotList :: Maybe DoNotList
  , Body CIP119 -> Maybe [Reference]
references :: Maybe [Reference]
  }
  deriving (Int -> Body CIP119 -> ShowS
[Body CIP119] -> ShowS
Body CIP119 -> String
(Int -> Body CIP119 -> ShowS)
-> (Body CIP119 -> String)
-> ([Body CIP119] -> ShowS)
-> Show (Body CIP119)
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> Body CIP119 -> ShowS
showsPrec :: Int -> Body CIP119 -> ShowS
$cshow :: Body CIP119 -> String
show :: Body CIP119 -> String
$cshowList :: [Body CIP119] -> ShowS
showList :: [Body CIP119] -> ShowS
Show, (forall x. Body CIP119 -> Rep (Body CIP119) x)
-> (forall x. Rep (Body CIP119) x -> Body CIP119)
-> Generic (Body CIP119)
forall x. Rep (Body CIP119) x -> Body CIP119
forall x. Body CIP119 -> Rep (Body CIP119) x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. Body CIP119 -> Rep (Body CIP119) x
from :: forall x. Body CIP119 -> Rep (Body CIP119) x
$cto :: forall x. Rep (Body CIP119) x -> Body CIP119
to :: forall x. Rep (Body CIP119) x -> Body CIP119
Generic)

instance FromJSON (Body CIP119) where
  parseJSON :: Aeson.Value -> Parser (Body CIP119)
  parseJSON :: Value -> Parser (Body CIP119)
parseJSON = String
-> (Object -> Parser (Body CIP119))
-> Value
-> Parser (Body CIP119)
forall a. String -> (Object -> Parser a) -> Value -> Parser a
withObject String
"Body" ((Object -> Parser (Body CIP119)) -> Value -> Parser (Body CIP119))
-> (Object -> Parser (Body CIP119))
-> Value
-> Parser (Body CIP119)
forall a b. (a -> b) -> a -> b
$ \Object
v ->
    Maybe Text
-> Text
-> Maybe ImageObject
-> Maybe Text
-> Maybe Text
-> Maybe Text
-> Maybe DoNotList
-> Maybe [Reference]
-> Body CIP119
Body
      (Maybe Text
 -> Text
 -> Maybe ImageObject
 -> Maybe Text
 -> Maybe Text
 -> Maybe Text
 -> Maybe DoNotList
 -> Maybe [Reference]
 -> Body CIP119)
-> Parser (Maybe Text)
-> Parser
     (Text
      -> Maybe ImageObject
      -> Maybe Text
      -> Maybe Text
      -> Maybe Text
      -> Maybe DoNotList
      -> Maybe [Reference]
      -> Body CIP119)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Object
v Object -> Key -> Parser (Maybe Text)
forall a. FromJSON a => Object -> Key -> Parser (Maybe a)
.:? Key
"paymentAddress"
      Parser
  (Text
   -> Maybe ImageObject
   -> Maybe Text
   -> Maybe Text
   -> Maybe Text
   -> Maybe DoNotList
   -> Maybe [Reference]
   -> Body CIP119)
-> Parser Text
-> Parser
     (Maybe ImageObject
      -> Maybe Text
      -> Maybe Text
      -> Maybe Text
      -> Maybe DoNotList
      -> Maybe [Reference]
      -> Body CIP119)
forall a b. Parser (a -> b) -> Parser a -> Parser b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> (Object
v Object -> Key -> Parser Value
forall a. FromJSON a => Object -> Key -> Parser a
.: Key
"givenName" Parser Value -> (Value -> Parser Text) -> Parser Text
forall a b. Parser a -> (a -> Parser b) -> Parser b
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= String -> Int -> Value -> Parser Text
textWithMaxLength String
"givenName" Int
80)
      Parser
  (Maybe ImageObject
   -> Maybe Text
   -> Maybe Text
   -> Maybe Text
   -> Maybe DoNotList
   -> Maybe [Reference]
   -> Body CIP119)
-> Parser (Maybe ImageObject)
-> Parser
     (Maybe Text
      -> Maybe Text
      -> Maybe Text
      -> Maybe DoNotList
      -> Maybe [Reference]
      -> Body CIP119)
forall a b. Parser (a -> b) -> Parser a -> Parser b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Object
v Object -> Key -> Parser (Maybe ImageObject)
forall a. FromJSON a => Object -> Key -> Parser (Maybe a)
.:? Key
"image"
      Parser
  (Maybe Text
   -> Maybe Text
   -> Maybe Text
   -> Maybe DoNotList
   -> Maybe [Reference]
   -> Body CIP119)
-> Parser (Maybe Text)
-> Parser
     (Maybe Text
      -> Maybe Text
      -> Maybe DoNotList
      -> Maybe [Reference]
      -> Body CIP119)
forall a b. Parser (a -> b) -> Parser a -> Parser b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> (Object
v Object -> Key -> Parser (Maybe Value)
forall a. FromJSON a => Object -> Key -> Parser (Maybe a)
.:? Key
"objectives" Parser (Maybe Value)
-> (Maybe Value -> Parser (Maybe Text)) -> Parser (Maybe Text)
forall a b. Parser a -> (a -> Parser b) -> Parser b
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= (Value -> Parser Text) -> Maybe Value -> Parser (Maybe Text)
forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
(a -> f b) -> t a -> f (t b)
forall (f :: * -> *) a b.
Applicative f =>
(a -> f b) -> Maybe a -> f (Maybe b)
traverse (String -> Int -> Value -> Parser Text
textWithMaxLength String
"objectives" Int
1000))
      Parser
  (Maybe Text
   -> Maybe Text
   -> Maybe DoNotList
   -> Maybe [Reference]
   -> Body CIP119)
-> Parser (Maybe Text)
-> Parser
     (Maybe Text -> Maybe DoNotList -> Maybe [Reference] -> Body CIP119)
forall a b. Parser (a -> b) -> Parser a -> Parser b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> (Object
v Object -> Key -> Parser (Maybe Value)
forall a. FromJSON a => Object -> Key -> Parser (Maybe a)
.:? Key
"motivations" Parser (Maybe Value)
-> (Maybe Value -> Parser (Maybe Text)) -> Parser (Maybe Text)
forall a b. Parser a -> (a -> Parser b) -> Parser b
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= (Value -> Parser Text) -> Maybe Value -> Parser (Maybe Text)
forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
(a -> f b) -> t a -> f (t b)
forall (f :: * -> *) a b.
Applicative f =>
(a -> f b) -> Maybe a -> f (Maybe b)
traverse (String -> Int -> Value -> Parser Text
textWithMaxLength String
"motivations" Int
1000))
      Parser
  (Maybe Text -> Maybe DoNotList -> Maybe [Reference] -> Body CIP119)
-> Parser (Maybe Text)
-> Parser (Maybe DoNotList -> Maybe [Reference] -> Body CIP119)
forall a b. Parser (a -> b) -> Parser a -> Parser b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> (Object
v Object -> Key -> Parser (Maybe Value)
forall a. FromJSON a => Object -> Key -> Parser (Maybe a)
.:? Key
"qualifications" Parser (Maybe Value)
-> (Maybe Value -> Parser (Maybe Text)) -> Parser (Maybe Text)
forall a b. Parser a -> (a -> Parser b) -> Parser b
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= (Value -> Parser Text) -> Maybe Value -> Parser (Maybe Text)
forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
(a -> f b) -> t a -> f (t b)
forall (f :: * -> *) a b.
Applicative f =>
(a -> f b) -> Maybe a -> f (Maybe b)
traverse (String -> Int -> Value -> Parser Text
textWithMaxLength String
"qualifications" Int
1000))
      Parser (Maybe DoNotList -> Maybe [Reference] -> Body CIP119)
-> Parser (Maybe DoNotList)
-> Parser (Maybe [Reference] -> Body CIP119)
forall a b. Parser (a -> b) -> Parser a -> Parser b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Object
v Object -> Key -> Parser (Maybe DoNotList)
forall a. FromJSON a => Object -> Key -> Parser (Maybe a)
.:? Key
"doNotList"
      Parser (Maybe [Reference] -> Body CIP119)
-> Parser (Maybe [Reference]) -> Parser (Body CIP119)
forall a b. Parser (a -> b) -> Parser a -> Parser b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Object
v Object -> Key -> Parser (Maybe [Reference])
forall a. FromJSON a => Object -> Key -> Parser (Maybe a)
.:? Key
"references"

-- Profile picture
data ImageObject = ImageObject
  { ImageObject -> Text
contentUrl :: Text -- Base64 encoded image or URL
  , ImageObject -> Maybe Text
sha256 :: Maybe Text -- Only present for URL images
  }
  deriving (Int -> ImageObject -> ShowS
[ImageObject] -> ShowS
ImageObject -> String
(Int -> ImageObject -> ShowS)
-> (ImageObject -> String)
-> ([ImageObject] -> ShowS)
-> Show ImageObject
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> ImageObject -> ShowS
showsPrec :: Int -> ImageObject -> ShowS
$cshow :: ImageObject -> String
show :: ImageObject -> String
$cshowList :: [ImageObject] -> ShowS
showList :: [ImageObject] -> ShowS
Show, (forall x. ImageObject -> Rep ImageObject x)
-> (forall x. Rep ImageObject x -> ImageObject)
-> Generic ImageObject
forall x. Rep ImageObject x -> ImageObject
forall x. ImageObject -> Rep ImageObject x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. ImageObject -> Rep ImageObject x
from :: forall x. ImageObject -> Rep ImageObject x
$cto :: forall x. Rep ImageObject x -> ImageObject
to :: forall x. Rep ImageObject x -> ImageObject
Generic)

instance FromJSON ImageObject where
  parseJSON :: Aeson.Value -> Parser ImageObject
  parseJSON :: Value -> Parser ImageObject
parseJSON = String
-> (Object -> Parser ImageObject) -> Value -> Parser ImageObject
forall a. String -> (Object -> Parser a) -> Value -> Parser a
withObject String
"ImageObject" ((Object -> Parser ImageObject) -> Value -> Parser ImageObject)
-> (Object -> Parser ImageObject) -> Value -> Parser ImageObject
forall a b. (a -> b) -> a -> b
$ \Object
v ->
    Text -> Maybe Text -> ImageObject
ImageObject
      (Text -> Maybe Text -> ImageObject)
-> Parser Text -> Parser (Maybe Text -> ImageObject)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Object
v Object -> Key -> Parser Text
forall a. FromJSON a => Object -> Key -> Parser a
.: Key
"contentUrl"
      Parser (Maybe Text -> ImageObject)
-> Parser (Maybe Text) -> Parser ImageObject
forall a b. Parser (a -> b) -> Parser a -> Parser b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Object
v Object -> Key -> Parser (Maybe Text)
forall a. FromJSON a => Object -> Key -> Parser (Maybe a)
.:? Key
"sha256"

-- DoNotList Enum
data DoNotList = DoNotListTrue | DoNotListFalse
  deriving (Int -> DoNotList -> ShowS
[DoNotList] -> ShowS
DoNotList -> String
(Int -> DoNotList -> ShowS)
-> (DoNotList -> String)
-> ([DoNotList] -> ShowS)
-> Show DoNotList
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> DoNotList -> ShowS
showsPrec :: Int -> DoNotList -> ShowS
$cshow :: DoNotList -> String
show :: DoNotList -> String
$cshowList :: [DoNotList] -> ShowS
showList :: [DoNotList] -> ShowS
Show, (forall x. DoNotList -> Rep DoNotList x)
-> (forall x. Rep DoNotList x -> DoNotList) -> Generic DoNotList
forall x. Rep DoNotList x -> DoNotList
forall x. DoNotList -> Rep DoNotList x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. DoNotList -> Rep DoNotList x
from :: forall x. DoNotList -> Rep DoNotList x
$cto :: forall x. Rep DoNotList x -> DoNotList
to :: forall x. Rep DoNotList x -> DoNotList
Generic)

instance FromJSON DoNotList where
  parseJSON :: Aeson.Value -> Parser DoNotList
  parseJSON :: Value -> Parser DoNotList
parseJSON = String -> (Text -> Parser DoNotList) -> Value -> Parser DoNotList
forall a. String -> (Text -> Parser a) -> Value -> Parser a
Aeson.withText String
"DoNotList" ((Text -> Parser DoNotList) -> Value -> Parser DoNotList)
-> (Text -> Parser DoNotList) -> Value -> Parser DoNotList
forall a b. (a -> b) -> a -> b
$
    \case
      Text
"true" -> DoNotList -> Parser DoNotList
forall a. a -> Parser a
forall (m :: * -> *) a. Monad m => a -> m a
return DoNotList
DoNotListTrue
      Text
"false" -> DoNotList -> Parser DoNotList
forall a. a -> Parser a
forall (m :: * -> *) a. Monad m => a -> m a
return DoNotList
DoNotListFalse
      Text
_ -> String -> Parser DoNotList
forall a. String -> Parser a
forall (m :: * -> *) a. MonadFail m => String -> m a
fail String
"Invalid doNotList value, must be one of: true, false"

-- Reference type
data Reference = Reference
  { Reference -> ReferenceType
refType :: ReferenceType
  , Reference -> Text
label :: Text
  , Reference -> Text
uri :: Text
  }
  deriving (Int -> Reference -> ShowS
[Reference] -> ShowS
Reference -> String
(Int -> Reference -> ShowS)
-> (Reference -> String)
-> ([Reference] -> ShowS)
-> Show Reference
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> Reference -> ShowS
showsPrec :: Int -> Reference -> ShowS
$cshow :: Reference -> String
show :: Reference -> String
$cshowList :: [Reference] -> ShowS
showList :: [Reference] -> ShowS
Show, (forall x. Reference -> Rep Reference x)
-> (forall x. Rep Reference x -> Reference) -> Generic Reference
forall x. Rep Reference x -> Reference
forall x. Reference -> Rep Reference x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. Reference -> Rep Reference x
from :: forall x. Reference -> Rep Reference x
$cto :: forall x. Rep Reference x -> Reference
to :: forall x. Rep Reference x -> Reference
Generic)

instance FromJSON Reference where
  parseJSON :: Aeson.Value -> Parser Reference
  parseJSON :: Value -> Parser Reference
parseJSON = String -> (Object -> Parser Reference) -> Value -> Parser Reference
forall a. String -> (Object -> Parser a) -> Value -> Parser a
withObject String
"Reference" ((Object -> Parser Reference) -> Value -> Parser Reference)
-> (Object -> Parser Reference) -> Value -> Parser Reference
forall a b. (a -> b) -> a -> b
$ \Object
v ->
    ReferenceType -> Text -> Text -> Reference
Reference
      (ReferenceType -> Text -> Text -> Reference)
-> Parser ReferenceType -> Parser (Text -> Text -> Reference)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Object
v Object -> Key -> Parser ReferenceType
forall a. FromJSON a => Object -> Key -> Parser a
.: Key
"@type"
      Parser (Text -> Text -> Reference)
-> Parser Text -> Parser (Text -> Reference)
forall a b. Parser (a -> b) -> Parser a -> Parser b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Object
v Object -> Key -> Parser Text
forall a. FromJSON a => Object -> Key -> Parser a
.: Key
"label"
      Parser (Text -> Reference) -> Parser Text -> Parser Reference
forall a b. Parser (a -> b) -> Parser a -> Parser b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Object
v Object -> Key -> Parser Text
forall a. FromJSON a => Object -> Key -> Parser a
.: Key
"uri"

-- ReferenceType Enum
data ReferenceType = GovernanceMetadata | Other | Link | Identity
  deriving (Int -> ReferenceType -> ShowS
[ReferenceType] -> ShowS
ReferenceType -> String
(Int -> ReferenceType -> ShowS)
-> (ReferenceType -> String)
-> ([ReferenceType] -> ShowS)
-> Show ReferenceType
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> ReferenceType -> ShowS
showsPrec :: Int -> ReferenceType -> ShowS
$cshow :: ReferenceType -> String
show :: ReferenceType -> String
$cshowList :: [ReferenceType] -> ShowS
showList :: [ReferenceType] -> ShowS
Show, (forall x. ReferenceType -> Rep ReferenceType x)
-> (forall x. Rep ReferenceType x -> ReferenceType)
-> Generic ReferenceType
forall x. Rep ReferenceType x -> ReferenceType
forall x. ReferenceType -> Rep ReferenceType x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. ReferenceType -> Rep ReferenceType x
from :: forall x. ReferenceType -> Rep ReferenceType x
$cto :: forall x. Rep ReferenceType x -> ReferenceType
to :: forall x. Rep ReferenceType x -> ReferenceType
Generic)

instance FromJSON ReferenceType where
  parseJSON :: Aeson.Value -> Parser ReferenceType
  parseJSON :: Value -> Parser ReferenceType
parseJSON = String
-> (Text -> Parser ReferenceType) -> Value -> Parser ReferenceType
forall a. String -> (Text -> Parser a) -> Value -> Parser a
Aeson.withText String
"ReferenceType" ((Text -> Parser ReferenceType) -> Value -> Parser ReferenceType)
-> (Text -> Parser ReferenceType) -> Value -> Parser ReferenceType
forall a b. (a -> b) -> a -> b
$
    \case
      Text
"GovernanceMetadata" -> ReferenceType -> Parser ReferenceType
forall a. a -> Parser a
forall (m :: * -> *) a. Monad m => a -> m a
return ReferenceType
GovernanceMetadata
      Text
"Other" -> ReferenceType -> Parser ReferenceType
forall a. a -> Parser a
forall (m :: * -> *) a. Monad m => a -> m a
return ReferenceType
Other
      Text
"Link" -> ReferenceType -> Parser ReferenceType
forall a. a -> Parser a
forall (m :: * -> *) a. Monad m => a -> m a
return ReferenceType
Link
      Text
"Identity" -> ReferenceType -> Parser ReferenceType
forall a. a -> Parser a
forall (m :: * -> *) a. Monad m => a -> m a
return ReferenceType
Identity
      Text
_ ->
        String -> Parser ReferenceType
forall a. String -> Parser a
forall (m :: * -> *) a. MonadFail m => String -> m a
fail String
"Invalid reference type, must be one of: GovernanceMetadata, Other, Link, Identity"

-- We don't need to validate Authors because it is optional in CIP-119
data instance Authors CIP119 = Absent