diff --git a/CHANGELOG.md b/CHANGELOG.md index 64af8aa..5d7630c 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -8,6 +8,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## [0.6.2.2] - Added JSON instances for `ZcashNet` +- Added JSON instances for `Transaction` - Added `ValidAddress` ## [0.6.2.1] diff --git a/src/ZcashHaskell/Types.hs b/src/ZcashHaskell/Types.hs index d6bfd2e..9884b7f 100644 --- a/src/ZcashHaskell/Types.hs +++ b/src/ZcashHaskell/Types.hs @@ -38,6 +38,7 @@ import Data.Maybe (fromJust, fromMaybe) import Data.Structured import qualified Data.Text as T import qualified Data.Text.Encoding as E +import qualified Data.Vector as V import Data.Word import qualified GHC.Generics as GHC import qualified Generics.SOP as SOP @@ -133,6 +134,18 @@ data Transaction = Transaction , tx_orchardBundle :: !(Maybe OrchardBundle) } deriving (Prelude.Show, Eq, Read) +instance ToJSON Transaction where + toJSON (Transaction t h c e tb sb ob) = + object + [ "txid" .= t + , "height" .= h + , "confirmations" .= c + , "expiry" .= e + , "transparent" .= tb + , "sapling" .= sb + , "orchard" .= ob + ] + -- | The transparent portion of a Zcash transaction data TransparentBundle = TransparentBundle { tb_vin :: ![H.TxIn] @@ -140,6 +153,10 @@ data TransparentBundle = TransparentBundle , tb_coinbase :: !Bool } deriving (Eq, Prelude.Show, Read) +instance ToJSON TransparentBundle where + toJSON (TransparentBundle vin vout c) = + object ["vin" .= vin, "vout" .= vout, "coinbase" .= c] + -- | Read a raw transparent bundle into the Haskell type fromRawTBundle :: RawTBundle -> Maybe TransparentBundle fromRawTBundle rtb = @@ -324,6 +341,10 @@ data SaplingBundle = SaplingBundle , sbSig :: !HexString } deriving stock (Eq, Prelude.Show, GHC.Generic, Read) +instance ToJSON SaplingBundle where + toJSON (SaplingBundle s o v sig) = + object ["spends" .= s, "outputs" .= o, "value" .= v, "sig" .= sig] + fromRawSBundle :: RawSBundle -> Maybe SaplingBundle fromRawSBundle b = if zsb_empty b @@ -355,6 +376,17 @@ data OrchardBundle = OrchardBundle , obSig :: !HexString } deriving stock (Eq, Prelude.Show, GHC.Generic, Read) +instance ToJSON OrchardBundle where + toJSON (OrchardBundle a f v an p s) = + object + [ "actions" .= a + , "flags" .= f + , "value" .= v + , "anchor" .= an + , "proof" .= p + , "sig" .= s + ] + fromRawOBundle :: RawOBundle -> Maybe OrchardBundle fromRawOBundle b = if zob_empty b @@ -377,6 +409,10 @@ data OrchardFlags = OrchardFlags deriving anyclass (Data.Structured.Show) deriving (BorshSize, ToBorsh, FromBorsh) via AsStruct OrchardFlags +instance ToJSON OrchardFlags where + toJSON (OrchardFlags s o) = + Data.Aeson.Array $ V.fromList [Data.Aeson.Bool s, Data.Aeson.Bool o] + -- | Type for the response from the `zebrad` RPC method `getinfo` data ZebraGetInfo = ZebraGetInfo { zgi_build :: !T.Text @@ -501,6 +537,17 @@ data ShieldedSpend = ShieldedSpend deriving anyclass (Data.Structured.Show) deriving (BorshSize, ToBorsh, FromBorsh) via AsStruct ShieldedSpend +instance ToJSON ShieldedSpend where + toJSON (ShieldedSpend cv a n rk p au) = + object + [ "cv" .= cv + , "anchor" .= a + , "nullifier" .= n + , "rk" .= rk + , "proof" .= p + , "spendAuthSig" .= au + ] + instance FromJSON ShieldedSpend where parseJSON = withObject "ShieldedSpend" $ \obj -> do @@ -525,6 +572,17 @@ data ShieldedOutput = ShieldedOutput deriving anyclass (Data.Structured.Show) deriving (BorshSize, ToBorsh, FromBorsh) via AsStruct ShieldedOutput +instance ToJSON ShieldedOutput where + toJSON (ShieldedOutput c cm e enc o p) = + object + [ "cv" .= c + , "cmu" .= cm + , "ephemeralKey" .= e + , "encCiphertext" .= enc + , "outCiphertext" .= o + , "proof" .= p + ] + instance FromJSON ShieldedOutput where parseJSON = withObject "ShieldedOutput" $ \obj -> do @@ -617,6 +675,19 @@ data OrchardAction = OrchardAction deriving anyclass (Data.Structured.Show) deriving (BorshSize, ToBorsh, FromBorsh) via AsStruct OrchardAction +instance ToJSON OrchardAction where + toJSON (OrchardAction n r c e en o cv a) = + object + [ "nullifier" .= n + , "rk" .= r + , "cmx" .= c + , "ephemeralKey" .= e + , "encCiphertext" .= en + , "outCiphertext" .= o + , "cv" .= cv + , "spendAuthSig" .= a + ] + instance FromJSON OrchardAction where parseJSON = withObject "OrchardAction" $ \obj -> do diff --git a/zcash-haskell.cabal b/zcash-haskell.cabal index 436bf5a..33c6140 100644 --- a/zcash-haskell.cabal +++ b/zcash-haskell.cabal @@ -59,6 +59,7 @@ library , text , haskoin-core , secp256k1-haskell >= 1.1 + , vector , utf8-string build-tool-depends: c2hs:c2hs