2023-12-20 20:03:42 +00:00
{- Copyright 2022 - 2024 Vergara Technologies LLC
This file is part of Zcash - Haskell .
Zcash - Haskell is free software : you can redistribute it and / or modify it
under the terms of the GNU Lesser General Public License as published by the Free
Software Foundation , either version 3 of the License , or ( at your option ) any
later version .
Zcash - Haskell is distributed in the hope that it will be useful , but WITHOUT
ANY WARRANTY ; without even the implied warranty of MERCHANTABILITY or FITNESS
FOR A PARTICULAR PURPOSE . See the GNU Lesser General Public License for more
details .
You should have received a copy of the GNU Lesser General Public License along with
Zcash - Haskell . If not , see < https :// www . gnu . org / licenses />.
- }
2023-04-13 23:35:15 +00:00
{- # LANGUAGE OverloadedStrings # -}
2024-03-08 18:44:10 +00:00
{- # LANGUAGE TypeSynonymInstances # -}
2023-04-13 23:35:15 +00:00
2024-01-12 15:46:26 +00:00
import C.Zcash ( rustWrapperUADecode )
2024-03-11 20:23:29 +00:00
import Control.Exception ( throwIO )
2024-03-05 21:09:35 +00:00
import Control.Monad.IO.Class ( liftIO )
2023-08-21 14:57:45 +00:00
import Data.Aeson
2023-10-04 16:12:30 +00:00
import Data.Bool ( Bool ( True ) )
2023-04-13 23:35:15 +00:00
import qualified Data.ByteString as BS
2024-04-29 15:27:45 +00:00
import qualified Data.ByteString.Char8 as C
2024-01-16 22:15:05 +00:00
import Data.Either ( isRight )
import Data.Foldable ( sequenceA_ )
2024-02-06 19:10:06 +00:00
import Data.HexString
2024-01-12 15:46:26 +00:00
import Data.Maybe
2023-08-21 14:57:45 +00:00
import qualified Data.Text as T
2023-04-27 14:50:07 +00:00
import qualified Data.Text.Encoding as E
2023-08-21 14:57:45 +00:00
import qualified Data.Text.Lazy.Encoding as LE
import qualified Data.Text.Lazy.IO as LTIO
2024-04-02 18:11:59 +00:00
import Data.Word
import Foreign.C.Types
2023-10-04 16:12:30 +00:00
import GHC.Float.RealFracMethods ( properFractionDoubleInteger )
2024-04-02 18:11:59 +00:00
import Haskoin.Crypto.Hash ( ripemd160 )
import Haskoin.Crypto.Keys.Extended
import Haskoin.Transaction.Common
2024-09-16 18:36:49 +00:00
import Network.HTTP.Simple ( Response ( .. ) )
2024-03-27 18:22:34 +00:00
import Test.HUnit
2023-06-14 15:55:20 +00:00
import Test.Hspec
2024-03-08 18:44:10 +00:00
import Test.Hspec.QuickCheck
import Test.QuickCheck
2024-01-16 22:15:05 +00:00
import ZcashHaskell.Keys ( generateWalletSeedPhrase , getWalletSeed )
2023-06-14 15:55:20 +00:00
import ZcashHaskell.Orchard
import ZcashHaskell.Sapling
2024-04-17 14:25:46 +00:00
( decodeSaplingAddress
, decodeSaplingOutput
2024-04-16 00:58:26 +00:00
, decodeSaplingOutputEsk
2024-04-17 14:25:46 +00:00
, encodeSaplingAddress
2024-03-11 02:19:51 +00:00
, genSaplingInternalAddress
2024-03-10 12:47:26 +00:00
, genSaplingPaymentAddress
, genSaplingSpendingKey
2024-04-11 21:01:29 +00:00
, getSaplingNotePosition
, getSaplingWitness
2023-09-27 15:37:53 +00:00
, getShieldedOutputs
2023-08-22 20:05:40 +00:00
, isValidSaplingViewingKey
2023-06-14 15:55:20 +00:00
, isValidShieldedAddress
, matchSaplingAddress
2024-04-10 12:06:04 +00:00
, updateSaplingCommitmentTree
2024-04-29 15:27:45 +00:00
, updateSaplingWitness
2023-06-14 15:55:20 +00:00
)
2024-03-10 12:47:26 +00:00
import ZcashHaskell.Transparent
2023-06-14 15:55:20 +00:00
import ZcashHaskell.Types
2024-03-10 12:47:26 +00:00
( AccountId
, BlockResponse ( .. )
2024-03-05 21:09:35 +00:00
, CoinType ( .. )
2023-08-22 20:05:40 +00:00
, DecodedNote ( .. )
2023-08-21 14:57:45 +00:00
, OrchardAction ( .. )
2024-04-29 15:27:45 +00:00
, OrchardBundle ( .. )
2024-04-17 14:21:47 +00:00
, OrchardCommitmentTree ( .. )
2024-03-14 17:35:13 +00:00
, OrchardSpendingKey ( .. )
2024-04-17 14:21:47 +00:00
, OrchardWitness ( .. )
2024-03-08 18:44:10 +00:00
, Phrase ( .. )
2023-05-04 20:26:49 +00:00
, RawData ( .. )
2024-03-27 18:22:34 +00:00
, RawOutPoint ( .. )
, RawTBundle ( .. )
, RawTxIn ( .. )
, RawTxOut ( .. )
2023-08-21 14:57:45 +00:00
, RawTxResponse ( .. )
2024-03-27 18:22:34 +00:00
, RawZebraTx ( .. )
2024-09-16 18:36:49 +00:00
, RpcError ( .. )
, RpcResponse ( .. )
2024-04-17 14:25:46 +00:00
, SaplingAddress ( .. )
2024-04-16 14:43:00 +00:00
, SaplingBundle ( .. )
2024-04-11 21:01:29 +00:00
, SaplingCommitmentTree ( .. )
2024-03-15 15:11:27 +00:00
, SaplingReceiver ( .. )
2024-03-14 16:13:10 +00:00
, SaplingSpendingKey ( .. )
2024-04-29 15:27:45 +00:00
, SaplingWitness ( .. )
2024-03-14 16:13:10 +00:00
, Scope ( .. )
2024-03-11 20:23:29 +00:00
, Seed ( .. )
2023-08-23 20:20:01 +00:00
, ShieldedOutput ( .. )
2024-03-14 16:13:10 +00:00
, ToBytes ( .. )
2024-03-13 19:12:28 +00:00
, TransparentAddress ( .. )
2024-04-02 18:11:59 +00:00
, TransparentBundle ( .. )
2024-04-14 11:57:36 +00:00
, TransparentReceiver ( .. )
2024-03-13 19:12:28 +00:00
, TransparentType ( .. )
2024-01-12 15:46:26 +00:00
, UnifiedAddress ( .. )
2023-05-04 20:26:49 +00:00
, UnifiedFullViewingKey ( .. )
2024-03-12 21:03:35 +00:00
, ZcashNet ( .. )
2024-03-26 14:56:10 +00:00
, ZebraTxResponse ( .. )
2023-08-21 20:58:12 +00:00
, decodeHexText
2024-04-02 16:23:05 +00:00
, fromRawOBundle
, fromRawSBundle
2024-03-27 18:22:34 +00:00
, fromRawTBundle
2024-03-06 03:10:05 +00:00
, getValue
2023-05-04 20:26:49 +00:00
)
2023-06-14 15:55:20 +00:00
import ZcashHaskell.Utils
2023-04-13 23:35:15 +00:00
2024-03-10 12:47:26 +00:00
m2bs :: Maybe BS . ByteString -> BS . ByteString
m2bs x = fromMaybe " " x
2024-03-05 22:01:17 +00:00
2023-04-13 23:35:15 +00:00
main :: IO ()
main = do
hspec $ do
2023-06-14 14:55:52 +00:00
describe " Bech32 " $ do
2024-03-04 17:59:07 +00:00
let s = " abc14w46h2at4w46h2at4w46h2at4w46h2at958ngu "
2023-06-14 14:55:52 +00:00
let decodedString = decodeBech32 s
2024-03-04 17:59:07 +00:00
it " hrp matches " $ do hrp decodedString ` shouldBe ` " abc "
xit " data matches " $ do
2023-06-14 14:55:52 +00:00
bytes decodedString ` shouldBe ` BS . pack ( [ 0x00 , 0x01 , 0x02 ] :: [ Word8 ] )
2024-03-04 17:59:07 +00:00
it " encoding works " $ do
encodeBech32m " abc " ( bytes decodedString ) ` shouldBe `
E . decodeUtf8Lenient s
2023-04-13 23:35:15 +00:00
describe " F4Jumble " $ do
it " jumble a string " $ do
let input =
[ 0x5d
, 0x7a
, 0x8f
, 0x73
, 0x9a
, 0x2d
, 0x9e
, 0x94
, 0x5b
, 0x0c
, 0xe1
, 0x52
, 0xa8
, 0x04
, 0x9e
, 0x29
, 0x4c
, 0x4d
, 0x6e
, 0x66
, 0xb1
, 0x64
, 0x93
, 0x9d
, 0xaf
, 0xfa
, 0x2e
, 0xf6
, 0xee
, 0x69
, 0x21
, 0x48
, 0x1c
, 0xdd
, 0x86
, 0xb3
, 0xcc
, 0x43
, 0x18
, 0xd9
, 0x61
, 0x4f
, 0xc8
, 0x20
, 0x90
, 0x5d
, 0x04
, 0x2b
] :: [ Word8 ]
let out =
[ 0x03
, 0x04
, 0xd0
, 0x29
, 0x14
, 0x1b
, 0x99
, 0x5d
, 0xa5
, 0x38
, 0x7c
, 0x12
, 0x59
, 0x70
, 0x67
, 0x35
, 0x04
, 0xd6
, 0xc7
, 0x64
, 0xd9
, 0x1e
, 0xa6
, 0xc0
, 0x82
, 0x12
, 0x37
, 0x70
, 0xc7
, 0x13
, 0x9c
, 0xcd
, 0x88
, 0xee
, 0x27
, 0x36
, 0x8c
, 0xd0
, 0xc0
, 0x92
, 0x1a
, 0x04
, 0x44
, 0xc8
, 0xe5
, 0x85
, 0x8d
, 0x22
] :: [ Word8 ]
2023-04-27 14:50:07 +00:00
BS . pack out ` shouldBe ` f4Jumble ( BS . pack input )
it " unjumble a string " $ do
let input =
[ 0x5d
, 0x7a
, 0x8f
, 0x73
, 0x9a
, 0x2d
, 0x9e
, 0x94
, 0x5b
, 0x0c
, 0xe1
, 0x52
, 0xa8
, 0x04
, 0x9e
, 0x29
, 0x4c
, 0x4d
, 0x6e
, 0x66
, 0xb1
, 0x64
, 0x93
, 0x9d
, 0xaf
, 0xfa
, 0x2e
, 0xf6
, 0xee
, 0x69
, 0x21
, 0x48
, 0x1c
, 0xdd
, 0x86
, 0xb3
, 0xcc
, 0x43
, 0x18
, 0xd9
, 0x61
, 0x4f
, 0xc8
, 0x20
, 0x90
, 0x5d
, 0x04
, 0x2b
] :: [ Word8 ]
let out =
[ 0x03
, 0x04
, 0xd0
, 0x29
, 0x14
, 0x1b
, 0x99
, 0x5d
, 0xa5
, 0x38
, 0x7c
, 0x12
, 0x59
, 0x70
, 0x67
, 0x35
, 0x04
, 0xd6
, 0xc7
, 0x64
, 0xd9
, 0x1e
, 0xa6
, 0xc0
, 0x82
, 0x12
, 0x37
, 0x70
, 0xc7
, 0x13
, 0x9c
, 0xcd
, 0x88
, 0xee
, 0x27
, 0x36
, 0x8c
, 0xd0
, 0xc0
, 0x92
, 0x1a
, 0x04
, 0x44
, 0xc8
, 0xe5
, 0x85
, 0x8d
, 0x22
] :: [ Word8 ]
f4UnJumble ( BS . pack out ) ` shouldBe ` BS . pack input
2023-08-21 14:57:45 +00:00
describe " JSON parsing " $ do
it " block response " $ do
j <- LTIO . readFile " block.json "
let p = eitherDecode $ LE . encodeUtf8 j :: Either String BlockResponse
case p of
Left s -> s ` shouldBe ` " "
Right x -> bl_height x ` shouldBe ` 2196277
it " raw transaction response " $ do
j <- LTIO . readFile " tx.json "
let t = eitherDecode $ LE . encodeUtf8 j :: Either String RawTxResponse
case t of
Left s -> s ` shouldBe ` " "
Right x ->
2024-02-06 19:10:06 +00:00
toText ( rt_id x ) ` shouldBe `
2023-08-21 14:57:45 +00:00
" 5242b51f22a7d6fe9dee237137271cde704d306a5fff6a862bffaebb6f0e7e56 "
2024-01-16 22:15:05 +00:00
describe " Seeds " $ do
it " generate seed phrase " $ do
s <- generateWalletSeedPhrase
2024-03-14 16:13:10 +00:00
BS . length ( getBytes s ) ` shouldNotBe ` 0
2024-01-16 22:15:05 +00:00
it " get seed from phrase " $ do
s <- generateWalletSeedPhrase
let x = getWalletSeed s
let result =
case x of
Nothing -> False
Just s' -> True
result ` shouldBe ` True
2023-06-14 14:55:52 +00:00
describe " Sapling address " $ do
it " succeeds with valid address " $ do
let sa =
" zs17faa6l5ma55s55exq9rnr32tu0wl8nmqg7xp3e6tz0m5ajn2a6yxlc09t03mqdmvyphavvf3sl8 "
isValidShieldedAddress sa ` shouldBe ` True
it " fails with invalid address " $ do
let sa =
" zs17faa6l5ma55s55exq9rnr32tu0wl8nmqg7xp3e6tz0m5ajn2a6yxlc09t03mqdmvyphavvffake "
isValidShieldedAddress sa ` shouldBe ` False
describe " Decode Sapling VK " $ do
let vk =
" zxviews1qdjagrrpqqqqpq8es75mlu6rref0qyrstchf8dxzeygtsejwfqu8ckhwl2qj5m8am7lmupxk3vkvdjm8pawjpmesjfapvsqw96pa46c2z0kk7letrxf7mkltwz54fwpxc7kc79mm5kce3rwn5ssl009zwsra2spppwgrx25s9k5hq65f69l4jz2tjmqgy0pl49qmtaj3nudk6wglwe2hpa327hydlchtyq9av6wjd6hu68e04ahwk9a9n2kt0kj3nj99nue65awtu5cwwcpjs "
let sa =
" zs1g2ne5w2r8kvalwzngsk3kfzppx3qcx5560pnfmw9rj5xfd3zfg9dkm7hyxnfyhc423fev5wuue4 "
2023-06-14 15:55:20 +00:00
let sa' =
" zs17faa6l5ma55s55exq9rnr32tu0wl8nmqg7xp3e6tz0m5ajn2a6yxlc09t03mqdmvyphavvf3sl8 "
2023-06-14 14:55:52 +00:00
let rawKey = decodeBech32 vk
2023-06-14 15:55:20 +00:00
let rawSa = decodeBech32 sa
let rawSa' = decodeBech32 sa'
2023-06-14 14:55:52 +00:00
it " is mainnet " $ do hrp rawKey ` shouldBe ` " zxviews "
2023-06-15 00:09:43 +00:00
it " is valid Sapling extended full viewing key " $ do
2023-09-28 19:23:42 +00:00
isValidSaplingViewingKey vk ` shouldBe ` True
2023-06-14 15:55:20 +00:00
it " matches the right Sapling address " $ do
matchSaplingAddress ( bytes rawKey ) ( bytes rawSa ) ` shouldBe ` True
it " doesn't match the wrong Sapling address " $ do
matchSaplingAddress ( bytes rawKey ) ( bytes rawSa' ) ` shouldBe ` False
2023-06-14 14:55:52 +00:00
describe " Decode invalid Sapling VK " $ do
let vk =
" zxviews1qdjagrrpqqqqpq8es75mlu6rref0qyrstchf8dxzeygtsejwfqu8ckhwl2qj5m8am7lmupxk3vkvdjm8pawjpmesjfapvsqw96pa46c2z0kk7letrxf7mkltwz54fwpxc7kc79mm5kce3rwn5ssl009zwsra2spppwgrx25s9k5hq65f69l4jz2tjmqgy0pl49qmtaj3nudk6wglwe2hpa327hydlchtyq9av6wjd6hu68e04ahwk9a9n2kt0kj3nj99nue65awtu5cwwfake "
let rawKey = decodeBech32 vk
it " is not mainnet " $ do hrp rawKey ` shouldBe ` " fail "
2023-04-13 23:35:15 +00:00
describe " Unified address " $ do
it " succeeds with correct UA " $ do
let ua =
" u1salpdyefywvsg2dlmxg9589yznh0h9v6qjr478k80amtkqkws5pr408lxt2953dpprvu06mahxt99cv65fgsm7sw8hlchplfg5pl89ur "
2024-01-12 15:46:26 +00:00
isJust ( isValidUnifiedAddress ua ) ` shouldBe ` True
2023-04-13 23:35:15 +00:00
it " fails with incorrect UA " $ do
let ua =
" u1salpdyefbreakingtheaddressh0h9v6qjr478k80amtkqkws5pr408lxt2953dpprvu06mahxt99cv65fgsm7sw8hlchplfg5pl89ur "
2024-01-12 15:46:26 +00:00
isValidUnifiedAddress ua ` shouldBe ` Nothing
2024-03-04 17:59:07 +00:00
it " encodes UA correctly " $ do
let ua =
" u1salpdyefywvsg2dlmxg9589yznh0h9v6qjr478k80amtkqkws5pr408lxt2953dpprvu06mahxt99cv65fgsm7sw8hlchplfg5pl89ur "
( encodeUnifiedAddress <$> isValidUnifiedAddress ua ) ` shouldBe `
Just ( E . decodeUtf8Lenient ua )
2023-05-04 14:23:05 +00:00
describe " Decode UVK from YWallet " $ do
let uvk =
" uview1u833rp8yykd7h4druwht6xp6k8krle45fx8hqsw6vzw63n24atxpcatws82z092kryazuu6d7rayyut8m36wm4wpjy2z8r9hj48fx5pf49gw4sjrq8503qpz3vqj5hg0vg9vsqeasg5qjuyh94uyfm7v76udqcm2m0wfc25hcyqswcn56xxduq3xkgxkr0l73cjy88fdvf90eq5fda9g6x7yv7d0uckpevxg6540wc76xrc4axxvlt03ptaa2a0rektglmdy68656f3uzcdgqqyu0t7wk5cvwghyyvgqc0rp3vgu5ye4nd236ml57rjh083a2755qemf6dk6pw0qrnfm7246s8eg2hhzkzpf9h73chhng7xhmyem2sjh8rs2m9nhfcslsgenm "
let res = decodeUfvk uvk
it " is mainnet " $ do maybe 0 net res ` shouldBe ` 1
it " has Orchard key " $ do BS . length ( maybe " " o_key res ) ` shouldBe ` 96
it " has Sapling key " $ do BS . length ( maybe " " s_key res ) ` shouldBe ` 128
it " does not have Transparent key " $ do
BS . length ( maybe " " t_key res ) ` shouldBe ` 1
describe " Decode bad UVK " $ do
it " should fail " $ do
let fakeUvk =
" uview1u83changinga987bundchofch4ract3r5x8hqsw6vzw63n24atxpcatws82z092kryazuu6d7rayyut8m36wm4wpjy2z8r9hj48fx5pf49gw4sjrq8503qpz3vqj5hg0vg9vsqeasg5qjuyh94uyfm7v76udqcm2m0wfc25hcyqswcn56xxduq3xkgxkr0l73cjy88fdvf90eq5fda9g6x7yv7d0uckpevxg6540wc76xrc4axxvlt03ptaa2a0rektglmdy68656f3uzcdgqqyu0t7wk5cvwghyyvgqc0rp3vgu5ye4nd236ml57rjh083a2755qemf6dk6pw0qrnfm7246s8eg2hhzkzpf9h73chhng7xhmyem2sjh8rs2m9nhfcslsgenm "
decodeUfvk fakeUvk ` shouldBe ` Nothing
2023-10-04 16:12:30 +00:00
describe " Check if UA and UVK match " $ do
let ua =
" u15hjz9v46azzmdept050heh8795qxzwy2pykg097lg69jpk4qzah90cj2q4amq0c07gta60x8qgw00qewcy3hg9kv9h6zjkh3jc66vr40u6uu2dxmqkqhypud95vm0gq7y5ga7c8psdqgthsrwvgd676a2pavpcd4euwwapgackxa3qhvga0wnl0k6vncskxlq94vqwjd7zepy3qd5jh "
let ua' =
" u17n7hpwaujyq7ux8f9jpyymtnk5urw7pyrf60smp5mawy7jgz325hfvz3jn3zsfya8yxryf9q7ldk8nu8df0emra5wne28zq9d9nm2pu4x6qwjha565av9aze0xgujgslz74ufkj0c0cylqwjyrh9msjfh7jzal6d3qzrnhkkqy3pqm8j63y07jxj7txqeac982778rmt64f32aum94x "
let uvk =
" uview1u833rp8yykd7h4druwht6xp6k8krle45fx8hqsw6vzw63n24atxpcatws82z092kryazuu6d7rayyut8m36wm4wpjy2z8r9hj48fx5pf49gw4sjrq8503qpz3vqj5hg0vg9vsqeasg5qjuyh94uyfm7v76udqcm2m0wfc25hcyqswcn56xxduq3xkgxkr0l73cjy88fdvf90eq5fda9g6x7yv7d0uckpevxg6540wc76xrc4axxvlt03ptaa2a0rektglmdy68656f3uzcdgqqyu0t7wk5cvwghyyvgqc0rp3vgu5ye4nd236ml57rjh083a2755qemf6dk6pw0qrnfm7246s8eg2hhzkzpf9h73chhng7xhmyem2sjh8rs2m9nhfcslsgenm "
it " succeeds with correct address " $ do
matchOrchardAddress uvk ua ` shouldBe ` True
it " fails with wrong address " $ do
matchOrchardAddress uvk ua' ` shouldBe ` False
2023-08-21 20:58:12 +00:00
describe " Decode Sapling tx " $ do
let svk =
" zxviews1qvapd723qqqqpqq09ldgykvyusthmkky2w062esx5xg3nz4m29qxcvndyx6grrhrdepu4ns88sjr3u6mfp2hhwj5hfd6y24r0f64uwq65vjrmsh9mr568kenk33fcumag6djcjywkm5v295egjuk3qdd47atprs0j33nhaaqep3uqspzp5kg4mthugvug0sc3gc83atkrgmguw9g7gkvh82tugrntf66lnvyeh6ufh4j2xt0xr2r4zujtm3qvrmd3vvnulycuwqtetg2jk384 "
2023-08-23 20:20:01 +00:00
let badvk =
" zxviews1qvapd723ffakeqq09ldgykvyusthmkky2w062esx5xg3nz4m29qxcvndyx6grrhrdepu4ns88sjr3u6mfp2hhwj5hfd6y24r0f64uwq65vjrmsh9mr568kenk33fcumag6djcjywkm5v295egjuk3qdd47atprs0j33nhaaqep3uqspzp5kg4mthugvug0sc3gc83atkrgmguw9g7gkvh82tugrntf66lnvyeh6ufh4j2xt0xr2r4zujtm3qvrmd3vvnulycuwqtetg2jk384 "
let rawKey = decodeBech32 svk
let badKey = decodeBech32 badvk
let rawTx =
2024-02-06 19:10:06 +00:00
fromText
2023-08-23 20:20:01 +00:00
" 050000800a27a726b4d0d6c200000000ff8e210000000001146cc65bd6d252d09b8eb0a8ab0aab6d7a798325aefc1d3032fc6d31373a85a25a3a16b447a698f720ade1bc290a74d85574b5b20515391035a67f8d5883dc65ea3ba4a17b009d6f325d41072b3ce240270959a7ffd040e5f16c697d8148973c62ffe037fc83aded21e4c91722b52520a2395c23e9c1a896f4b0f12d32ae8e31833d9d95adae40f6ecf7aff52af184efd390a4c1aa76b5fb1cab6003b1a8a004016f385926661f56d38273ec2c3df7775210310a65fff5fa9ac5509f0784eefea28bdcc67b0ff69eef930335f3b9768529e2bfe733024492101f642f989de8cbf04dd66638e9317780bce47085079675b772664c8007e96597dba83ea9af22ddf07ff1c212983d4a902914431245357527294e69ea5616e720ef1e9215bbfa33ba108b8d07efff2bad1850525d7725c681761c9b8c844a5548afabf176863de7b4cde3901defc3e83d31086d3c6e6af9a5fcc3cfb38b52ac7de84f91df5e0587f7603773401a62eeef10cd3ccf4d927ef42402c32f32280abbeaac33e73ceda52089820a186e9a1adfea81453998c6bbaa0deb41bc4f94586bfee80bad25fc71abe7c6dd44bcb1a6929a0112c7e4f8fcadb9745bde9422b954f72954c4d22db48719de61f383d620935b647337f73d119d79fd208e1d5a92f0855447df5782cd4764ba91efa65d9e4ebaa34e2eccb7aac93a5b0efe0c7664f3cd9384b3ff706ad3019c907cdcfa084351c9f6a0bfa8c78c91272ca66ac86dd6e1d0d6ba9704ea7dc54f71a053dce91f844c1ca62b5ddfe6b53834f4a816b1b01460810d9b87517659f4915adf4b84783a60ecf3bd71569259f1ff90a91a0b314bd4c77976d7893bf42e5d6ad0f8df95eb6d6c69d41490be8e39b2452df3bebfc297d5b0fc97f081890390fb0727a96898585f0120a7da9a798f2032590553f724d8756c67c5b0d1c0d23301c4ed60fa283994fd712aab17ca6360256fd5aef0ebc48f0256e3eda5894b53981d0d46768aefdc85b48c1525b7f134dce5d4ec2d76c03c821513f1652d9671219d744bdce5e69b9a74ca0c7c837668f0d8ffffffffffff9534b3d594e1609b3bace18608750b35a066c57f85e291d194400cb351430bbbe212abba32be071e747b7310863bd5fd989855a6567a351b288144b6e9f838c6a517db94673246ef0010b65f9c0be8aca654f6f57b83d893663cfd389ab96ce50e8077fe588c16b1b5989c6cc262e6658efb9b88ac800e49e9e5999e2651b8fff28fa77071d63790df155ed8344e2581ac5205b31d4f17bd748fcf60e35a9d6048d23c94c7aca8d4e541fda497aa268df9c173af5877a5da56d8fa2a42166900c734b62e56792f6c8bed48e4f108a817e83d64d6a59e38cfdb55c0f8a89bc7507c89326266f7ac03a3941f448cb879bd792bb116d0be8876c0856a76ddec0f0c02e16f0338626013ee5f6037fc6a3c69fa291204039d04d17c11295ee3024aea8f5d381e9b7eb3f938b6f9182bf4f889f1e53e30f998b1cdd23f45cfaa20aaef058248cc2e1c487fcdf54a4bc22a68a17cb6fa7b2fbf333b99feb84643d321398b675634929602126b2fb40171e514769bf82f18c267ce9cda0c24300caa9a5a361144d3b7b9ab2243ee9811d9b2e72c8bb1d145cdfcf6b29994a969b41c47208f5dba8d6d871e490e9b970afec4d8bca40ba51825cdc78cc7cde6b6f235a4105b1d1b5e2765efd753095ce770f070b02cce3316721b9345680c146c2f428c0bbca90d5a8cd0a1c4c31cbfa8ec165ea9f9c71d2d05e3cf8bae5e779786f179c45a3cd8087d820cae812aded04f8acda9068af80ea834f79f1bd03bfd66f8a19074649a85ce877df1a621a867debb423ec0d19015b326fcf6f143aba34029c1da2fc7b099378a366c38c9609ef6a9d9e175e21b0c1ab94a84e28ee7f1a00e39cb6fb59f44e4567e9f85f8f98158263c52ec433c042397c784edb07c28d2bca036f59090e819157375d610acb1993a4107b48da13a371f5383429baee209b2c0cc150fcef79a042749668ba1f89ad24a8c746142191ed0e8fd63624a331d98d50daa84ccf9043076947cf5115b9f8787acd36000c5e72c8d783b29bb28a3e46036d0a592ce8a158ee5a7ac210be72d3a6185c13645d96a8446021b64043ab8b589a20091c152e7d5a993ba94770eea988e289e1536d0d81dbc7046ca9c6d918446bf970894f073c920006681ccf6d1a3f138519c68eba0296069e42dc60f2bcd0f17c400efe4f4e87de8606606dc4fdf31494df4d454d14a440b1d9db4265c7aa9bc8683c68cb149f2cc826427575e2af82e842199a9cb9fdc7243b3bc12f1a71c37eac5cf88ba830cb95728897fa4c177a290d6b2b3814173262da14db9b4ef39fc54f888a6ffef4221ae672fb03bc78ebef479360a682ddb12ea0369a428a6c2960ff8327e9a2f5e5d98ce1eae748db8f6a4631c789b4d751d6b99c97c149a813998d44a7b57ba06c8bcb8a6c73c6388cdcfeb1346cec8fee7bdebf2a2388d9722183eb2d2e0e183cdd092152ef640880f4514f3c5e836cc3a8249413500630aa8da85f9e3cd92bdadbb69a2bab8d71f0b3ec5832a7ddbddd67b34c33b2e12a0c8468e852e4a8f7df45657e9632088aa7c6c5048a2686019cfec33b27fc88e23759938dd55a5dff589c1c21a37da617609e9d8be37dbf9bd6e84ee160fe10268171d969e4611afe9d3482ed4b132dcdd11ee516f36d512a333da20266fd984caebf4937fdfd18ed07b4a45771cf5c8c16c6b258b289a07d136a22acc766011f366c420bafb8fc1a10e42219bede5a3d1166c525491ab60bbd1f973fd3fb2e94cea888e24
2023-09-27 15:37:53 +00:00
let x = getShieldedOutputs rawTx
describe " extract Shielded Output bytes " $ do
it " should have outputs " $ do null x ` shouldBe ` False
2023-08-23 20:20:01 +00:00
describe " succeeds with correct key " $ do
2023-09-27 15:37:53 +00:00
let a = decodeSaplingOutput ( bytes rawKey ) ( head x )
2023-08-23 20:20:01 +00:00
it " amount should match " $ do maybe 0 a_value a ` shouldBe ` 10000
it " memo should match " $ do
2024-04-29 15:27:45 +00:00
C . filter ( /= '\ NUL' ) ( maybe " " a_memo a ) ` shouldBe `
" Tx with Sapling and Orchard "
2023-08-23 20:20:01 +00:00
describe " fails with incorrect key " $ do
2023-09-27 15:37:53 +00:00
let a = decodeSaplingOutput ( bytes badKey ) ( head x )
2023-08-23 20:20:01 +00:00
it " amount should not match " $ do maybe 0 a_value a ` shouldNotBe ` 10000
it " memo should not match " $ do
maybe " " a_memo a ` shouldNotBe ` " Tx with Sapling and Orchard "
2023-05-04 20:26:49 +00:00
describe " Decode Orchard tx " $ do
let uvk =
" uview1u833rp8yykd7h4druwht6xp6k8krle45fx8hqsw6vzw63n24atxpcatws82z092kryazuu6d7rayyut8m36wm4wpjy2z8r9hj48fx5pf49gw4sjrq8503qpz3vqj5hg0vg9vsqeasg5qjuyh94uyfm7v76udqcm2m0wfc25hcyqswcn56xxduq3xkgxkr0l73cjy88fdvf90eq5fda9g6x7yv7d0uckpevxg6540wc76xrc4axxvlt03ptaa2a0rektglmdy68656f3uzcdgqqyu0t7wk5cvwghyyvgqc0rp3vgu5ye4nd236ml57rjh083a2755qemf6dk6pw0qrnfm7246s8eg2hhzkzpf9h73chhng7xhmyem2sjh8rs2m9nhfcslsgenm "
let res = decodeUfvk uvk
let a =
OrchardAction
2024-02-06 19:10:06 +00:00
( fromText
2023-05-04 20:26:49 +00:00
" 248b16d98dfa33f7ba69a0610a63b606699da76c288840b81d7691ee42764416 " )
2024-02-06 19:10:06 +00:00
( fromText
2023-05-04 20:26:49 +00:00
" 17fcc27cce560733edaf91439a8020c4a029a4e7d5893ce024d5ff4b40bbd0a9 " )
2024-02-06 19:10:06 +00:00
( fromText
2023-05-04 20:26:49 +00:00
" 34796d541864832acca43f083892e98a46c912802d5643672d3f25bea177c61c " )
2024-02-06 19:10:06 +00:00
( fromText
2023-05-04 20:26:49 +00:00
" a6d2ca10e3fc7446e372266ef45ee3dc0ba373bd378e6bf3092519a7f272bd8c " )
2024-02-06 19:10:06 +00:00
( fromText
2023-05-04 20:26:49 +00:00
" 08beafdf59110b5d045e4acc13731ef1a27bfa3a9cabe1d575640c18f18ee6697fbb132d36e982ae3eadf5f37fd35f42c2bb07def14759deab1fbe2f98dc1d5913e4a6ef388b714e2cfd6d89ba2302800e02ab5f45e0e02e3895448518cd8afd2c37bb48a66d8b988a37de9d0838d92876894a311bb9f314ba842e5c18ff7a3d8c7f0ff1a7209e2d661595db8f4a4aa267b9593258914bf63c09286eeda7c9b27ddbb4646208c0d03a8fbdc5d96633335a5a65316f5b25189bdce735bdea7e900de56d3b475ae51b7c35eb7ae79ba104baeb0a5a09d1cd8bb347ab34fb26d62ddbf024f5394710626ec0a665b9c917e65b00256db635145164a0329db7bc5358f435d573b2662adf8a6128801825ec8fb7d8aeef567d35c875ddd784fceb7620355e3f056a648b39b4b2d29a1f5e7b7c4ec5fd2b1874ff1e832b308f8644e83878d90582b9a6fd6c293e19dd3e24dbe1b4c15c96608169843d46551900a8cb787b15f0f1696b736dd4c8ebacf1e3288b14e469bdc004fa8557d6b1395700eaba59334906bb012f876e4cd7acd2157719ebd2e28bd0cd4ab4ac458f8848e1c30e729803dd47102200fe703932a15c3618862ec83b40d3aa0ec2343641bcb9afbf931ab21aa4afdbe7e51deca24283c2ccab0eef6e07aac5a4bf3a775bf7d2ddfc8d8766c3bf8e35df1435cf515d93c3b9549477bd9f53d133f05dd256fbcc0b13a63e3e7f8cce6301ab4f19c114f5af079f8c581537458e861b553218a890ea3e77fb99781c7088cd43c67c155ec611c1148721cab5fd0168e4a5ec390b506ec44145474c " )
2024-02-06 19:10:06 +00:00
( fromText
2023-05-04 20:26:49 +00:00
" 1e40d33446d9f0f0fad40f8829c1ffe860c11c3439e2c15d37c6c40282f9e933dc01798c800e6c92edb4d20478b92559510eda67f3855f68f5ab22ca31e1885c7fa9d4c9ebfb62ceb5e73267bcad0ba7 " )
2024-02-06 19:10:06 +00:00
( fromText
2023-05-04 20:26:49 +00:00
" 63d0d6e8e92691f700bf8af246dcd4ae1041b13e3969f7a9d819a06e0f9429bc " )
2024-02-06 19:10:06 +00:00
( fromText
2023-05-04 20:26:49 +00:00
" fe362be160accf2794841c244e8d80bbeb80b9bc95bb653d297a98d32bddf5a05dd5f874891d55924a83f722f75f576f63796770c31074067694cffb2cce7a2a " )
let b =
OrchardAction
2024-02-06 19:10:06 +00:00
( fromText
2023-05-04 20:26:49 +00:00
" 8921446787f1bd28fa0e4cc5c945ea7fc71165a25f40cd2a325dae0c4467d12c " )
2024-02-06 19:10:06 +00:00
( fromText
2023-05-04 20:26:49 +00:00
" 240b08b7861aa78989c68cbedd0038af9b3e3456bdc7ff582d597df571d54da2 " )
2024-02-06 19:10:06 +00:00
( fromText
2023-05-04 20:26:49 +00:00
" e1bc8ccba69ab9f429bf735417aa005cf439d27500b0d3086dbf1be764b42a36 " )
2024-02-06 19:10:06 +00:00
( fromText
2023-05-04 20:26:49 +00:00
" c89c58ef8553e7d09ba4090654edd1a8c98763c44d3dfb9dad18286c7ef363ae " )
2024-02-06 19:10:06 +00:00
( fromText
2023-05-04 20:26:49 +00:00
" 0eee1ca5a3a4959cd4b8bc277e6e633f950680c4acb978c14ad8d944a784f46771c9d666a203ca3ac693943d79dd23f8b76a734a62e81932cbe98e8c851f47a11aaef50249e53151f38f88262a4bae8cf26f5f8b2db1d165aff9b57b64713a677c167608585c038e34ca7bbe468e5f86475ccec0a4a8b9a43b56e342e77a6bd09415787c9f4a1c6f20599f57545f1ac32c3a338d7a5bb2d35456adb880cb65c1455969e10df5d94b8c74b244e7093b1a88cc10697a7c2f4d34b6eae3296e64b820573b4d52e06b4427af5b8f5d6722d3a93fd85da615fceac732976ad2c1be4150b4821c149521f5419ea0746fb132d47f593cfc8a3aab6b2b4480c12fadf21280ccd3142e7188d9e5aef3fcd8c5dc0c066dc975bead023ef7f89a486b615b146110ae68b703a8349a5fc225b26a08b2adaf36fb44c9ad1be59d7ced134eb84e3f0b4aec19b71b2d26e910628a11446b97c5e6bbf97e1befa4e04b5947f83c65161b92f58088d28e57adc2a2873e27008e29772c5803502842045cb355d1ea5a9d27c2683dcb38cb49d26af39625ba99b1342f700387b939e7ff6c129417ca8836fe1e96331e35c8bc0763879e8c17cd4535fbcb27a2785c0a47294e07cb54837bb997df34882ce0bececc6adca365c76fc7533cf0503458937dcfb6058b016dbbd399b9f0cca44cbc881016f4957b5e10daada3393d5b2a4cb15ed983506d4d264f9855ce2ef87a7d4a1fc03293a22c28a53c4455447d546813fa33008e5d2d81848825fae2f437ab9575ba99c230e78f4b23e575e7647beff0e4c4e2b0a1f7320e9460 " )
2024-02-06 19:10:06 +00:00
( fromText
2023-05-04 20:26:49 +00:00
" d727aeec27bb0f7463c6ed4f5b3f4085cfd3e7218478db0dcebfca875e025320fb64bc4062251823859e963446cadd9924c559e5f981480df5a4f036daf5a8033d4c8241e128902aa1aeaf6adc149730 " )
2024-02-06 19:10:06 +00:00
( fromText
2023-05-04 20:26:49 +00:00
" 98e72813aeb6ea05347798e35379bc881d9cf2b37d38850496ee956fbecd8eab " )
2024-02-06 19:10:06 +00:00
( fromText
2023-05-04 20:26:49 +00:00
" cb9926f519041343c957a74f2f67900ed3d250c4dbcd26b9e2addd5247b841a9fde2219d2ef8c9ae8145fecc7792ca6770830c58c95648087f3c8a0a69369402 " )
2023-09-27 15:37:53 +00:00
let decryptedNote = ( ` decryptOrchardAction ` a ) =<< res
let decryptedNote2 = ( ` decryptOrchardAction ` b ) =<< res
2023-05-04 20:26:49 +00:00
describe " First action (sender) " $ do
it " Decryption fails " $ do decryptedNote ` shouldBe ` Nothing
describe " Second action (recipient) " $ do
it " Decryption succeeds " $ do decryptedNote2 ` shouldNotBe ` Nothing
it " Tx amount is validated " $ do
( a_value <$> decryptedNote2 ) ` shouldBe ` Just 3000
it " Memo is validated " $ do
let msg = maybe " " a_memo decryptedNote2
msg ` shouldBe `
" Hello World! \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL \ NUL "
2024-03-14 16:13:10 +00:00
describe " Wallet seed phrase: " $ do
2024-03-11 20:23:29 +00:00
prop " Generated phrases are valid " $ again prop_PhraseLength
prop " Derived seeds are valid " $ again prop_SeedLength
before getSeed $
2024-03-14 16:13:10 +00:00
describe " Optimized spending key tests: " $ do
2024-03-13 19:12:28 +00:00
it " Transparent spending keys are valid " $ \ s ->
property $ prop_TransparentSpendingKey s
it " Transparent receivers are valid " $ \ s ->
property $ prop_TransparentReceiver s
2024-03-11 20:23:29 +00:00
it " Sapling spending keys are valid " $ \ s ->
property $ prop_SaplingSpendingKey s
it " Sapling receivers are valid " $ \ s ->
property $ prop_SaplingReceiver s
2024-03-12 17:22:05 +00:00
it " Sapling receivers are distinct " $ \ s ->
2024-03-11 20:48:27 +00:00
property $ prop_SaplingRecRepeated s
2024-03-11 20:23:29 +00:00
it " Orchard spending keys are valid " $ \ s ->
property $ prop_OrchardSpendingKey s
it " Orchard receivers are valid " $ \ s ->
property $ prop_OrchardReceiver s
2024-03-12 17:22:05 +00:00
it " Orchard receivers are distinct " $ \ s ->
property $ prop_OrchardRecRepeated s
2024-03-14 16:13:10 +00:00
describe " Address tests: " $ do
2024-01-12 15:46:26 +00:00
it " Encode transparent " $ do
let ua =
" u17n7hpwaujyq7ux8f9jpyymtnk5urw7pyrf60smp5mawy7jgz325hfvz3jn3zsfya8yxryf9q7ldk8nu8df0emra5wne28zq9d9nm2pu4x6qwjha565av9aze0xgujgslz74ufkj0c0cylqwjyrh9msjfh7jzal6d3qzrnhkkqy3pqm8j63y07jxj7txqeac982778rmt64f32aum94x "
let msg =
case isValidUnifiedAddress ua of
Nothing -> " Bad UA "
2024-03-12 21:03:35 +00:00
Just u ->
2024-04-13 22:27:59 +00:00
maybe " No transparent " ( encodeTransparentReceiver ( ua_net u ) ) $
2024-03-12 21:03:35 +00:00
t_rec u
2024-01-16 22:15:05 +00:00
msg ` shouldBe ` " t1LPWuQnjCRH7JAeEErSXKixcUteLJRJjKD "
2024-03-12 21:03:35 +00:00
it " Recover UA from YWallet " $
ioProperty $ do
let p =
2024-03-14 16:13:10 +00:00
Phrase
" security expect junk hour people bind law hub between topic wink cliff spirit scissors auction idle figure option wide useful swift prison cushion round "
2024-03-12 21:03:35 +00:00
let targetUA =
isValidUnifiedAddress
" u1qsylqauvnhw8tsfe3cldcsj3mjrfqzgaf3mt8yzlkjuvsf5wzj223yvrt8q66qukfqcc80x3z0mk6ym6pm2f0hukzkp6t4wj78h85t6kfr2u9mqsfhdd73g3sc7ezy2ut3rtq5jmejatwv4xqqd6l8tt9fycer8kdw0gz6e607nkssqsc7kd7nk2yfz2hpvpqhdg39wxalpjzhe34j7 "
let s = getWalletSeed p
case s of
Nothing -> return $ expectationFailure " Failed to generate seed "
Just s' -> do
let oK = genOrchardSpendingKey s' MainNetCoin 0
2024-03-13 17:50:39 +00:00
let sK = genSaplingSpendingKey s' MainNetCoin 0
2024-03-14 21:44:18 +00:00
let tK = genTransparentPrvKey s' MainNetCoin 0
2024-03-14 16:13:10 +00:00
let oR = genOrchardReceiver 0 External =<< oK
2024-03-12 21:03:35 +00:00
let sR = genSaplingPaymentAddress 0 =<< sK
2024-03-15 15:11:27 +00:00
tR <- genTransparentReceiver 0 External =<< tK
2024-03-12 21:03:35 +00:00
let newUA = UnifiedAddress MainNet oR sR $ Just tR
return $ Just newUA ` shouldBe ` targetUA
2024-03-14 16:13:10 +00:00
it " Recover UA from Zingo: " $
2024-03-12 21:03:35 +00:00
ioProperty $ do
let p =
2024-03-14 16:13:10 +00:00
Phrase
" cloth swing left trap random tornado have great onion element until make shy dad success art tuition canvas thunder apple decade elegant struggle invest "
2024-03-12 21:03:35 +00:00
let targetUA =
isValidUnifiedAddress
" u1trd8cvc6265ywwj4mmvuznsye5ghe2dhhn3zy8kcuyg4vx3svskw9r2dedp5hu6m740vylkqc34t4w9eqkl9fyu5uyzn3af72jg235440ke6tu5cf994eq85n97x69x9824hqejmwz3d8qqthtesrd6gerjupdymldhl9xccejjwfj0dhh9mt4rw4kytp325twlutsxd20rfqhzxu3m "
let s = getWalletSeed p
case s of
Nothing -> return $ expectationFailure " Failed to generate seed "
Just s' -> do
let oK = genOrchardSpendingKey s' MainNetCoin 0
2024-03-13 17:50:39 +00:00
let sK = genSaplingSpendingKey s' MainNetCoin 0
2024-03-14 21:44:18 +00:00
let tK = genTransparentPrvKey s' MainNetCoin 0
2024-03-14 16:13:10 +00:00
let oR = genOrchardReceiver 0 External =<< oK
2024-03-12 21:03:35 +00:00
let sR = genSaplingPaymentAddress 0 =<< sK
2024-03-15 15:11:27 +00:00
tR <- genTransparentReceiver 0 External =<< tK
2024-03-12 21:03:35 +00:00
let newUA = UnifiedAddress MainNet oR sR $ Just tR
return $ Just newUA ` shouldBe ` targetUA
2024-03-15 15:11:27 +00:00
describe " Sapling Change Payment Address generation test " $ do
it " Call genSaplingInternalAddress " $ do
let sk =
[ 3
, 183
, 26
, 151
, 89
, 0
, 0
, 0
, 128
, 199
, 189
, 33
, 169
, 114
, 194
, 50
, 0
, 139
, 140
, 162
, 100
, 100
, 35
, 58
, 226
, 6
, 47
, 232
, 34
, 214
, 11
, 173
, 142
, 40
, 45
, 163
, 190
, 207
, 49
, 130
, 158
, 113
, 232
, 251
, 79
, 98
, 77
, 195
, 196
, 40
, 42
, 113
, 133
, 35
, 211
, 68
, 146
, 104
, 5
, 56
, 244
, 162
, 55
, 239
, 55
, 112
, 37
, 38
, 189
, 183
, 121
, 201
, 1
, 60
, 158
, 151
, 141
, 123
, 250
, 95
, 169
, 123
, 208
, 56
, 103
, 74
, 85
, 49
, 152
, 207
, 245
, 216
, 58
, 37
, 0
, 127
, 186
, 245
, 234
, 47
, 68
, 11
, 78
, 76
, 12
, 171
, 37
, 63
, 172
, 90
, 111
, 94
, 88
, 152
, 211
, 53
, 243
, 142
, 16
, 195
, 142
, 50
, 14
, 13
, 32
, 91
, 5
, 82
, 182
, 121
, 136
, 109
, 125
, 165
, 125
, 123
, 226
, 54
, 60
, 34
, 62
, 111
, 167
, 88
, 254
, 113
, 204
, 47
, 181
, 97
, 18
, 220
, 46
, 51
, 160
, 62
, 16
, 199
, 143
, 184
, 200
, 209
, 124
, 154
, 175
, 29
, 216
, 48
, 201
] :: [ Word8 ]
let cAdr =
[ 31
, 232
, 31
, 17
, 196
, 178
, 208
, 227
, 206
, 199
, 105
, 55
, 147
, 23
, 151
, 206
, 117
, 59
, 249
, 162
, 218
, 140
, 189
, 17
, 60
, 116
, 106
, 56
, 64
, 203
, 152
, 52
, 155
, 133
, 179
, 118
, 47
, 161
, 70
, 155
, 21
, 22
, 41
] :: [ Word8 ]
let bscAdr = SaplingReceiver $ BS . pack cAdr
let ca = genSaplingInternalAddress ( SaplingSpendingKey $ BS . pack sk )
fromMaybe ( SaplingReceiver " " ) ca ` shouldBe ` bscAdr
2024-03-26 14:56:10 +00:00
describe " Zebra response processing: " $ do
2024-03-29 20:51:48 +00:00
it " Read block time " $ do
let blkdata =
" 04000000c732575a3e94b7464c84b35935c2fca26e40d37b6f3278bda3d941877b192a0048cb59da8eeaf9f622d4537ec2a27918415f444d0bb143e8091b470a18a438c117fd96323fd1a9c775ed793154de0e8a2023b551431e89b5ce6f30ef047388f0bdbb0266fe81481f2c006046a8be3bca5b8819209d053a88184bb48753171accb807c38f46d00000fd400500b6a304cbc4e6caecc9b3a29ce42d71752bf5396944e28465e29d1bd7e7f3c680db3c4b85a1488d7c4e21a70c1cf50cfe4e7f70a4f1abb638f144afb90dfa69adfc7c981fd8792df19926da695356699ab76213094431bf6491b80572c310ab8e51c27cda39c771371dbf7adc60089ff5f9614577a92ce3a1e452d5d8280e3d970322e1fc5937c53369623d5e58e57672b48c2edc7a86f7d7de62e06668097547b782a01d3794a50f131695f7de3e4bf038b12abffd29b8eba618820e143ba0be57ccaa67f64511460027efb065c6ddff501376744c6b68ca01d884025e7f939521d230b1a46016d66ad3ab2262dbd477b38bbec234a19425b939dc0f1d868035c3ef99eee635c9dfd62235ede6d62f652fec499127a152e7be4f959a9bb7fcca9b335de98d14aee1330fe37f1ba28be26902a1cddbc3f67f2f6317093d3f278c1c0156e5319a0b35360e38719911b8012a8cc34893f05dc28a22787f3e0461836aef602110e621c8b9d78e991ccc0160deb8c8921f6fd13bd00d47a170b9d0b09ffd57e37467400c138823dce7c12027eb9f919b8d5f4072b331a042f6f5ebb814c6a903110cc97161787d1eb2716c8fb98d747abf321a0b079f3b6a1a0329337b4922a0d739886a03f0d475d41005733f26c675dd9694712d6ee07772a5e8f6b5871789ac14159beced65d3b2196725baa4ce04f059a7034ff0d7ce081e94d23e0115b9d8f0d99fa5b4f9771b4feaac881ac80f178c3575cc70858e40f53f1d0406253edba75e2bb6f40eb2ef4ece3df2b8dadbd3ac168b1743a0cfb68ba81ca4c838435002587852e81e0a0c3c77e11218df892ac0c2f343967b127fbb822712ceabc459ded7f3ca3e95ed5ddfe6cdfe5657da1b12ee47eb63af7a839cdbc1f52f51e349dbf2bd7d8529f814108723d97fcfda7563c4fbe3a24118352e4706f9f91406f11acde3a570e10a258fa6a5415f57a26988249a87e57f192d0408b6f56c2ef65d5e37597d144e8fe1014a4f552dc8c213b0a70b2ccff6747f6f1e0d598715d8cb0da37e0331c01da1f9e0505e9d1907628427d5d032a29fa0e14b75289b10c7d3109b590aec2a4debda9eabcbd3163f6df67efd92687d0c492a71d48b2995a658b34e96814e5674a62e3738efe53e0daf4bfe9d1031e45a246bd3b32c6d581b71c0b60ad711570bca3848c38ba5aed74d977a185d199db721c2677d4868e5afaa6cc2c7369898f58f93738681118d529194d41f0cb6103915d2e99422db387fb90046eae764a79dfe8733a7f68439d0f37e773d16ac7f0ba3a8ce0fd6746d038704b2a0a979659a859682581fee0be3fc50eed13e85e6b52f398d16b59f5f738c1eb289b3861d636b961d9220c1f76bf8a8be3ffd1e2472461202285aa1c5b7eac58564aaab0beedb65e1078517e031888aa3cb8843876aaf19311d5150529a10c9d9bce1538f7533aff126e518ef1ebd919f26aa3869ed1ced167cb1de6075897ad2dc461b9156922c4ee387f8e1635e95564d3964e47d39e6e82079e0220df00614ecd4fd31a5f3d13c9191fc65037ad3cd651f055cc795260f21bb0ba8acd7e3b65b5ff81d5a1b187a777c826f96637e00f8147c4bd43753fe9e0cd73564b53a0e9eab27745505ccd2e4a1a217307c66030ca115580ce6ecb9a8b043ca41bd2de15abd13838d130d3cfecd8d0e3bb6c982bf1f9cdc799c3256e2d722d3f13cd7acdb9d75d7e36483b2ae01e5dcb70db824eadd9c3955d79557d612a879fa6da1da479807640e37bf25a22091f1cf6fb5293e60e5616416fb2adb1d9892258e8ac6859978159338d3b6e2063b9d842a24d61d0616506d5088fe76025df35619febd57f92e30699a0df8731bdbad0775922bb12fb1697d9da833010400008085202f89010000000000000000000000000000000000000000000000000000000000000000ffffffff0603204c2a010cffffffff0480b2e60e000000001976a914278aff0c0f8734638ce81aaef4ab0afddd36552888ac286bee000000000017a9140c0bcca02f3cba01a5d7423ac3903d40586399eb8740787d010000000017a91471e1df05024288a00802de81e08c437859586c878738c94d010000000017a91493916098d2a161a91f3ddebab69dd5db9587b6248700000000204c2a000000000000000000000000 "
getBlockTime ( hexString blkdata ) ` shouldBe ` 1711455165
2024-04-02 16:23:05 +00:00
describe " Raw transaction from faucet " $ do
2024-03-26 14:56:10 +00:00
let h =
hexString
" 0400008085202f8900010829d200000000001976a91484ae5002305847e7176362d7c12c19c5bdbbaf8088ac0000000023392a00f02cd200000000000192331caef004cc758fb666bed1908e61daa82d5c9835c0544afd8369589d350b04a7488a9870983860779ca2e0079a286fe71f60d5c583c3427d24ff968bad3246c1c838b90f465becc1ddfea5839b730ec219d577ed182f6da8f493350b422c86943b7c8ff42de8aee0fe01f4b91c8bb204008f06f85c3dffdb622632d2d4e8b8f0c7457cfa0f4238c7ef4c8903a89559e9307c26e844747ccb9b8dd5e7e83637983746b2fec3de051312306eb8b15db4766b3ef5fe3086d53d388cf2b3b209389ff3644e47d6bfdbe2fafef1bc2311093ad0b49f4600925f55328da337e73f01f83097acd8f2aca7a85f28e75fb4efec6551e026a1ebb35c25efde455cc44002bb8cc79288ed738423432558ebb583874aa5c356abe5be794e1bfaeaf6a7eccf67e5d938751a3a351bc21d4422d2ff0f36f5b30759d79b1ef2d83618d9c1769694454002d2f2be74de3ac10d39829369c87a70e1e9769e7d5ae7c865282a04487a8ae4cf5beeecaea6a3be1c864bdd8d61df88f08a76ac49d28a3a069d2c0d02068a10e88674b39c9d03da49256d914319d267c0d1db08ee7777668e90a94c50a065977222ee620f2291f6ca3fa464fafe8fc3fedf64a836eef5a2ca16aaae5573ee082a77f046d388750fa4ce3853c846ae3f338741c7976f72db4ade4abd4211e8d335ec8c83309bc7d7140a99dfb64a29839b9acc74de4ac0949bcbec4e76be9096a45ab6ca19b165f4097e24ab92d7b58694b0897789c3cdcca2b3d4b0a9da153fafe68f940031b6548d3c37c1301faa9adcfc41c417e613c0838340e28801f72610289d7435910fd276ca243d119541e0a121d263fdda149ac40f293e6fee6d5ddc32532ad947548eb5d20a5bfea97543965fe09313f1a5a78ce51ecac9c36b54cb573780da15d197f5ffacf1fa0d2b5495057a29104d610936c1898d1058f6f7b90e614bc2e3ff56b1e75aa4708128e3782f602dbdd29ece268311965592ddd536ea63841ea953b20677e0dd911852d23b85a3382420d22cd276b216e81638540b04966210a9308e8f9fb46958c967e3c2e36ae081a95cec8865a87d85d5689f660fe6c616ebfc2dab0f6e41d3e8c2906405fb98a506d90a8e8c6201d520a0deaa65e92e91f965288128101427d58e0b1e3ad8a49526feed27f3bcc6d505591483e2e4cc4a9b678d63f3abc905f26f91083bc595b89ff0b6cc3caa9d93013127ab7b30fbe18fad6f7f380fd6d5668fb6c3fdea3771fdd3004994e5752275ff7b186f9ad95f9d7ff01263f1165de34c1ae867e8954d66186880a90d73eace4dc1b8b17c76815242342821b4fab93755c3dc24e60aafd1cd3e283a7414de3af18c61328d92e9141916b8bb816de024a5a047a66508340a3287f698a41804e297916ff04f2921a0eeb8fcc5690c7fc024f57ab1fb6c6bc9a0caf9bf9e0e9aad64ceb2634bedbda6716235e4b93b67cd07ae06fde6abd2893143b55628be83fd4b347ce407dabf28e288f99d23b031376bfc1b1552cac1557e4730b03be581a92feae7d39fa2cf1c565a6cbe59a83b64b90ef8fc73ff6f8b9562d77fae1221df8f5ddb029f12ae80c3f128b87e56f78224b875af54a2fa1434749bb2e1c7ad9331497a71015ae0fc63903f36023e7f34b97c6ec5976ba3740845e5870c85f1b2042cdca86620881e08595215332de7d5828844e9e44124e42e1c60f6821cb71640c6643b01681553c932d310632a8b21154445176eb1a9a3c87dff22508bdbe4f1500e19131a072c42ff1d106ade135722a9e37e95e7e93917378e7907aae4be92dab78b1cd5a771d6064f6e3afc26ff84943a84de7f6ca6b0ab5993d1013b061da4053d77398cbeb329a6ae16f76493f85df1164b4f1fdff69bf113c8f18274a4ce6a05dd4c1ccbacb8d2c3760210e312c3a344294b43b23d06b7ce7263d3178e4fd530ba5838dc0e517b7d6fff2a0d9c4d69105a8fdab3f0c51a219c1ec10337b7cf05f8f3b1fb0a09f600308e5c21ae6ae06d6f87a6766d29e3a34f331f520d80524d580bd54b25716b6b937534233b856e022d20e53779b3a4a3615a3d62d1824c2bfa906e7804d629cc6712a3aee8c3703e99ec807cdb2d381acf126d63b83a2ce1d8f5cb768270bf41ae5637976acbaad8a1fa52cfb7a2f012966f3d29867cf2c28e504043a09eeff91917f6e96dc35a7df124074da73a20b87c7c8e2196f344cc08bd4c2406daaf6064488b5f9983131d90141fba82b13b0b1ff60565be66d53c36df3a9b4c772bffd428b34f94060ad32c59c9c029eba5fabd7a01b4e7252406c0ce7bb93c831034b100cc71090b37a436f96ce902973e2dca9594886b602ed6142697413aa448652529fe688a2e62fa96f8031ade066bb2bdc682f0ae3a526c7ad3c5d01e243b999a58aa5f6816dcd7a0cdd49202e128b99436f71e7fb7033bf96d8e3930e39e024530ec4b7932d334e54a66bfc3630b472336b6719d5a38e6e9bed938f71fe49e0af0b20c5db5408cabb3227b1690e904ea3116ee568330f56a5a698b914570962da4d831f5f5acde9acb257d272d0cd14e3133c89307f2d1575e32b8cc1582d1e4a680d35a1a2cace6233dfb4b0a7fea26f41785e1ac6007dd20d8b6dc3bd6857fa487c52b39f86647a67931b33910b746331305199d20ecd2e4d3b454226a134240831ea5a35c1e2d603c48eea209868b839c79a9318b6fd1078bc0f2bb9b0e931b64d63fbbcbf22b41e3cf7bee5cecb3c0e7b3ae39cf736fce8645ab33becbc9586a9154e29dd88f42ec7d
2024-04-24 16:57:00 +00:00
let h1 =
hexString
" 0400008085202f89014b6ded3d2ee43e54135c04f9a305b473d7d741bbe6f383aa636e03e948705e0d01000000fdfd0000483045022100b34ca0fb34959230b95a48e9de95521dc4c013bdc0e6bd2a77a67b373fadea42022030a1b13f16993ab212d9f674b7b8dd3c6723137c183dbd41a9bbfcf66d7811c40147304402200f0bd12663a52ccb5e6211ec633932bbc7f0151ab51194038534abf88f689025022051fe62591dfa11a96095b4aeee2114c77a0d773242939f7ac2fa8e5262ff0865014c6952210231ee0c161e846bc133ad41d295f560d7e24829415afc78ead24d4b10198bb7342103b0b11f2dd10611d06cd6232233678dce736ce2b2141c62bdf0b4fe6f79d736da21029cbeda22b05352f66a338561604cbe11e8332f836385f16abf5088045c39d4dd53aefdffffff02b63500000000000017a91499a8b5b1f3d3a1a12e92dd4f3d94bee8fc34c527873362fa020000000017a914d75fe4791fcd50f2874f1b7457fca5833293b3a38700000000000000000000000000000000000000 "
2024-03-27 18:22:34 +00:00
let t = readZebraTransaction h
2024-04-24 16:57:00 +00:00
let t1 = readZebraTransaction h1
2024-04-02 18:11:59 +00:00
it " Transparent output is identified " $ do
2024-04-02 16:23:05 +00:00
case t of
Nothing -> assertFailure " Couldn't decode "
Just t' -> do
2024-04-02 18:11:59 +00:00
let a =
2024-04-03 21:16:42 +00:00
" utest13dq4u4dnf3yddw8lq2n6zdclshra6xsp8zgkc5ydyu6k20zrsscmuex46qa4vh84rgd78sqnlleapznnz7mnzx9wv0unts8pv32paj8se5ca3kves2u4a89uy6e8cf4hnarxydxh7hq2e9uu39punfmm53k5h45xn9k3dx35la8j7munh9td7774m8gkqgc4mn40t69w20uu2gtks7a "
2024-04-02 18:11:59 +00:00
let a' = isValidUnifiedAddress a
2024-04-02 16:23:05 +00:00
let tb = zt_tBundle t'
let myTb = fromRawTBundle tb
2024-04-02 18:11:59 +00:00
case a' of
Nothing -> assertFailure " Couldn't read address "
Just addr -> do
case myTb of
Nothing -> assertFailure " Couldn't read transparent bundle "
2024-04-03 21:16:42 +00:00
Just myTb' -> do
let pkHash =
BS . take 20 $
BS . drop 3 $
( \ ( TxOut v s ) -> s ) ( head ( tb_vout myTb' ) )
pkHash ` shouldBe `
2024-04-13 22:27:59 +00:00
maybe " " ( hexBytes . tr_bytes ) ( t_rec addr )
2024-04-24 16:57:00 +00:00
it " Transparent input is identified " $ do
case t1 of
Nothing -> assertFailure " Couldn't decode "
Just t1' -> do
let tb1 = zt_tBundle t1'
let txInHex =
HexString
" Km \ 237 =. \ 228 >T \ DC3 \ \ \ EOT \ 249 \ 163 \ ENQ \ 180 s \ 215 \ 215 A \ 187 \ 230 \ 243 \ 131 \ 170 cn \ ETX \ 233 Hp^ \ r "
2024-04-29 15:27:45 +00:00
toText txInHex ` shouldBe `
" 4b6ded3d2ee43e54135c04f9a305b473d7d741bbe6f383aa636e03e948705e0d "
2024-04-24 16:57:00 +00:00
it " Sapling component is read " $ do
case t of
Nothing -> assertFailure " Couldn't decode "
Just t' -> do
let sb = zt_sBundle t'
fromRawSBundle sb ` shouldNotBe ` Nothing
describe " Raw transaction with Sap spend " $ do
let h =
hexString
" 050000800a27a726b4d0d6c200000000c3c02a0000000111ac7f9600d034fec892f50600006b09ad88c990a8f3c5bffb6856beebd0ce356c5d1413c63a9a88db71c3f41dc12cd60197ee742fc75b217215e7144db48bd3fa55de211e0c8d7da70aba0efe17124b5250fc9fa095c8e50b53168142eb7ec402289a84ab762ddafb0f972fc07c61eb45249922752dfac17fd704a3b6156a6955286c04587f37fc781a9a0b28e92664dde2300c6321dd21d367c16b4c2b510e5d0a4358624e1ceb816da155e588726f783ed6bf396eaecada3d3bde7a0722419014c509a7fe264003af5388c5c8cdf2076137b26cf66383b41dea2af415f3d16767124616609b96789e2811f7bc8b36c0b746d225c0aa2c98b370fd39b2015eea43d523e5fbccc7ca127e59bc92ac8ad32d05243d278a26f07f33f45df23c3e8dd40d72af35a70068cc3f8445478c9cd3a56d3515e207a1b95c39c9d8b45e66827cf63e6018bf1012a47aa23ec0174735949f62036df3f677f92d3aa10365e2d358d92f77e9a6294c245eb8536493e8480f5215cdf7c863623727efa188fd8679f95318d0072915dc2be8e77b5778c48d3a2ea614990984c29dfaf7c582d269f0e9ffe6e3c475c99dbf5f8756c334b3c7b5954d68549c65fc2648bb389ba63397525829c48f7f32e43e866dfbc8ad86f54a867e592524f9c43b007328b78220cab4537c2d65f64c819ecc19ae09e17b3c84208cc169c2eaf8831d452dc83527a966b288aacce6f261aa8ed23e2c0613c48161c1eb0199915ee9c1f9cf0e7e5445539f5016b3ff701408b45557154a53e48998b49a2d149a67202caa6b585348b42fbeda770e084128760c742537743ba8cec4f997fe575db9cb370d89278c607a598ff06f1ece047855ea0a3d808d84272e22bcdeb2eb5bbe5754947be5d6fe42038d26f13313e039adf7e1091a901a6daa24b247b13c810eb5b50cd6040463c6bfa209a792d77eafb0f063167b11777d97ad05ca7eec1f1a45698e33f8e8b11a0ab0ad16ec10e4abba6de69255e0e00c7e712503a107012a46fcb9c5186a1fc5be96dcc279fa3dd18e69ee4a8ba75edaff105716b4751717aa818d514620ddd13a6716729417571a342dcc8a6f341d05db7614e729491095e4bcc6fbdec2908b6f74d7db81106ab2e1c0ee6217ba3cbb174232a42f2e6aba7e92eb2934dcd91c5a36eae1aac5160bf6076a39baeea84b8bad043c565eb8c4206a74b68c9342f9d7b1b31eec86bb9c5c73549313dd2cbe3bce55ecfdd952f3eb4dd5fa7c2000727b62a0faeb0fac1cf05246221c37560359c44610ee8f93cdd1179fc35fbd808152f507e790eb2140faccb2f6c9897a3a219d8752388e846c7277d82dc80850aeef2de46eb2d81563d53714d39e3553f5133abeae6c487d10664e1b10a90a5319adfa7471aa429095bd272ff4d3df227bdc6075e0cafba54201bddc44edcdfd2317f682f40a25e582273c4845b550b17724eca81e89268eafef9e98533b85bb2c54cdcb6beb4d6f2fc0459a2b36cbb43fcbab720678553fc930063c64a09445ff637c12d0ade4acdef1e19e8481a0b7c2dd968a2ceb7f50efbb76fe21f49d8829d8a26b10453626593a694586a828705c5ab02cccd60e351171aea3e1aaeda07cd960e0f5205019766ff3afe124a47f4ef16f0e671e1968e662c7974ee54872538c7019cc5396f165013f4c482d400ed4ff5fb34189c75e92d336cb25563867215dc3aa195f736e06657c9e27f1468acd580ee51ca44220be83c215c1223758a7676d376ea0d0aa74b73032b85a45f69e6f8d4ec3efb6861d5adc35f57e6112dfa7334ba6fbd64b14498a89d8596423125b6486d9208937e9aa010831edcc168be8b7abe7ac21cae4794fe5f019abe1715d5d8601b646767d396e1b7fb8ff50aa43d88a2426545270093ce80be1aaa849dd2edc0310e3cb0bc13a23108776a44e3250fe5aa89b6d62159206377e03e302e3dabff9ecd8675870c7d55e33cb915d7e73b765d1c61f9ba0d504429fe99516df0534cf6a5ad53424b9be39e4835dfb301ae5cbd9edd628f0cdb6c54bd4986a9fba65f60e833bf17b461746ffcc312d9584a55c55c42c8e760d017be56f54a4e1423648c3877f8a44e3a56c21bf2bf85550f3d8a8f040c8c6687aadb2c4d1e1613626a11d30fb25340f5f14b6a7752c5e6c7b866b10f1155360f35ddc8f07ed591fa3366948fbcde1a16c35a589457ded90b69675bad01a1fa9386e68dd2001498d41033a6effe882d9e864ea7991e0c71b3e65c158cba64014f800000000003b38927526d5fc5a1b2f16addcd4aa162272f280e977087de02ec2969f10d25ea3de9a5d3d3975b4b683897bf828be631813bd5b949ddf9c3c5b103b69aa483f5fc46485bc7a5dd51a47543f57d346e680e12d9429ef7c21cacf407656779235d205dffae23666e01d92fb18c063d1bd7cd00935f029149c7e20b3d72b1b951117f0629b1ef1e49047532a59fd8bc1817343d45e832078806eb10304b8e034fdce70464d33cf6c66e857fbda170573a7965f8eed58e6cb7edec4e9f8a666fbca0aeeca2d4d161caae23005f6e0adf6859c8f1bece409aa5d44d285a8e8e9fe86365af4e92384dce318724443e8a95cc790df47cdd3e8aa9ccf19acc5eb19b4cb517c3f63e59512c037a66312786cb6cd2bcd4480e0a21ac63a83b7b9c84d3207a6410aa51a60d15b5526e3ffb4cbb02ee9f43f7ce316ef01dd75544224481d4b8ad2a8944928e2b4432812d1b20aeae3b51808028321588952ea70afeef1709eff5a75463a2201299484ecc421c8452e1700ca9f4932b0aba6b5d46f36e80f2f0297eaf7f44a79cbd21046ca53073e
let t = readZebraTransaction h
2024-04-02 16:23:05 +00:00
it " Sapling component is read " $ do
case t of
Nothing -> assertFailure " Couldn't decode "
Just t' -> do
let sb = zt_sBundle t'
fromRawSBundle sb ` shouldNotBe ` Nothing
describe " Raw transaction with Orchard " $ do
2024-03-27 18:22:34 +00:00
let h =
hexString
2024-04-02 16:23:05 +00:00
" 050000800a27a726b4d0d6c200000000ff8e210000000001146cc65bd6d252d09b8eb0a8ab0aab6d7a798325aefc1d3032fc6d31373a85a25a3a16b447a698f720ade1bc290a74d85574b5b20515391035a67f8d5883dc65ea3ba4a17b009d6f325d41072b3ce240270959a7ffd040e5f16c697d8148973c62ffe037fc83aded21e4c91722b52520a2395c23e9c1a896f4b0f12d32ae8e31833d9d95adae40f6ecf7aff52af184efd390a4c1aa76b5fb1cab6003b1a8a004016f385926661f56d38273ec2c3df7775210310a65fff5fa9ac5509f0784eefea28bdcc67b0ff69eef930335f3b9768529e2bfe733024492101f642f989de8cbf04dd66638e9317780bce47085079675b772664c8007e96597dba83ea9af22ddf07ff1c212983d4a902914431245357527294e69ea5616e720ef1e9215bbfa33ba108b8d07efff2bad1850525d7725c681761c9b8c844a5548afabf176863de7b4cde3901defc3e83d31086d3c6e6af9a5fcc3cfb38b52ac7de84f91df5e0587f7603773401a62eeef10cd3ccf4d927ef42402c32f32280abbeaac33e73ceda52089820a186e9a1adfea81453998c6bbaa0deb41bc4f94586bfee80bad25fc71abe7c6dd44bcb1a6929a0112c7e4f8fcadb9745bde9422b954f72954c4d22db48719de61f383d620935b647337f73d119d79fd208e1d5a92f0855447df5782cd4764ba91efa65d9e4ebaa34e2eccb7aac93a5b0efe0c7664f3cd9384b3ff706ad3019c907cdcfa084351c9f6a0bfa8c78c91272ca66ac86dd6e1d0d6ba9704ea7dc54f71a053dce91f844c1ca62b5ddfe6b53834f4a816b1b01460810d9b87517659f4915adf4b84783a60ecf3bd71569259f1ff90a91a0b314bd4c77976d7893bf42e5d6ad0f8df95eb6d6c69d41490be8e39b2452df3bebfc297d5b0fc97f081890390fb0727a96898585f0120a7da9a798f2032590553f724d8756c67c5b0d1c0d23301c4ed60fa283994fd712aab17ca6360256fd5aef0ebc48f0256e3eda5894b53981d0d46768aefdc85b48c1525b7f134dce5d4ec2d76c03c821513f1652d9671219d744bdce5e69b9a74ca0c7c837668f0d8ffffffffffff9534b3d594e1609b3bace18608750b35a066c57f85e291d194400cb351430bbbe212abba32be071e747b7310863bd5fd989855a6567a351b288144b6e9f838c6a517db94673246ef0010b65f9c0be8aca654f6f57b83d893663cfd389ab96ce50e8077fe588c16b1b5989c6cc262e6658efb9b88ac800e49e9e5999e2651b8fff28fa77071d63790df155ed8344e2581ac5205b31d4f17bd748fcf60e35a9d6048d23c94c7aca8d4e541fda497aa268df9c173af5877a5da56d8fa2a42166900c734b62e56792f6c8bed48e4f108a817e83d64d6a59e38cfdb55c0f8a89bc7507c89326266f7ac03a3941f448cb879bd792bb116d0be8876c0856a76ddec0f0c02e16f0338626013ee5f6037fc6a3c69fa291204039d04d17c11295ee3024aea8f5d381e9b7eb3f938b6f9182bf4f889f1e53e30f998b1cdd23f45cfaa20aaef058248cc2e1c487fcdf54a4bc22a68a17cb6fa7b2fbf333b99feb84643d321398b675634929602126b2fb40171e514769bf82f18c267ce9cda0c24300caa9a5a361144d3b7b9ab2243ee9811d9b2e72c8bb1d145cdfcf6b29994a969b41c47208f5dba8d6d871e490e9b970afec4d8bca40ba51825cdc78cc7cde6b6f235a4105b1d1b5e2765efd753095ce770f070b02cce3316721b9345680c146c2f428c0bbca90d5a8cd0a1c4c31cbfa8ec165ea9f9c71d2d05e3cf8bae5e779786f179c45a3cd8087d820cae812aded04f8acda9068af80ea834f79f1bd03bfd66f8a19074649a85ce877df1a621a867debb423ec0d19015b326fcf6f143aba34029c1da2fc7b099378a366c38c9609ef6a9d9e175e21b0c1ab94a84e28ee7f1a00e39cb6fb59f44e4567e9f85f8f98158263c52ec433c042397c784edb07c28d2bca036f59090e819157375d610acb1993a4107b48da13a371f5383429baee209b2c0cc150fcef79a042749668ba1f89ad24a8c746142191ed0e8fd63624a331d98d50daa84ccf9043076947cf5115b9f8787acd36000c5e72c8d783b29bb28a3e46036d0a592ce8a158ee5a7ac210be72d3a6185c13645d96a8446021b64043ab8b589a20091c152e7d5a993ba94770eea988e289e1536d0d81dbc7046ca9c6d918446bf970894f073c920006681ccf6d1a3f138519c68eba0296069e42dc60f2bcd0f17c400efe4f4e87de8606606dc4fdf31494df4d454d14a440b1d9db4265c7aa9bc8683c68cb149f2cc826427575e2af82e842199a9cb9fdc7243b3bc12f1a71c37eac5cf88ba830cb95728897fa4c177a290d6b2b3814173262da14db9b4ef39fc54f888a6ffef4221ae672fb03bc78ebef479360a682ddb12ea0369a428a6c2960ff8327e9a2f5e5d98ce1eae748db8f6a4631c789b4d751d6b99c97c149a813998d44a7b57ba06c8bcb8a6c73c6388cdcfeb1346cec8fee7bdebf2a2388d9722183eb2d2e0e183cdd092152ef640880f4514f3c5e836cc3a8249413500630aa8da85f9e3cd92bdadbb69a2bab8d71f0b3ec5832a7ddbddd67b34c33b2e12a0c8468e852e4a8f7df45657e9632088aa7c6c5048a2686019cfec33b27fc88e23759938dd55a5dff589c1c21a37da617609e9d8be37dbf9bd6e84ee160fe10268171d969e4611afe9d3482ed4b132dcdd11ee516f36d512a333da20266fd984caebf4937fdfd18ed07b4a45771cf5c8c16c6b258b289a07d136a22acc766011f366c420bafb8fc1a10e42219bede5a3d1166c525491ab60bbd1f973fd3fb2e94cea888e
2024-03-27 18:22:34 +00:00
let t = readZebraTransaction h
2024-04-02 16:23:05 +00:00
it " Sapling component is read " $ do
case t of
Nothing -> assertFailure " Couldn't decode "
Just t' -> do
let sb = zt_sBundle t'
fromRawSBundle sb ` shouldNotBe ` Nothing
it " Orchard component is read " $ do
case t of
Nothing -> assertFailure " Couldn't decode "
Just t' -> do
let ob = zt_oBundle t'
fromRawOBundle ob ` shouldNotBe ` Nothing
2024-04-29 15:27:45 +00:00
it " Orchard CMX is present " $ do
case t of
Nothing -> assertFailure " Couldn't decode "
Just t' -> do
let ob = zt_oBundle t'
case fromRawOBundle ob of
Nothing -> assertFailure " Couldn't open the orchard bundle "
Just s -> toBytes ( cmx ( head ( obActions s ) ) ) ` shouldNotBe ` " "
2024-04-05 19:12:39 +00:00
describe " Raw transaction with Transparent inputs " $ do
let h =
hexString
" 0400008085202f89014b6ded3d2ee43e54135c04f9a305b473d7d741bbe6f383aa636e03e948705e0d01000000fdfd0000483045022100b34ca0fb34959230b95a48e9de95521dc4c013bdc0e6bd2a77a67b373fadea42022030a1b13f16993ab212d9f674b7b8dd3c6723137c183dbd41a9bbfcf66d7811c40147304402200f0bd12663a52ccb5e6211ec633932bbc7f0151ab51194038534abf88f689025022051fe62591dfa11a96095b4aeee2114c77a0d773242939f7ac2fa8e5262ff0865014c6952210231ee0c161e846bc133ad41d295f560d7e24829415afc78ead24d4b10198bb7342103b0b11f2dd10611d06cd6232233678dce736ce2b2141c62bdf0b4fe6f79d736da21029cbeda22b05352f66a338561604cbe11e8332f836385f16abf5088045c39d4dd53aefdffffff02b63500000000000017a91499a8b5b1f3d3a1a12e92dd4f3d94bee8fc34c527873362fa020000000017a914d75fe4791fcd50f2874f1b7457fca5833293b3a38700000000000000000000000000000000000000 "
let t = readZebraTransaction h
it " TxIn parsing " $ do
case t of
Nothing -> assertFailure " Couldn't decode "
Just t' -> do
let tb = zt_tBundle t'
show tb ` shouldNotBe ` " "
2024-04-10 12:06:04 +00:00
describe " Sapling commitment trees " $ do
let tree =
2024-04-11 21:01:29 +00:00
SaplingCommitmentTree $
2024-04-10 12:06:04 +00:00
hexString
" 01916df07670600aefa3b412a120d6b8d9a3d2ff9466a7ec770cd52d34ddb42313001000013c60b031a5e44650059fcc7101a3f551b807ab8b3a116a5a9c7fa0f3babbe735017c0d36686294ff19d59e58b6a2ac6a7ad607a804bc202c84012d8e94f233970c0128dbde5180af5304d8577376d78297130b615a327974c10881f6d876869aea05011b80b4ca60f74dfe33c78b062df73c84b8b44dab4604db16f5b61eea40134373010c96e4cc8a6a80fba0d41e4eb3070d80769104dc33fb61133b1304c15bf9e23e000107114fe4bb4cd08b47f6ae47477c182d5da9fe5c189061808c1091e9bf3b4524000001447d6b9100cddd5f80c8cf4ddee2b87eba053bd987465aec2293bd0514e68b0d015f6c95e75f4601a0a31670a7deb970fc8988c611685161d2e1629d0a1a0ebd07015f8b9205e0514fa235d75c150b87e23866b882b39786852d1ab42aab11d31a4a0117ddeb3a5f8d2f6b2d0a07f28f01ab25e03a05a9319275bb86d72fcaef6fc01501f08f39275112dd8905b854170b7f247cf2df18454d4fa94e6e4f9320cca05f24011f8322ef806eb2430dc4a7a41c1b344bea5be946efc7b4349c1c9edb14ff9d39 "
let cmu1 =
hexString
" 45e47c5df6f5c5e48aa3526e977b2d1b57eda57214e36f06128008cb17b0125f "
let cmu2 =
hexString
" 426ef44b3b22e0eeda7e4d2b62bac63966572b224e50f97ee56c9490cde4910d "
let tree2 =
hexString
" 01a47029e9b43722c57143a5d07681bff3e2315c9a28ad49d69e7c1f2f6e81ac160010000000000000012f4f72c03f8c937a94919a01a07f21165cc8394295291cb888ca91ed003810390107114fe4bb4cd08b47f6ae47477c182d5da9fe5c189061808c1091e9bf3b4524000001447d6b9100cddd5f80c8cf4ddee2b87eba053bd987465aec2293bd0514e68b0d015f6c95e75f4601a0a31670a7deb970fc8988c611685161d2e1629d0a1a0ebd07015f8b9205e0514fa235d75c150b87e23866b882b39786852d1ab42aab11d31a4a0117ddeb3a5f8d2f6b2d0a07f28f01ab25e03a05a9319275bb86d72fcaef6fc01501f08f39275112dd8905b854170b7f247cf2df18454d4fa94e6e4f9320cca05f24011f8322ef806eb2430dc4a7a41c1b344bea5be946efc7b4349c1c9edb14ff9d39 "
it " Commitment tree is updated correctly " $ do
2024-04-11 21:01:29 +00:00
let t1 = updateSaplingCommitmentTree tree cmu1
t1 ` shouldNotBe ` Nothing
it " Incremental witness is generated " $ do
2024-04-10 12:06:04 +00:00
let t1 = updateSaplingCommitmentTree tree cmu1
case t1 of
2024-04-11 21:01:29 +00:00
Nothing -> assertFailure " Failed to append node to tree "
Just t -> getSaplingWitness t ` shouldNotBe ` Nothing
it " Position of note is obtained " $ do
let p =
getSaplingNotePosition <$>
( getSaplingWitness =<< updateSaplingCommitmentTree tree cmu1 )
p ` shouldBe ` Just 129405
2024-04-17 14:21:47 +00:00
describe " Orchard commitment trees " $ do
let tree =
OrchardCommitmentTree $
hexString
" 01d5c803729654208f33d33dc68ef539ea098abc5aec215ae67c4d8aa10a14e11d01bb83047c72eb4f71813d00dee37082169546df2d7097bf7fd187ef6a93063b281f015e710ed46b53b48b12733652e150f9dcbc7e7b571cf64f294cf903864c78882f01cac32bc901f501f714a028f7ebe44c1dd8b42661be1c96730066a6fa6ede653600000000000001746e6bc066a10e7f80a9ff8993dcb25c819edd64f2ca10ac248ef7848d41450500011e6191f91b3fceb62dc881a156e1b9d2e88e09dca25093cf9c4936c8869fb41a013bf8b923e4187754e85175748d9cce4824a6787e4258977b5bfe1ba59012c032000001f3bbdc62260c4fca5c84bf3487246d4542da48eeeec8ec40c1029b6908eef83c00000000000000000000000000000000 "
let cmx =
hexString
" d5c803729654208f33d33dc68ef539ea098abc5aec215ae67c4d8aa10a14e11d "
it " Commitment tree is updated correctly " $ do
let t1 = updateOrchardCommitmentTree tree cmx
t1 ` shouldNotBe ` Nothing
it " Incremental witness is generated " $ do
let t1 = updateOrchardCommitmentTree tree cmx
case t1 of
Nothing -> assertFailure " Failed to append node to tree "
Just t -> getOrchardWitness t ` shouldNotBe ` Nothing
it " Position of note is obtained " $ do
let p =
getOrchardNotePosition <$>
( getOrchardWitness =<< updateOrchardCommitmentTree tree cmx )
p ` shouldBe ` Just 39432
2024-04-10 14:27:09 +00:00
describe " Extract Sapling Address - UA Valid " $ do
2024-04-14 11:57:36 +00:00
let sr =
getSaplingFromUA
" u14a5c4ufn9feqvxssnvscep29j5cse4gjpg0w3w5vjhafn74hg9k73xgnxqv6m255n23weggr6j97c8kdwvn4pkz7rz6my52z8248gjmr7knlw536tcurs5km7knqnzez4cywudt3q6shr553hurduvljfeqvfzgegenfjashslkz3y4ykhxel6mrjp9gsm9xk7k6kdxn9y84kccmv8l "
2024-04-10 00:23:16 +00:00
it " Extract sapling address " $ do
2024-04-14 11:57:36 +00:00
case sr of
Nothing ->
assertFailure " UA invalid or does not contain a Sapling receiver "
2024-04-10 14:27:09 +00:00
Just t -> do
2024-04-14 11:57:36 +00:00
print t
t ` shouldBe `
" zs1waxrpde36rlrjdwfhnvw030sn29lzwmvmeupd8x2uuqgypaafx7mqcy0ep8yf2xtg30n5424t60 "
2024-04-10 14:27:09 +00:00
describe " Extract Sapling Address - UA Invalid " $ do
2024-04-14 11:57:36 +00:00
let sr =
getSaplingFromUA
" u14a5c4ufn9qfevxssnvscep29j5cse4gjpg0w3w5vjhafn74hg9k73xgnxqv6m255n23weggr6j97c8kdwvn4pkz7rz6my52z8248gjmr7knlw536tcurs5km7knqnzez4cywudt3q6shr553hurduvljfeqvfzgegenfjashslkz3y4ykhxel6mrjp9gsm9xk7k6kdxn9y84kccmv8l "
2024-04-10 14:27:09 +00:00
it " Try to extract sapling address from invalid UA " $ do
2024-04-14 11:57:36 +00:00
sr ` shouldBe ` Nothing
2024-04-13 22:27:59 +00:00
describe " Decode a Transparent Address " $ do
let ta = decodeTransparentAddress " t1dMjvesbzdG41xgKaGU3HgwYJwSgbCK54e "
it " Try to decode a valid Transparent Address " $ do
print ta
ta ` shouldNotBe ` Nothing
2024-04-14 11:57:36 +00:00
it " Encode and decode should be the same " $ do
let ua =
" u17n7hpwaujyq7ux8f9jpyymtnk5urw7pyrf60smp5mawy7jgz325hfvz3jn3zsfya8yxryf9q7ldk8nu8df0emra5wne28zq9d9nm2pu4x6qwjha565av9aze0xgujgslz74ufkj0c0cylqwjyrh9msjfh7jzal6d3qzrnhkkqy3pqm8j63y07jxj7txqeac982778rmt64f32aum94x "
case isValidUnifiedAddress ua of
Nothing -> assertFailure " Bad UA "
Just u -> do
let tAdd =
maybe
" No transparent "
( encodeTransparentReceiver ( ua_net u ) ) $
t_rec u
( ta_receiver <$> decodeTransparentAddress ( E . encodeUtf8 tAdd ) ) ` shouldBe `
t_rec u
2024-04-16 18:39:56 +00:00
describe " Decode a Sapling Address (MainNet) " $ do
2024-04-17 14:25:46 +00:00
let sa =
decodeSaplingAddress
" zs1waxrpde36rlrjdwfhnvw030sn29lzwmvmeupd8x2uuqgypaafx7mqcy0ep8yf2xtg30n5424t60 "
2024-04-16 18:39:56 +00:00
it " Try to decode a valid MainNet Sapling Address " $ do
2024-04-17 14:25:46 +00:00
case sa of
2024-04-16 22:51:14 +00:00
Nothing -> assertFailure " Failed to decode MainNet SaplingAddress "
2024-04-17 14:25:46 +00:00
Just s -- Sapling address decoded succesfully
-> do
2024-04-16 22:51:14 +00:00
let sh = encodeSaplingAddress ( net_type s ) ( sa_receiver s )
2024-04-17 14:25:46 +00:00
case sh of
Nothing ->
assertFailure " Failed to encode MainNet SaplingAddress "
Just zsh -> do
print zsh
zsh ` shouldBe `
" zs1waxrpde36rlrjdwfhnvw030sn29lzwmvmeupd8x2uuqgypaafx7mqcy0ep8yf2xtg30n5424t60 "
2024-04-16 18:39:56 +00:00
describe " Decode a Sapling Address (TestNet) " $ do
2024-04-17 14:25:46 +00:00
let sa =
decodeSaplingAddress
" ztestsapling188csdsvhdny25am8ume03qr2026hdy03zpg5pq7jmmfxtxtct0e93p0rg80yfxvynqd4gwlwft5 "
2024-04-16 18:39:56 +00:00
it " Try to decode a valid TestNet Sapling Address " $ do
2024-04-16 22:51:14 +00:00
case sa of
Nothing -> assertFailure " Failed to decode TestNet SaplingAddress "
2024-04-17 14:25:46 +00:00
Just s -- Sapling address decoded succesfully
-> do
2024-04-16 22:51:14 +00:00
let sh = encodeSaplingAddress ( net_type s ) ( sa_receiver s )
2024-04-17 14:25:46 +00:00
case sh of
Nothing ->
assertFailure " Failed to encode TestNet SaplingAddress "
Just zsh -> do
print zsh
zsh ` shouldBe `
" ztestsapling188csdsvhdny25am8ume03qr2026hdy03zpg5pq7jmmfxtxtct0e93p0rg80yfxvynqd4gwlwft5 "
2024-04-16 00:58:26 +00:00
describe " Decode Sapling Output with spending key " $ do
2024-04-16 14:43:00 +00:00
let p =
Phrase
" cloth swing left trap random tornado have great onion element until make shy dad success art tuition canvas thunder apple decade elegant struggle invest "
let seed = getWalletSeed p
let sK = genSaplingSpendingKey ( fromJust seed ) MainNetCoin 0
let txHex =
hexString
" 050000800a27a726b4d0d6c20000000005bd2500000001efdca98904a8b34a0fcfefc47240249a18a530289f2ff6a15bb9885abf6e541aa6c9a851b63df5cbd7473b5b5bc5efbc4a3130c15ce18b92b87b67de2cc72846babecb9030390f0ab02d54960636633695c0c1631f9e87625b92976b12492fcb02d260bd68e7c21cc8ffaad1c3ea5182dee524a09f7b5babcd7d6d85270d6d0d3d48aa620513b632cc17eca91e237b38b1212739e8df6ddcb85c2314cd76c52e26791e2d99fd7ea468b2fb4df3e9bce602daa6a6ad8a57fcee27ce5eee3da998902b5ecf4651adaed9bfd17d0d6de3f4d8c1d391f91c571a341f105e3afd913c25012c623f274406cccda52535a0b4ab883b763d1c7405e6aac941575a965ef0b9b0114588d9d7a2be82a3eb11c662c1fc85a31e8f07fa2c2a9dcb295d5530e893b2aa43c04a508eb182257c791aa4f75d6f5d77a8fbace89666ee80b572015ae4c33b8510e88a8a338da305237d1fc5d267a4ea6914d6f9cacd1a5e158a1acd2722284ff71fd870d92143872def753e2ecde9c04c3b80b513609d47a523243508548c8873426c52eaab76b9cf2b90e63fe9c5485eddfcacac65ca811c634df22a01610b22770ba3d294f566de7e0764641985b62ce2cd71735999111bb323b14d87e482201798672881da255062dc68f912343b911154f7c96442a01be25219f0315bc78c1c3693f80e9a9cd062eee2de8a37cf073f505d936f1be9ef9a78f95e8f70ef20e0e23c2c59c37cd94cfdc5c0d0d14849aea4aa6b6a7b33a0fc57a2a91a5950ba92fec1465db65b02e36fff82d2cacb4cc9038d1a8f30559a6211c52507f2dba723d54e08e82b127cd63fad97e44292e90aa87a1e798504d0f67f242561eecc3ab40911472d75457afecaf9a026e9e0ebcd07c7e78c0bd2963674fa51d6d2c157791c5d60574047a0a4ef496f1465117ed6b9408a107cd77daa0501bb49f548b97d6eb45ace8c0620b0361031f6031af5ff53015c6755fd3c76e9e45c8694d0f38722aa9bd31987fb503a0fef5f3f97033a19212e9d549b7f7de12c2dd3f1b5db353cb40c486a0ab00ecd80d1bc6ef96ba9855bbae57c6bb9965e1ac01d4d2cccd150a44a1e511bf8f9956e7472339306f7c14d90e61e4b01d6e3b98a6b5008ce102b4646d31fc11af90d4834dd8e0005fdc8ca2310fd6cdd4180def97074fedfe645e3c9f399ca9bd282b7743d943c95e4c76a7deae192be69b80f71f7f3dd9ff5199f7c82f743030ffdd69fe88463ef6efd62d329662ab48325d4d67bed52bcdf16d1991adf5fdeadb02e81bf627d5c58d013277f1ab04fec34985917a7495d4056d47986ebcdd18c08cd9f6ba3a1487f646c1a8d99714db89d3d7708cb3455d72943a609f3db3097b7ab295316c2bcf88c73ca159e995acddcc149fd186bd82cd34f02af8e4b68ad39db8621ae92db4d41f53d2567948a423ed2a7fe38b1ff77c0b1cf46d90077bd062b3c2edb9caab921b01c546866a376d29feeaee6ff8e7583c8b4a4f631c4cb339172e5b217ee75793f7608ea6d600c680f86ce63a89a5963ec5e20ade9464f3142c0100c8ce4426b34f887b68c9658cad2dbf8a1c5da4eb7b576bab32b5af129437cd34e3c8b8d17bece85cb661ed20224539ed3eb1d61eec727deb79585f8630a807acd44978dd6ec190312d1c8dacc4cf02783136d730ab0216f7105a9f11d090c5a6e69eb726ba5e785de2f99dc7a8051250544cc661b56913715fdd31cbb5fff3f0b5000a325db631ff60ad241051511dd32e322900df8f5707a59bbe8c1ac85f4be97cfe6700a9193458fa23a70b6639f0bdfd879493520d8e4e593002f5cd9d4bb60aad67610cfb03142a5fc9cefe08cf76a23706288779cefa08ba26e33b9ca58109e0e8abf150dceec584ceabe74e3c838f86a4c3920a37d8dac148317a3c3e132ecaa551ddb7085a8702dc970b5dee5264ee1bf8bc89e92912ff1f3b4e5d10627f3e55b7f6216c0249cb2aabd1267762cad1a88b6c81bc42ac47b6f53e5598ea1dce228165f0e748c0af90eaa421813dc38a521daf83e688c298ddc0a1adac1418f04a7739a6d4f7fdfae64320d8d8107f5bacb87596b7f777a85002d9dcf66c930bfa427a6508198d8cf625279b3c6b438e098f04453d9607bb83271b2ce1f11bcb4c59f0edc4135cf4d5bade66c422c654f9dff4fa720589975d05ae7b10b1d6d2ed72c26534be10a229605f4e946c21abdfd629b1ec18e5819a1be5c89fbf446c65b39fdb32ad5cd9079beee1b73bb3b3a37c3cc10270000000000007a2aed01922521f492d80b45e7d267745f3423c1760982418b9f69390660fb12a6ec696bed9fb392633c496f576a910a0c4d5e37ad76839d951d4895f76948c72fcd580590e014c9b0b3a091ec19ab40a5d59131024055636725f98c29303bab5718006e7154379227c58d18b04938b43c8fa4fe793db395754c3270d71f90dd0fd907c39c848446f99de6efefebe414f981c29f2eb448d1d15ff314ee0c763b66dbf6917e44e18310e0fa1340069512867157552c696a3f89c909668e0698e83825b1b0d73a38a2d99531a8c053a48acdcf9fa9bafcd8ce1f3c3b784bbe23775be45176a5b0a42978008ba5c60020714ba3c0174c9a068b45081267609f7ca31e32d7367cdb0ffb88c7cb762e55b48e4edc639da5ec739a1a5ae0d7b9a16000adb66352c377e3a316a18c66f3c994c0e62b81b3ebc485e4e3438426f1a32a3a875483def774eb45e13df7a14c9ac4f9ac22bcebf3515a6dafe9aad745451708180fadcce8870302e65d90954fd9cae32e3374c8734385c6b4bc3581d997e0f20e6db537a39c8f9b5e54e0a2bcc41e26
let txHex2 =
hexString
" 0400008085202f8900000000000045b52a00e80300000000000001638ca17ebf9c8fa40eb74be6cc0f702c8a009695b0ae1debc87f4623baa2fdb3f7d7639e3fc8c696cf5ee19d3efccf50e38546de089c4d95a4a3a4a5dd53ef4465bf1d0f111e8a87f1f499ba1d7acaa523f344046ed86c1a42d412fdfb6803cf8e155df11d1beec2d11aecc2cda622b4028db0691fd61d74969a96021bec1f45855f06c8e2c1e02aed41c4549f2e4227572f873847542e1e29077269460e2885cc0a1775378a20e7b1ef40d1e358020ea3c24991ea5bc150932d538b126ea8cdbe5fef9728efedf40912b75634c4ba8288a2ab6f09ad4b8081d395bb4dc49f221011891a8b4af3cc831bf5bdf013950d6a4c4442d314f62d18913a2e18f041cac9535ca8a973e38c3e9796f4eac80d4d88a39c701b17aaf452c19410fe45188d86d91fdee3799ba7bce793c3d0bfba9139c006eb4b279b48dbed04ff75564a068d4b022ac523d40f0a4c65d955873e7498df63bbd87b2518aaac084c8bd8d44d620a07d994ee09ae8e1792d47393b6b570ae1a9122dbf7bcc1f494120d20ca0c028e7443befa6ec5956c3b0c593c6065c7ee909f90de6188e38c24e57d8f0f4cc8fa430c51bb108db782764cff55de9c6b11bbecd2493d2e0fa9f646428feef858d322258e2bc7f6072ad014d8b249567b14276280bab8f2fe6b62ead86cda2dbf1264a89d07964845acb2ac5f9187f01f3980f0edfcee5f4082ad30f0c9512766063a55974c876cfb1b2115cbd46d9d49a3929ba42f4f9ba5ab15ddb106376a24786ba6631860f1e04df72a8a9dde04fb9128d453436f34eb560f52629deded87d46f0a6355da1070f14a0ea10fcae274bbc1b3f190858eb32ef47cf4fbca4d86fabe737ca1291f40979b6cda84bb43231598363ac9fc3d9af0d74a0a0797eb0dacc6dbd2687f3c8cd92468d39915edf9e45161ed10d78e17b629c5d5c73a09ff737fb370ce80a710bc97c391936223e926563f0ba27ec983c09477e23f8c288e35c57da1ce05ab740dd2d7afc800257c17276e4b9970f08288623c506275e0b0c8d5f60aab32974c24164d1b547e756218acf68849eea30480f529c8c05e62a65c9d070285b46c4a477ca5df220c696364523cc5d6db9ca852b1eb036846b537f4b566913660ad8b83d9c72daeb45274a55032cab9a3e0b3a1e386829dd10c6ba01dbc393843d67c553d74be7969b1879bf0a2ce05f108159a0df47f279b490d5a45ca1d90ff1a61650c6ae87611746d35f8410b39f2301a1be54711d58243cbc3afa29df2a7be5565cff1cad0bd34c370c345b2f38ac7020ac79f9d6c9eeaf2c7165acade98faf18a4e1b55a4e2a18a6dd4790057008ad40c51b0967b87a8d54cde958801ef98ae4a6c9f0e94f5c02a498a9173780b5b0790c248241125fe762c4697a320f1d08d782029c4fcb34fc8580c8c9885ba8339c5693170c157d1ebc663cdccd0a4bf6e77bdc3026252696ae0317ff7a3d9c190476e4605128e50eb42d3d5d86459d6fe8c22e5482822b61f0bcbfbc28374ed93ccbe97e3af400265f02ea525a8c4853dba3d667d7502e914f99ab5062f81fe1c699663694944c8a2fe4679a6866d1d3fc07acf31041881dad5faa08385f51c5880265fe6f6bbd7961cfb9c8ceb8d1f5e1a99f7bc606585136c18d2eb3b9222576614c7092ff47d32696b50faa67c0170a2b3212a32f7bd79daa69a84fe2ef3b62081d78418d0a5902dc65d9442f1824366d8906d514ff1db6bfcb39202257e9e523cea9c311c0d4c13efc6fe6bea7dbd0c1c9ad39594ebca64586701a2384d40e62198cf379ecf21ddd8522e98a447f1c0f79e03abd232da7c8b9c39260a21097eedff86744445c7785ba0251fea0572d5ec7f78134c75fd03fc3d62d283384bb097120b47b780b4a60b5c04d53e90c9ff2e781ac9b039384fbd48d1d163c69029e8cb05d874b798c7973b3b1b1b0e04f984a252b73c848698320843e007aea2e07f40f139e24d0e497eac26727a2b9aad4f223887cd423b9fd6cf58353f0b011ea73b2a9843c25529df7b88f2357fba75353218012d1ba4b89b45d50564e9e7f16101c69c4232d2de683bd0960cc87a016dce7bb088720f8f6c092bdf2f2954e937168b780b2f8a7828d49f5b0d8809f25d74e6374065c4596c5a8ef2d2c4a18a0bbbb2ae9cb6d0f6332614270c4438ef07effd094df92b74cbb828305debaac629cb01a98e32d16e04d0b8c52c8a9a2c526481fd627d453e97bf33ea717775dc06abb09f0b95a435daf64e41d198ef6c686baffe891e9a1da8df943b12d1b5f192387b5b367db75593ace3399439621ec9d4195c188be12781cb165e559161381482bc513bb9a35d3746c30d88cc475642d63016c8a75347c1bb706bb3276218e6269e6e1a1c8912b077b5e82235ba837899c6c23bec2917457442f9f607d3d63b8c8ea5f065ca5e7a4ec037665a40003d9a0c95d97234ac9d50efa385cadfc79820a017abfd3f678ba5d7a8b890f5ca6c10ffbea407c6ac18638bde1806f739b7fd6ed49c665884f8cd4cdf77a9c02cad0ffa8971cdbe664ea7539521c87d9658808b112d1ea22b155208dfd693a48d5dd703279192ae5d9acab817c53193e17542db27d63764daccefb0be38b2bbdbd01345919e2f08811f99fb54a33033f6abc76c5ab4ebc9056f0e8d3005f80ffaf403ea744ff86a30fdc23f319972c4ccc81b3f6a23ad9fb00e480cd0b7d138e9db6e7cd25e424d29205782b06e4b0c5b932820ee2035fe657ec36489f60829d8c31dfe36accbc0fb78176508b6024b60909dba12747745d454c150f54945ef6a9a085e3a6b6539ace61f767e1e5fb1054355bf
2024-04-16 00:58:26 +00:00
let tree =
SaplingCommitmentTree $
hexString
" 01fef9aa4cfdc8c26eb2693907e96eccaacd61ed04ed7860f1d83260e6e383b936001001bdd6575663c970df26d8eb84b0be6411f65337912c90b1a0a8ba2b9303326d350000000000012f4f72c03f8c937a94919a01a07f21165cc8394295291cb888ca91ed003810390107114fe4bb4cd08b47f6ae47477c182d5da9fe5c189061808c1091e9bf3b4524000001447d6b9100cddd5f80c8cf4ddee2b87eba053bd987465aec2293bd0514e68b0d015f6c95e75f4601a0a31670a7deb970fc8988c611685161d2e1629d0a1a0ebd07015f8b9205e0514fa235d75c150b87e23866b882b39786852d1ab42aab11d31a4a0117ddeb3a5f8d2f6b2d0a07f28f01ab25e03a05a9319275bb86d72fcaef6fc01501f08f39275112dd8905b854170b7f247cf2df18454d4fa94e6e4f9320cca05f24011f8322ef806eb2430dc4a7a41c1b344bea5be946efc7b4349c1c9edb14ff9d39 "
let sk =
SaplingSpendingKey
" \ ETX \ 189 \ 201 \ 190 \ 128 \ NUL \ NUL \ NUL \ 128 $q \ CAN +P \ 196 \ 229 VM \ 129 :+ \ SI \ 171 W \ 248 ) \ 216 \ 196 \ 215 \ 141 \ 229 \ 239 \ 141 *Y \ 175 } \ 253 \ 232 s \ 156 (K \ 179 \ GS \ 139 \ 232 \ 246 \ ETB \ 181 `l \ 226 i \ 156 \ 211 # \ t dNT \ 248 \ 138 i \ 220 \ 136 \ 209 >U \ 150 cl \ f + \ 201 i \ 132 \ 250 \ 220 \ 208 \ 137 \ 178 \ 196 \ 238 \ 141 \ \ , \ 208 \ 194 * \ 245 \ 145 b \ FS \ 244 \ 164 \ 230 \ 194 C` \ ACK \ 140 \ 220 \ 194 \ ACK \ 190 \ 224 u \ FS \ 167 CK \ 181 \ DC2 \ r \ US \ 152 \ 237 \ 238 \ 137 \ 209 S \ 238 \ 240 D' \ 248 \ 255 \ 164 F \ 254 )n \ a \ 231 r \ 128 ! \ 177 \ 168 \ 210 \ 141 \ 234 \ STX 5 \ 189 \ b = \ 191 \ ETX : \ US gvB \ 155 \ 162 \ 234 \ 200 \ DC1 $z \ 252 \ 177 C+ \ 252 "
let so1 =
ShieldedOutput
( hexString
2024-04-16 14:43:00 +00:00
" 8e7443befa6ec5956c3b0c593c6065c7ee909f90de6188e38c24e57d8f0f4cc8 " )
2024-04-16 00:58:26 +00:00
( hexString
2024-04-16 14:43:00 +00:00
" fa430c51bb108db782764cff55de9c6b11bbecd2493d2e0fa9f646428feef858 " )
2024-04-16 00:58:26 +00:00
( hexString
2024-04-16 14:43:00 +00:00
" d322258e2bc7f6072ad014d8b249567b14276280bab8f2fe6b62ead86cda2dbf " )
2024-04-16 00:58:26 +00:00
( hexString
" 1264a89d07964845acb2ac5f9187f01f3980f0edfcee5f4082ad30f0c9512766063a55974c876cfb1b2115cbd46d9d49a3929ba42f4f9ba5ab15ddb106376a24786ba6631860f1e04df72a8a9dde04fb9128d453436f34eb560f52629deded87d46f0a6355da1070f14a0ea10fcae274bbc1b3f190858eb32ef47cf4fbca4d86fabe737ca1291f40979b6cda84bb43231598363ac9fc3d9af0d74a0a0797eb0dacc6dbd2687f3c8cd92468d39915edf9e45161ed10d78e17b629c5d5c73a09ff737fb370ce80a710bc97c391936223e926563f0ba27ec983c09477e23f8c288e35c57da1ce05ab740dd2d7afc800257c17276e4b9970f08288623c506275e0b0c8d5f60aab32974c24164d1b547e756218acf68849eea30480f529c8c05e62a65c9d070285b46c4a477ca5df220c696364523cc5d6db9ca852b1eb036846b537f4b566913660ad8b83d9c72daeb45274a55032cab9a3e0b3a1e386829dd10c6ba01dbc393843d67c553d74be7969b1879bf0a2ce05f108159a0df47f279b490d5a45ca1d90ff1a61650c6ae87611746d35f8410b39f2301a1be54711d58243cbc3afa29df2a7be5565cff1cad0bd34c370c345b2f38ac7020ac79f9d6c9eeaf2c7165acade98faf18a4e1b55a4e2a18a6dd4790057008ad40c51b0967b87a8d54cde958801ef98ae4a6c9f0e94f5c02a498a9173780b5b0790c248241125fe762c4697a320f1d08d782029c4fcb34fc8580c8c9885ba8339c5693170c157d1ebc663cdccd0a4bf6e77bdc3026252696ae0317ff7a3d9c190476e4605128e50eb42d3d5d8 " )
( hexString
" 6459d6fe8c22e5482822b61f0bcbfbc28374ed93ccbe97e3af400265f02ea525a8c4853dba3d667d7502e914f99ab5062f81fe1c699663694944c8a2fe4679a6866d1d3fc07acf31041881dad5faa083 " )
( hexString
" 85f51c5880265fe6f6bbd7961cfb9c8ceb8d1f5e1a99f7bc606585136c18d2eb3b9222576614c7092ff47d32696b50faa67c0170a2b3212a32f7bd79daa69a84fe2ef3b62081d78418d0a5902dc65d9442f1824366d8906d514ff1db6bfcb39202257e9e523cea9c311c0d4c13efc6fe6bea7dbd0c1c9ad39594ebca64586701a2384d40e62198cf379ecf21ddd8522e98a447f1c0f79e03abd232da7c8b9c39260a21097eedff86744445c7785ba0251fea0572d5ec7f78134c75fd03fc3d62 " )
2024-04-16 14:43:00 +00:00
let so2 =
ShieldedOutput
( hexString
" d283384bb097120b47b780b4a60b5c04d53e90c9ff2e781ac9b039384fbd48d1 " )
( hexString
" d163c69029e8cb05d874b798c7973b3b1b1b0e04f984a252b73c848698320843 " )
( hexString
" e007aea2e07f40f139e24d0e497eac26727a2b9aad4f223887cd423b9fd6cf58 " )
( hexString
" 353f0b011ea73b2a9843c25529df7b88f2357fba75353218012d1ba4b89b45d50564e9e7f16101c69c4232d2de683bd0960cc87a016dce7bb088720f8f6c092bdf2f2954e937168b780b2f8a7828d49f5b0d8809f25d74e6374065c4596c5a8ef2d2c4a18a0bbbb2ae9cb6d0f6332614270c4438ef07effd094df92b74cbb828305debaac629cb01a98e32d16e04d0b8c52c8a9a2c526481fd627d453e97bf33ea717775dc06abb09f0b95a435daf64e41d198ef6c686baffe891e9a1da8df943b12d1b5f192387b5b367db75593ace3399439621ec9d4195c188be12781cb165e559161381482bc513bb9a35d3746c30d88cc475642d63016c8a75347c1bb706bb3276218e6269e6e1a1c8912b077b5e82235ba837899c6c23bec2917457442f9f607d3d63b8c8ea5f065ca5e7a4ec037665a40003d9a0c95d97234ac9d50efa385cadfc79820a017abfd3f678ba5d7a8b890f5ca6c10ffbea407c6ac18638bde1806f739b7fd6ed49c665884f8cd4cdf77a9c02cad0ffa8971cdbe664ea7539521c87d9658808b112d1ea22b155208dfd693a48d5dd703279192ae5d9acab817c53193e17542db27d63764daccefb0be38b2bbdbd01345919e2f08811f99fb54a33033f6abc76c5ab4ebc9056f0e8d3005f80ffaf403ea744ff86a30fdc23f319972c4ccc81b3f6a23ad9fb00e480cd0b7d138e9db6e7cd25e424d29205782b06e4b0c5b932820ee2035fe657ec36489f60829d8c31dfe36accbc0fb78176508b6024b60909dba12747745d454c150f54945ef6a9a085e3a6b6539ace61f767e1e5fb1 " )
( hexString
" 054355bf26622674d58d4b5037457138e50abfefe92b515c74c608fcd2a5af50eab0bc85d57ba3bda52fa00c9c15d44a24586b2cacc6be00209ae49202430645d4a5022703b1cace87829dc783d5092d " )
( hexString
" 97e5f003d16720844ba1bd157688a7697133f4bb4a33a7c91974937a1351d7af56d16d4a10bd196ddda700fcd8be517f8f9e39a17ba0eea235d98450a626be3a998ac31f35e8e082106a31fe94da11d02b73748db4aa519df6bbf25c1d62a2cf0b192c6a486bca2632fee9e4124ce2dba6f3366a14850f6a3b784d863119f52458ed774f8d63105b4f6a3d2e09cc74e3a02ec8386213087b4c849172ded6724a45c9c12744ec4a0f86a29b803b17187df5dd5f90e71d1f3f4578d4e1496e8892 " )
2024-04-16 00:58:26 +00:00
it " Sap output 1 " $ do
2024-04-16 14:43:00 +00:00
let pos =
getSaplingNotePosition <$>
( getSaplingWitness =<<
updateSaplingCommitmentTree
tree
( fromText
" fa430c51bb108db782764cff55de9c6b11bbecd2493d2e0fa9f646428feef858 " ) )
case pos of
Nothing -> assertFailure " couldn't get note position "
Just p -> do
let dn = decodeSaplingOutputEsk sk so1 TestNet External p
dn ` shouldBe ` Nothing
it " Sap output 2 " $ do
case readZebraTransaction txHex2 of
Nothing -> assertFailure " Failed to read Tx "
Just tx -> do
let sBundle = fromRawSBundle $ zt_sBundle tx
case sBundle of
Nothing -> assertFailure " Failed to get sapling bundle "
Just sB -> do
let sOuts = sbOutputs sB
let pos =
getSaplingNotePosition <$>
( getSaplingWitness =<<
updateSaplingCommitmentTree
tree
( fromText
" d163c69029e8cb05d874b798c7973b3b1b1b0e04f984a252b73c848698320843 " ) )
case pos of
Nothing -> assertFailure " couldn't get note position "
Just p -> do
let dn =
decodeSaplingOutputEsk
sk
( head . tail $ sOuts )
TestNet
External
p
dn ` shouldBe ` Nothing
it " Decode Sapling Output from Zingo " $ do
case readZebraTransaction txHex of
Nothing -> assertFailure " Failed to read Tx "
Just tx -> do
case sK of
Nothing -> assertFailure " Failed to generate spending key "
Just sK' -> do
let sBundle = fromRawSBundle $ zt_sBundle tx
case sBundle of
Nothing -> assertFailure " Failed to get sapling bundle "
Just sB -> do
let sOuts = sbOutputs sB
let pos =
getSaplingNotePosition <$>
( getSaplingWitness =<<
updateSaplingCommitmentTree
tree
( fromText
" d163c69029e8cb05d874b798c7973b3b1b1b0e04f984a252b73c848698320843 " ) )
case pos of
Nothing -> assertFailure " couldn't get note position "
Just p -> do
let dn =
decodeSaplingOutputEsk
sK'
( head . tail $ sOuts )
MainNet
External
p
2024-04-29 15:27:45 +00:00
dn ` shouldNotBe ` Nothing
2024-04-18 00:36:04 +00:00
describe " Generate an ExchangeAddress (MainNet) from transparent address " $ do
let ta = decodeTransparentAddress " t1dMjvesbzdG41xgKaGU3HgwYJwSgbCK54e "
it " Try to generate valid ExchangeAddress from Transparent Address " $ do
2024-04-24 21:04:56 +00:00
case ta of
Nothing -> assertFailure " Failed to decode transparent address "
Just t -> do
case ( tr_type ( ta_receiver t ) ) of
P2SH ->
assertFailure
" P2SH not supported for ExchengeAddress generation "
2024-04-18 00:36:04 +00:00
P2PKH -> do
2024-04-24 21:04:56 +00:00
let exch =
encodeExchangeAddress ( ta_network t ) ( ta_receiver t )
2024-04-18 00:36:04 +00:00
case exch of
2024-04-24 21:04:56 +00:00
Nothing -> assertFailure " Failed to encode Exchange address "
Just addr -> do
2024-08-30 16:02:52 +00:00
let eadr = decodeExchangeAddress ( E . encodeUtf8 addr )
2024-04-24 21:04:56 +00:00
eadr ` shouldNotBe ` Nothing
2024-04-29 15:27:45 +00:00
describe " Witness updates " $ do
it " Sapling " $ do
let wit =
SaplingWitness $
hexString
" 01bd8a3f3cfc964332a2ada8c09a0da9dfc24174befb938abb086b9be5ca049e49013607f5e51826c8e5f660571ddfae14cd6fb1dc026bcd6855459b4e9339b20521100000019f0d7efb00169bb2202152d3266059d208ab17d14642c3339f9075e997160657000000012f4f72c03f8c937a94919a01a07f21165cc8394295291cb888ca91ed003810390107114fe4bb4cd08b47f6ae47477c182d5da9fe5c189061808c1091e9bf3b4524000001447d6b9100cddd5f80c8cf4ddee2b87eba053bd987465aec2293bd0514e68b0d015f6c95e75f4601a0a31670a7deb970fc8988c611685161d2e1629d0a1a0ebd07015f8b9205e0514fa235d75c150b87e23866b882b39786852d1ab42aab11d31a4a0117ddeb3a5f8d2f6b2d0a07f28f01ab25e03a05a9319275bb86d72fcaef6fc01501f08f39275112dd8905b854170b7f247cf2df18454d4fa94e6e4f9320cca05f24011f8322ef806eb2430dc4a7a41c1b344bea5be946efc7b4349c1c9edb14ff9d39038cd7f6e2238d16ef49420963348dd4e4c7d23d5e5dac69507fba8937f63eb626f6856115bea2fa8db3a65a0ab294db41c51435d3b7ea27c7b2835aca28e82a2c1d9634efe07449a47c251518ac6f92c49f3a1ef119948f6a824d1e7ff7d0443e0101e57ec972a9b9383dc9cb228980d2d7752bb2abebc4a604ca48c5457039d2e05b000301392bed8592185dde5ab7fc81aed75e98fcf041f1a3fda55ad0b0b139ba9380130001808304b4d7c4fc407f5ce28247a7119013aeaaf1481902419c42bc8b21575c15 "
let cmus =
[ hexString
" 958ccdc752f2f593f6c1c8e2d7201348cd896e54c6d3c92200bdbe8b859eac44 "
, hexString
" e49992fdd071d90bf56242d1aa625bbe267a34e0debd4307818a686d05b45447 "
, hexString
" 0c4b26766d89bf6cdb4fd3b0317b4e9a2fb3850f6a24869f32fe7cb0fd512e18 "
]
updateSaplingWitness wit cmus ` shouldBe `
SaplingWitness
( hexString
" 01bd8a3f3cfc964332a2ada8c09a0da9dfc24174befb938abb086b9be5ca049e49013607f5e51826c8e5f660571ddfae14cd6fb1dc026bcd6855459b4e9339b20521100000019f0d7efb00169bb2202152d3266059d208ab17d14642c3339f9075e997160657000000012f4f72c03f8c937a94919a01a07f21165cc8394295291cb888ca91ed003810390107114fe4bb4cd08b47f6ae47477c182d5da9fe5c189061808c1091e9bf3b4524000001447d6b9100cddd5f80c8cf4ddee2b87eba053bd987465aec2293bd0514e68b0d015f6c95e75f4601a0a31670a7deb970fc8988c611685161d2e1629d0a1a0ebd07015f8b9205e0514fa235d75c150b87e23866b882b39786852d1ab42aab11d31a4a0117ddeb3a5f8d2f6b2d0a07f28f01ab25e03a05a9319275bb86d72fcaef6fc01501f08f39275112dd8905b854170b7f247cf2df18454d4fa94e6e4f9320cca05f24011f8322ef806eb2430dc4a7a41c1b344bea5be946efc7b4349c1c9edb14ff9d39038cd7f6e2238d16ef49420963348dd4e4c7d23d5e5dac69507fba8937f63eb626f6856115bea2fa8db3a65a0ab294db41c51435d3b7ea27c7b2835aca28e82a2c1d9634efe07449a47c251518ac6f92c49f3a1ef119948f6a824d1e7ff7d0443e0101e49992fdd071d90bf56242d1aa625bbe267a34e0debd4307818a686d05b45447010c4b26766d89bf6cdb4fd3b0317b4e9a2fb3850f6a24869f32fe7cb0fd512e1803000121c06ee1f1584f79d50785797a694c742be2ded600367ab7d54f3ed49e3adf7201808304b4d7c4fc407f5ce28247a7119013aeaaf1481902419c42bc8b21575c15 " )
it " Orchard " $ do
let wit =
OrchardWitness $
hexString
" 016225b41339a00dd764b452fca190a0245e7118224965942e3a6d798365c34631001f0000011d6f5da3f619bfaab957fc643c17eb144db0101c90f422da2fcbe0e80d74412e000000000001746e6bc066a10e7f80a9ff8993dcb25c819edd64f2ca10ac248ef7848d41450500011e6191f91b3fceb62dc881a156e1b9d2e88e09dca25093cf9c4936c8869fb41a013bf8b923e4187754e85175748d9cce4824a6787e4258977b5bfe1ba59012c032000001f3bbdc62260c4fca5c84bf3487246d4542da48eeeec8ec40c1029b6908eef83c00000000000000000000000000000000040e02c864db8b574f165f616d48e2f12eb25099b5c90186af26d9e50f5058863e0504bfbc12edc35e05042c16bbfb8fed591f01f18fe128eeb57f2c456c9eb222d6d261c549e95d9007bce4c6ae0b86bc865711cdd9f0fa92e2d5b5e149b51f3be127df3b1d2372adf6c811b2e456c1d64d0e9eb167a995f9c6b66a03c9cbda250101c094201bae3b4ef582a3e8654f65a72fbd41e20e1ec9a43d3f4101afc868731e000200019df5b9366d0f21caa678d1567390b5bfd3cfa0438271bcfe301b5558a2863301 "
let cmxs =
[ hexString
" 712ba86615ff4447e8d7c7b59f3873f03c03a173438b8e4c8d416756ed4fae10 "
, hexString
" c094201bae3b4ef582a3e8654f65a72fbd41e20e1ec9a43d3f4101afc868731e "
, hexString
" ac20b8170b008888c19fc6e16f5e30a5ef1653e5219d0cd0c9353c3aa8f79823 "
]
updateOrchardWitness wit cmxs ` shouldBe `
OrchardWitness
( hexString
2024-09-16 18:36:49 +00:00
" 016225b41339a00dd764b452fca190a0245e7118224965942e3a6d798365c34631001f0000011d6f5da3f619bfaab957fc643c17eb144db0101c90f422da2fcbe0e80d74412e000000000001746e6bc066a10e7f80a9ff8993dcb25c819edd64f2ca10ac248ef7848d41450500011e6191f91b3fceb62dc881a156e1b9d2e88e09dca25093cf9c4936c8869fb41a013bf8b923e4187754e85175748d9cce4824a6787e4258977b5bfe1ba59012c032000001f3bbdc62260c4fca5c84bf3487246d4542da48eeeec8ec40c1029b6908eef83c00000000000000000000000000000000040e02c864db8b574f165f616d48e2f12eb25099b5c90186af26d9e50f5058863e0504bfbc12edc35e05042c16bbfb8fed591f01f18fe128eeb57f2c456c9eb222d6d261c549e95d9007bce4c6ae0b86bc865711cdd9f0fa92e2d5b5e149b51f3be127df3b1d2372adf6c811b2e456c1d64d0e9eb167a995f9c6b66a03c9cbda250101c094201bae3b4ef582a3e8654f65a72fbd41e20e1ec9a43d3f4101afc868731e01ac20b8170b008888c19fc6e16f5e30a5ef1653e5219d0cd0c9353c3aa8f7982302010cfb50d8c877eb39e9c07082a032dd99d34be7c19fa7f30e9fecf5f14736240f019df5b9366d0f21caa678d1567390b5bfd3cfa0438271bcfe301b5558a2863301 " )
2024-04-18 00:36:04 +00:00
2024-03-08 18:44:10 +00:00
-- | Properties
2024-03-11 20:23:29 +00:00
prop_PhraseLength :: Property
prop_PhraseLength =
2024-03-08 18:44:10 +00:00
ioProperty $ do
p <- generateWalletSeedPhrase
2024-03-14 16:13:10 +00:00
return $ BS . length ( getBytes p ) >= 95
2024-03-08 18:44:10 +00:00
2024-03-11 20:23:29 +00:00
prop_SeedLength :: Property
prop_SeedLength =
2024-03-08 18:44:10 +00:00
ioProperty $ do
p <- generateWalletSeedPhrase
let s = getWalletSeed p
2024-03-14 16:13:10 +00:00
return $ maybe 0 ( BS . length . getBytes ) s === 64
2024-03-08 18:44:10 +00:00
2024-03-11 20:23:29 +00:00
prop_OrchardSpendingKey :: Seed -> CoinType -> NonNegative Int -> Property
prop_OrchardSpendingKey s c ( NonNegative i ) =
genOrchardSpendingKey s c i =/= Nothing
2024-03-08 18:44:10 +00:00
2024-03-11 20:23:29 +00:00
prop_OrchardReceiver ::
2024-03-14 16:13:10 +00:00
Seed -> CoinType -> NonNegative Int -> NonNegative Int -> Scope -> Property
prop_OrchardReceiver s c ( NonNegative i ) ( NonNegative j ) scope =
2024-03-14 17:35:13 +00:00
genOrchardReceiver
j
scope
( fromMaybe ( OrchardSpendingKey " " ) $ genOrchardSpendingKey s c i ) =/=
2024-03-14 16:13:10 +00:00
Nothing
2024-03-08 18:44:10 +00:00
2024-03-13 17:50:39 +00:00
prop_SaplingSpendingKey :: Seed -> CoinType -> NonNegative Int -> Property
prop_SaplingSpendingKey s c ( NonNegative i ) =
genSaplingSpendingKey s c i =/= Nothing
2024-03-11 20:23:29 +00:00
2024-03-13 17:50:39 +00:00
prop_SaplingReceiver ::
Seed -> CoinType -> NonNegative Int -> NonNegative Int -> Property
prop_SaplingReceiver s c ( NonNegative i ) ( NonNegative j ) =
2024-03-14 16:13:10 +00:00
genSaplingPaymentAddress
i
( fromMaybe ( SaplingSpendingKey " " ) $ genSaplingSpendingKey s c j ) =/=
2024-03-11 20:23:29 +00:00
Nothing
2024-03-10 12:47:26 +00:00
2024-03-13 17:50:39 +00:00
prop_SaplingRecRepeated :: Seed -> CoinType -> NonNegative Int -> Property
prop_SaplingRecRepeated s c ( NonNegative i ) =
2024-03-14 16:13:10 +00:00
genSaplingPaymentAddress
i
( fromMaybe ( SaplingSpendingKey " " ) $ genSaplingSpendingKey s c 1 ) =/=
genSaplingPaymentAddress
( i + 1 )
( fromMaybe ( SaplingSpendingKey " " ) $ genSaplingSpendingKey s c 1 )
2024-03-11 20:48:27 +00:00
2024-03-12 17:22:05 +00:00
prop_OrchardRecRepeated ::
2024-03-14 16:13:10 +00:00
Seed -> CoinType -> NonNegative Int -> NonNegative Int -> Scope -> Property
prop_OrchardRecRepeated s c ( NonNegative i ) ( NonNegative j ) scope =
2024-03-14 17:35:13 +00:00
genOrchardReceiver
j
scope
( fromMaybe ( OrchardSpendingKey " " ) $ genOrchardSpendingKey s c i ) =/=
genOrchardReceiver
( j + 1 )
scope
( fromMaybe ( OrchardSpendingKey " " ) $ genOrchardSpendingKey s c i )
2024-03-12 17:22:05 +00:00
2024-03-15 15:11:27 +00:00
prop_TransparentSpendingKey :: Seed -> CoinType -> NonNegative Int -> Property
prop_TransparentSpendingKey s coinType ( NonNegative i ) =
2024-03-13 19:12:28 +00:00
ioProperty $ do
2024-03-15 15:11:27 +00:00
k <- genTransparentPrvKey s coinType i
2024-03-13 19:12:28 +00:00
return $ xPrvChild k == fromIntegral i
prop_TransparentReceiver ::
2024-03-15 15:11:27 +00:00
Seed -> CoinType -> Scope -> NonNegative Int -> NonNegative Int -> Property
prop_TransparentReceiver s coinType scope ( NonNegative i ) ( NonNegative j ) =
2024-03-13 19:12:28 +00:00
ioProperty $ do
2024-03-15 15:11:27 +00:00
k <- genTransparentPrvKey s coinType i
r <- genTransparentReceiver j scope k
2024-04-13 22:27:59 +00:00
return $ tr_type r == P2PKH
2024-03-13 19:12:28 +00:00
2024-03-08 18:44:10 +00:00
-- | Generators
genOrcArgs :: Gen ( CoinType , Int , Int )
genOrcArgs = do
i <- arbitrarySizedNatural
j <- arbitrarySizedNatural
c <- elements [ MainNetCoin , TestNetCoin , RegTestNetCoin ]
return ( c , i , j )
2024-03-10 12:47:26 +00:00
genSapArgs :: Gen Int
genSapArgs = choose ( 1 , 50 )
2024-03-11 20:23:29 +00:00
getSeed :: IO Seed
getSeed = do
p <- generateWalletSeedPhrase
let s = getWalletSeed p
case s of
Nothing -> throwIO $ userError " Couldn't generate seed "
Just s' -> return s'
2024-03-08 18:44:10 +00:00
-- | Arbitrary instances
2024-03-11 20:23:29 +00:00
instance Arbitrary CoinType where
arbitrary = elements [ MainNetCoin , TestNetCoin , RegTestNetCoin ]
2024-03-14 16:13:10 +00:00
instance Arbitrary Scope where
arbitrary = elements [ External , Internal ]