1+ {-# LANGUAGE BangPatterns #-}
12{-# LANGUAGE DataKinds #-}
23{-# LANGUAGE DeriveAnyClass #-}
34{-# LANGUAGE DeriveGeneric #-}
@@ -64,11 +65,18 @@ import Cardano.Ledger.MemoBytes (
6465 )
6566import Cardano.Ledger.MemoBytes.Internal (mkMemoBytesShort )
6667import qualified Codec.Serialise as Cborg (Serialise (.. ))
68+ import Control.Applicative (asum )
6769import Control.DeepSeq (NFData )
68- import Data.Aeson (ToJSON (.. ), Value (Null ))
70+ import Control.Monad ((<$!>) )
71+ import Data.Aeson (FromJSON (.. ), ToJSON (.. ), Value (Null ), object , withObject , (.:) , (.=) )
72+ import qualified Data.Aeson as Aeson
73+ import Data.Aeson.Types (Parser )
74+ import qualified Data.ByteString.Base16 as BS16
6975import Data.ByteString.Short (ShortByteString , fromShort , toShort )
7076import Data.Coerce (coerce )
7177import Data.MemPack
78+ import Data.Text.Encoding (encodeUtf8 )
79+ import qualified Data.Text.Encoding as Text (decodeUtf8 )
7280import Data.Typeable (Typeable )
7381import GHC.Generics (Generic )
7482import NoThunks.Class (NoThunks )
@@ -92,6 +100,12 @@ instance Typeable era => DecCBOR (PlutusData era) where
92100instance Typeable era => DecCBOR (Annotator (PlutusData era )) where
93101 decCBOR = pure <$> fromPlainDecoder Cborg. decode
94102
103+ instance ToJSON (PlutusData era ) where
104+ toJSON (PlutusData d) = plutusDataToJson d
105+
106+ instance FromJSON (PlutusData era ) where
107+ parseJSON v = PlutusData <$> plutusDataFromJson v
108+
95109newtype Data era = MkData (MemoBytes (PlutusData era ))
96110 deriving (Eq , Generic )
97111 deriving newtype (SafeToHash , ToCBOR , NFData , DecCBOR )
@@ -117,6 +131,56 @@ instance HashAnnotated (Data era) EraIndependentData where
117131
118132instance Typeable era => NoThunks (Data era )
119133
134+ instance ToJSON (Data era ) where
135+ toJSON = toJSON . getMemoRawType
136+
137+ instance Era era => FromJSON (Data era ) where
138+ parseJSON v = mkMemoizedEra @ era <$> parseJSON v
139+
140+ plutusDataToJson :: PV1. Data -> Aeson. Value
141+ plutusDataToJson = \ case
142+ PV1. Constr n fields ->
143+ object [" constructor" .= n, " fields" .= map plutusDataToJson fields]
144+ PV1. Map kvs ->
145+ object
146+ [ " map"
147+ .= [ object [" k" .= plutusDataToJson k, " v" .= plutusDataToJson v]
148+ | (k, v) <- kvs
149+ ]
150+ ]
151+ PV1. List elems ->
152+ object [" list" .= map plutusDataToJson elems]
153+ PV1. I n ->
154+ object [" int" .= n]
155+ PV1. B bs ->
156+ object [" bytes" .= Text. decodeUtf8 (BS16. encode bs)]
157+
158+ plutusDataFromJson :: Aeson. Value -> Parser PV1. Data
159+ plutusDataFromJson = withObject " Data" $ \ o ->
160+ asum
161+ [ do
162+ ! n <- o .: " constructor"
163+ ! fields <- o .: " fields" >>= mapM plutusDataFromJson
164+ pure $ PV1. Constr n fields
165+ , do
166+ ! kvs <-
167+ o .: " map"
168+ >>= mapM
169+ ( withObject " MapEntry" $ \ kv -> do
170+ ! k <- kv .: " k" >>= plutusDataFromJson
171+ ! v <- kv .: " v" >>= plutusDataFromJson
172+ pure (k, v)
173+ )
174+ pure $ PV1. Map kvs
175+ , PV1. List <$!> (o .: " list" >>= mapM plutusDataFromJson)
176+ , PV1. I <$!> o .: " int"
177+ , PV1. B <$!> (o .: " bytes" >>= parsePlutusByteStringData)
178+ ]
179+ where
180+ parsePlutusByteStringData t = case BS16. decode (encodeUtf8 t) of
181+ Left e -> fail $ " bytes: invalid hex: " <> e
182+ Right bs -> pure bs
183+
120184pattern Data :: forall era . Era era => PV1. Data -> Data era
121185pattern Data p <- (getMemoRawType -> PlutusData p)
122186 where
0 commit comments