Browse Source

Merge pull request #1 from gilardh/master

Update
duke
Duke Leto 4 years ago
committed by GitHub
parent
commit
950a596943
No known key found for this signature in database GPG Key ID: 4AEE18F83AFDEB23
  1. 39
      README.md
  2. 13
      cli/Cargo.toml
  3. 58
      cli/mkrelease.sh
  4. 25
      cli/src/main.rs
  5. 2
      cli/src/version.rs
  6. BIN
      hushpaperwallet.png
  7. 13
      lib/Cargo.toml
  8. 392
      lib/src/paper.rs
  9. 61
      lib/src/pdf.rs
  10. 8
      ui/.gitignore
  11. 6
      ui/hushpaperwalletui_resource.rc
  12. 18
      ui/mkdockerwinlinux.sh
  13. 76
      ui/mkrelease.sh
  14. 20
      ui/papersapling.pro
  15. 4
      ui/qtlib/Cargo.toml
  16. 4
      ui/qtlib/src/hushpaperrust.h
  17. 2
      ui/qtlib/src/lib.rs
  18. 4
      ui/res/Info.plist
  19. 6
      ui/src/about.ui
  20. 6
      ui/src/main.cpp
  21. 6
      ui/src/mainwindow.cpp
  22. 2
      ui/src/mainwindow.ui
  23. 2
      web/.gitignore
  24. 36
      web/Cargo.toml
  25. 176
      web/LICENSE_APACHE
  26. 25
      web/LICENSE_MIT
  27. 26
      web/README.md
  28. 3
      web/package-lock.json
  29. 17
      web/src/lib.rs
  30. 10
      web/src/utils.rs
  31. 13
      web/tests/web.rs
  32. 3
      web/www/.gitignore
  33. 5
      web/www/.travis.yml
  34. 201
      web/www/LICENSE-APACHE
  35. 25
      web/www/LICENSE-MIT
  36. 5
      web/www/bootstrap.js
  37. 159
      web/www/index.html
  38. 153
      web/www/index.js
  39. 42
      web/www/package.json
  40. 14
      web/www/webpack.config.js

39
README.md

@ -1,22 +1,23 @@
# zecpaperwallet
zecpaperwallet is a Zcash Sapling paper wallet generator that can run completely offline. You can run it on an air-gapped computer to generate your shielded z-addresses, which will allow you to keep your keys completely offline.
# hushpaperwallet
hushpaperwallet is a paper wallet generator that can run completely offline.
You can run it on an air-gapped computer to generate your shielded z-addresses, which will allow you to keep your keys completely offline.
*Example:*
![Paper Wallet](docs/paperwallet.png?raw=true)
*Example:*
![screenshot](hushpaperwallet.png?raw=true)
# Download
zecpaperwallet is available as pre-built binaries from our [release page](https://github.com/adityapk00/zecpaperwallet/releases). Download the zip file for your platform, extract it and run the `./zecpaperwallet` binary.
hushpaperwallet is available as pre-built binaries from our [release page](https://github.com/MyHush/hushpaperwallet/releases). Download the zip file for your platform, extract it and run the `./hushpaperwallet` binary.
# Generating wallets
To generate a Zcash paper wallet, simply run `./zecpaperwallet`
To generate a Hush paper wallet, simply run `./hushpaperwallet`
You'll be asked to type some random characters that will add entropy to the random number generator. Run with `--help` to see all options
## Saving as PDFs
To generate a Zcash paper wallet and save it as a PDF, run
`./zecpaperwallet -z 3 --format pdf zecpaper-output.pdf`
To generate a Hush paper wallet and save it as a PDF, run
`./hushpaperwallet -z 3 --format pdf hushpaper-output.pdf`
This will generate 3 shielded z-addresses and their corresponding private keys, and save them in a PDF file called `zecpaper-output.pdf`
This will generate 3 shielded z-addresses and their corresponding private keys, and save them in a PDF file called `hushpaper-output.pdf`
## Vanity Addresses
You can generate a "vanity address" (that is, an address starting with a given prefix) by specifying a `--vanity` argument with the prefix you want.
@ -24,14 +25,14 @@ You can generate a "vanity address" (that is, an address starting with a given p
Note that generating vanity addresses with a prefix longer than 4-5 characters is computationally expensive. You can run it on multiple CPUs on your computer by specifying the `--threads` option.
# Compiling from Source
zecpaperwallet is built with rust. To compile from source, you [install Rust](https://www.rust-lang.org/tools/install). Basically, you need to:
hushpaperwallet is built with rust. To compile from source, you [install Rust](https://www.rust-lang.org/tools/install). Basically, you need to:
```
curl https://sh.rustup.rs -sSf | sh
```
Checkout the zecpaperwallet repository and build the CLI
Checkout the hushpaperwallet repository and build the CLI
```
git clone https://github.com/adityapk00/zecpaperwallet.git
cd zecpaperwallet/cli
git clone https://github.com/MyHush/hushpaperwallet.git
cd hushpaperwallet/cli
cargo build --release
```
@ -39,17 +40,17 @@ The binary is available in the `target/release` folder.
## Ensuring Security
When generating paper wallets that will store large amounts of crypto, please take special care to ensure the keys are generated and kept completely offline.
1. `zecpaperwallet` supports ARMv8 (Raspberry Pi 3+). You can put one in a Faraday cage along with a printer, and print out the PDFs securely.
2. Please ensure you supply random entropy when you run `zecpaperwallet`. Your entropy is mixed in with system-provided entropy to generate keys
1. `hushpaperwallet` supports ARMv8 (Raspberry Pi 3+). You can put one in a Faraday cage along with a printer, and print out the PDFs securely.
2. Please ensure you supply random entropy when you run `hushpaperwallet`. Your entropy is mixed in with system-provided entropy to generate keys
3. If you can, run with `unshare`, which will disable all network interfaces to a process, providing you with an additional layer of safety. (See next section)
4. After you've generated the keys, you can tear off the Address potion of the wallet and take it to your online computer/phone to send the address funds. Please always keep the private key offline.
5. When you're ready to spend the cold storage keys, import the private key into a full node, then don't re-use the key again.
### Run without network
If you are running a newish version of Linux, you can be doubly sure that the process is not contacting the network by running zecpaperwallet without the network namespace.
If you are running a newish version of Linux, you can be doubly sure that the process is not contacting the network by running hushpaperwallet without the network namespace.
```
sudo unshare -n ./target/release/zecpaperwallet
sudo unshare -n ./target/release/hushpaperwallet
```
`unshare -n` runs the process without a network interface which means you can be sure that your data is not being sent across the network.
@ -57,11 +58,11 @@ sudo unshare -n ./target/release/zecpaperwallet
## Help options
```
USAGE:
zecpaperwallet [FLAGS] [OPTIONS] [output]
hushpaperwallet [FLAGS] [OPTIONS] [output]
FLAGS:
-h, --help Prints help information
-n, --nohd Don't reuse HD keys. Normally, zecpaperwallet will use the same HD key to derive multiple
-n, --nohd Don't reuse HD keys. Normally, hushpaperwallet will use the same HD key to derive multiple
addresses. This flag will use a new seed for each address
--testnet Generate Testnet addresses
-V, --version Prints version information

13
cli/Cargo.toml

@ -1,11 +1,14 @@
[package]
name = "zecpaperwallet"
version = "0.1.0"
authors = ["ZecWallet"]
name = "hushpaperwallet"
version = "0.1.1"
authors = [
"ZecWallet",
"The Hush developers"
]
edition = "2018"
[dependencies]
clap = "2.33.0"
zecpaperlib = { path = "../lib" }
hushpaperlib = { path = "../lib" }
json = "0.11.14"
printpdf = "0.2.8"
printpdf = "0.3.2"

58
cli/mkrelease.sh

@ -32,58 +32,58 @@ cargo clean
cargo build --release
# macOS
rm -rf target/macOS-zecpaperwallet-v$APP_VERSION
mkdir -p target/macOS-zecpaperwallet-v$APP_VERSION
cp target/release/zecpaperwallet target/macOS-zecpaperwallet-v$APP_VERSION/
rm -rf target/macOS-hushpaperwallet-v$APP_VERSION
mkdir -p target/macOS-hushpaperwallet-v$APP_VERSION
cp target/release/hushpaperwallet target/macOS-hushpaperwallet-v$APP_VERSION/
# For Windows and Linux, build via docker
docker run --rm -v $(pwd)/..:/opt/zecpaperwallet rustbuild:latest bash -c "cd /opt/zecpaperwallet/cli && cargo build --release && cargo build --release --target x86_64-pc-windows-gnu && cargo build --release --target aarch64-unknown-linux-gnu"
docker run --rm -v $(pwd)/..:/opt/hushpaperwallet rustbuild:latest bash -c "cd /opt/hushpaperwallet/cli && cargo build --release && cargo build --release --target x86_64-pc-windows-gnu && cargo build --release --target aarch64-unknown-linux-gnu"
# Now sign and zip the binaries
gpg --batch --output target/macOS-zecpaperwallet-v$APP_VERSION/zecpaperwallet.sig --detach-sig target/macOS-zecpaperwallet-v$APP_VERSION/zecpaperwallet
gpg --batch --output target/macOS-hushpaperwallet-v$APP_VERSION/hushpaperwallet.sig --detach-sig target/macOS-hushpaperwallet-v$APP_VERSION/hushpaperwallet
cd target
cd macOS-zecpaperwallet-v$APP_VERSION
gsha256sum zecpaperwallet > sha256sum.txt
cd macOS-hushpaperwallet-v$APP_VERSION
gsha256sum hushpaperwallet > sha256sum.txt
cd ..
zip -r macOS-zecpaperwallet-v$APP_VERSION.zip macOS-zecpaperwallet-v$APP_VERSION
zip -r macOS-hushpaperwallet-v$APP_VERSION.zip macOS-hushpaperwallet-v$APP_VERSION
cd ..
#Linux
rm -rf target/linux-zecpaperwallet-v$APP_VERSION
mkdir -p target/linux-zecpaperwallet-v$APP_VERSION
cp target/release/zecpaperwallet target/linux-zecpaperwallet-v$APP_VERSION/
gpg --batch --output target/linux-zecpaperwallet-v$APP_VERSION/zecpaperwallet.sig --detach-sig target/linux-zecpaperwallet-v$APP_VERSION/zecpaperwallet
rm -rf target/linux-hushpaperwallet-v$APP_VERSION
mkdir -p target/linux-hushpaperwallet-v$APP_VERSION
cp target/release/hushpaperwallet target/linux-hushpaperwallet-v$APP_VERSION/
gpg --batch --output target/linux-hushpaperwallet-v$APP_VERSION/hushpaperwallet.sig --detach-sig target/linux-hushpaperwallet-v$APP_VERSION/hushpaperwallet
cd target
cd linux-zecpaperwallet-v$APP_VERSION
gsha256sum zecpaperwallet > sha256sum.txt
cd linux-hushpaperwallet-v$APP_VERSION
gsha256sum hushpaperwallet > sha256sum.txt
cd ..
zip -r linux-zecpaperwallet-v$APP_VERSION.zip linux-zecpaperwallet-v$APP_VERSION
zip -r linux-hushpaperwallet-v$APP_VERSION.zip linux-hushpaperwallet-v$APP_VERSION
cd ..
#Windows
rm -rf target/Windows-zecpaperwallet-v$APP_VERSION
mkdir -p target/Windows-zecpaperwallet-v$APP_VERSION
cp target/x86_64-pc-windows-gnu/release/zecpaperwallet.exe target/Windows-zecpaperwallet-v$APP_VERSION/
gpg --batch --output target/Windows-zecpaperwallet-v$APP_VERSION/zecpaperwallet.sig --detach-sig target/Windows-zecpaperwallet-v$APP_VERSION/zecpaperwallet.exe
rm -rf target/Windows-hushpaperwallet-v$APP_VERSION
mkdir -p target/Windows-hushpaperwallet-v$APP_VERSION
cp target/x86_64-pc-windows-gnu/release/hushpaperwallet.exe target/Windows-hushpaperwallet-v$APP_VERSION/
gpg --batch --output target/Windows-hushpaperwallet-v$APP_VERSION/hushpaperwallet.sig --detach-sig target/Windows-hushpaperwallet-v$APP_VERSION/hushpaperwallet.exe
cd target
cd Windows-zecpaperwallet-v$APP_VERSION
gsha256sum zecpaperwallet.exe > sha256sum.txt
cd Windows-hushpaperwallet-v$APP_VERSION
gsha256sum hushpaperwallet.exe > sha256sum.txt
cd ..
zip -r Windows-zecpaperwallet-v$APP_VERSION.zip Windows-zecpaperwallet-v$APP_VERSION
zip -r Windows-hushpaperwallet-v$APP_VERSION.zip Windows-hushpaperwallet-v$APP_VERSION
cd ..
# aarch64 (armv8)
rm -rf target/aarch64-zecpaperwallet-v$APP_VERSION
mkdir -p target/aarch64-zecpaperwallet-v$APP_VERSION
cp target/aarch64-unknown-linux-gnu/release/zecpaperwallet target/aarch64-zecpaperwallet-v$APP_VERSION/
gpg --batch --output target/aarch64-zecpaperwallet-v$APP_VERSION/zecpaperwallet.sig --detach-sig target/aarch64-zecpaperwallet-v$APP_VERSION/zecpaperwallet
rm -rf target/aarch64-hushpaperwallet-v$APP_VERSION
mkdir -p target/aarch64-hushpaperwallet-v$APP_VERSION
cp target/aarch64-unknown-linux-gnu/release/hushpaperwallet target/aarch64-hushpaperwallet-v$APP_VERSION/
gpg --batch --output target/aarch64-hushpaperwallet-v$APP_VERSION/hushpaperwallet.sig --detach-sig target/aarch64-hushpaperwallet-v$APP_VERSION/hushpaperwallet
cd target
cd aarch64-zecpaperwallet-v$APP_VERSION
gsha256sum zecpaperwallet > sha256sum.txt
cd aarch64-hushpaperwallet-v$APP_VERSION
gsha256sum hushpaperwallet > sha256sum.txt
cd ..
zip -r aarch64-zecpaperwallet-v$APP_VERSION.zip aarch64-zecpaperwallet-v$APP_VERSION
zip -r aarch64-hushpaperwallet-v$APP_VERSION.zip aarch64-hushpaperwallet-v$APP_VERSION
cd ..

25
cli/src/main.rs

@ -1,25 +1,22 @@
extern crate clap;
extern crate zecpaperlib;
extern crate hushpaperlib;
mod version;
use clap::{Arg, App};
use zecpaperlib::paper::*;
use zecpaperlib::pdf;
use hushpaperlib::paper::*;
use hushpaperlib::pdf;
use std::io;
use std::io::prelude::*;
fn main() {
let matches = App::new("zecpaperwaller")
let matches = App::new("hushpaperwaller")
.version(version::version())
.about("A command line Zcash Sapling paper wallet generator")
.arg(Arg::with_name("testnet")
.long("testnet")
.help("Generate Testnet addresses"))
.about("A command line Hush paper wallet generator")
.arg(Arg::with_name("format")
.short("f")
.long("format")
.help("What format to generate the output in")
.help("What format to generate the output in: json or pdf")
.takes_value(true)
.value_name("FORMAT")
.possible_values(&["pdf", "json"])
@ -27,7 +24,7 @@ fn main() {
.arg(Arg::with_name("nohd")
.short("n")
.long("nohd")
.help("Don't reuse HD keys. Normally, zecpaperwallet will use the same HD key to derive multiple addresses. This flag will use a new seed for each address"))
.help("Don't reuse HD keys. Normally, hushpaperwallet will use the same HD key to derive multiple addresses. This flag will use a new seed for each address"))
.arg(Arg::with_name("output")
.short("o")
.long("output")
@ -69,8 +66,6 @@ fn main() {
}))
.get_matches();
let is_testnet: bool = matches.is_present("testnet");
let nohd: bool = matches.is_present("nohd");
// Get the filename and output format
@ -114,7 +109,7 @@ fn main() {
let prefix = matches.value_of("vanity_prefix").unwrap().to_string();
println!("Generating address starting with \"{}\"", prefix);
let addresses = match generate_vanity_wallet(is_testnet, num_threads, prefix) {
let addresses = match generate_vanity_wallet(num_threads, prefix) {
Ok(w) => w,
Err(e) => {
eprintln!("{}", e);
@ -143,7 +138,7 @@ fn main() {
print!("Generating {} Sapling addresses and {} Transparent addresses...", z_addresses, t_addresses);
io::stdout().flush().ok();
let addresses = generate_wallet(is_testnet, nohd, z_addresses, t_addresses, &entropy);
let addresses = generate_wallet(nohd, z_addresses, t_addresses, &entropy);
println!("[OK]");
addresses
@ -161,7 +156,7 @@ fn main() {
// We already know the output file name was specified
print!("Writing {:?} as a PDF file...", filename.unwrap());
io::stdout().flush().ok();
match pdf::save_to_pdf(is_testnet, &addresses, filename.unwrap()) {
match pdf::save_to_pdf(&addresses, filename.unwrap()) {
Ok(_) => { println!("[OK]");},
Err(e) => {
eprintln!("[ERROR]");

2
cli/src/version.rs

@ -1 +1 @@
pub fn version() -> &'static str { &"0.5" }
pub fn version() -> &'static str { &"0.1.1" }

BIN
hushpaperwallet.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 24 KiB

13
lib/Cargo.toml

@ -1,7 +1,10 @@
[package]
name = "zecpaperlib"
version = "0.1.0"
authors = ["ZecWallet"]
name = "hushpaperlib"
version = "0.1.1"
authors = [
"ZecWallet",
"The Hush developers"
]
edition = "2018"
[features]
@ -11,10 +14,10 @@ default = ["printpdf"]
rand = "0.5"
hex = "0.3"
bech32 = "0.6"
zcash_primitives = { git = "https://github.com/zcash/librustzcash", rev = "5a48d179b8434a0318e7e19dda506e245a904092" }
zcash_primitives = { git = "https://github.com/gilardh/librustzcash", rev = "5a48d179b8434a0318e7e19dda506e245a904092" }
json = "0.11.14"
qrcode = { version = "0.8", default-features = false }
printpdf = { version = "0.2.8", optional = true }
printpdf = { version = "0.3.2", optional = true }
libsecp256k1 = "0.2.2"
ripemd160 = "0.8.0"
sha2 = "0.8.0"

392
lib/src/paper.rs

@ -55,17 +55,7 @@ pub struct CoinParams {
pub cointype : u32,
}
pub fn params(is_testnet: bool) -> CoinParams {
if is_testnet {
CoinParams {
taddress_version : [0x1D, 0x25],
tsecret_prefix : [0xEF],
zaddress_prefix : "ztestsapling".to_string(),
zsecret_prefix : "secret-extended-key-test".to_string(),
zviewkey_prefix : "zviewtestsapling".to_string(),
cointype : 1
}
} else {
pub fn params() -> CoinParams {
CoinParams {
taddress_version : [0x1C, 0xB8],
tsecret_prefix : [0x80],
@ -74,7 +64,6 @@ pub fn params(is_testnet: bool) -> CoinParams {
zviewkey_prefix : "zviews".to_string(),
cointype : 133
}
}
}
pub fn increment(s: &mut [u8; 32]) -> Result<(), ()> {
@ -114,7 +103,7 @@ fn get_bech32_for_prefix(prefix: String) -> Result<Vec<u5>, String> {
return Ok(ans);
}
fn encode_address(spk: &ExtendedSpendingKey, is_testnet: bool) -> String {
fn encode_address(spk: &ExtendedSpendingKey) -> String {
let (_d, addr) = spk.default_address().expect("Cannot get result");
// Address is encoded as a bech32 string
@ -123,23 +112,23 @@ fn encode_address(spk: &ExtendedSpendingKey, is_testnet: bool) -> String {
v.get_mut(..11).unwrap().copy_from_slice(&addr.diversifier.0);
addr.pk_d.write(v.get_mut(11..).unwrap()).expect("Cannot write!");
let checked_data: Vec<u5> = v.to_base32();
let encoded : String = Bech32::new(params(is_testnet).zaddress_prefix.into(), checked_data).expect("bech32 failed").to_string();
let encoded : String = Bech32::new(params().zaddress_prefix.into(), checked_data).expect("bech32 failed").to_string();
return encoded;
}
fn encode_privatekey(spk: &ExtendedSpendingKey, is_testnet: bool) -> String {
fn encode_privatekey(spk: &ExtendedSpendingKey) -> String {
// Private Key is encoded as bech32 string
let mut vp = Vec::new();
spk.write(&mut vp).expect("Can't write private key");
let c_d: Vec<u5> = vp.to_base32();
let encoded_pk = Bech32::new(params(is_testnet).zsecret_prefix.into(), c_d).expect("bech32 failed").to_string();
let encoded_pk = Bech32::new(params().zsecret_prefix.into(), c_d).expect("bech32 failed").to_string();
return encoded_pk;
}
/// A single thread that grinds through the Diversifiers to find the defualt key that matches the prefix
pub fn vanity_thread(is_testnet: bool, entropy: &[u8], prefix: String, tx: mpsc::Sender<String>, please_stop: Arc<AtomicBool>) {
pub fn vanity_thread(entropy: &[u8], prefix: String, tx: mpsc::Sender<String>, please_stop: Arc<AtomicBool>) {
let mut seed: [u8; 32] = [0; 32];
seed.copy_from_slice(&entropy[0..32]);
@ -148,7 +137,7 @@ pub fn vanity_thread(is_testnet: bool, entropy: &[u8], prefix: String, tx: mpsc:
let vanity_bytes = get_bech32_for_prefix(prefix).expect("Bad char in prefix");
let master_spk = ExtendedSpendingKey::from_path(&ExtendedSpendingKey::master(&seed),
&[ChildIndex::Hardened(32), ChildIndex::Hardened(params(is_testnet).cointype), ChildIndex::Hardened(0)]);
&[ChildIndex::Hardened(32), ChildIndex::Hardened(params().cointype), ChildIndex::Hardened(0)]);
let mut spkv = vec![];
master_spk.write(&mut spkv).unwrap();
@ -177,8 +166,8 @@ pub fn vanity_thread(is_testnet: bool, entropy: &[u8], prefix: String, tx: mpsc:
let spk = ExtendedSpendingKey::read(&spkv[..]).unwrap();
let encoded = encode_address(&spk, is_testnet);
let encoded_pk = encode_privatekey(&spk, is_testnet);
let encoded = encode_address(&spk);
let encoded_pk = encode_privatekey(&spk);
let wallet = array!{object!{
"num" => 0,
@ -231,7 +220,7 @@ fn pretty_duration(secs: f64) -> (String, String) {
}
/// Generate a vanity address with the given prefix.
pub fn generate_vanity_wallet(is_testnet: bool, num_threads: u32, prefix: String) -> Result<String, String> {
pub fn generate_vanity_wallet(num_threads: u32, prefix: String) -> Result<String, String> {
// Test the prefix first
match get_bech32_for_prefix(prefix.clone()) {
Ok(_) => (),
@ -247,7 +236,7 @@ pub fn generate_vanity_wallet(is_testnet: bool, num_threads: u32, prefix: String
let mut handles = Vec::new();
for _i in 0..num_threads {
let testnet_local = is_testnet.clone();
//let testnet_local = is_testnet.clone();
let prefix_local = prefix.clone();
let tx_local = mpsc::Sender::clone(&tx);
let ps_local = please_stop.clone();
@ -256,7 +245,7 @@ pub fn generate_vanity_wallet(is_testnet: bool, num_threads: u32, prefix: String
system_rng.fill(&mut entropy);
let handle = thread::spawn(move || {
vanity_thread(testnet_local, &entropy, prefix_local, tx_local, ps_local);
vanity_thread(&entropy, prefix_local, tx_local, ps_local);
});
handles.push(handle);
}
@ -264,7 +253,7 @@ pub fn generate_vanity_wallet(is_testnet: bool, num_threads: u32, prefix: String
let mut processed: u64 = 0;
let now = SystemTime::now();
let mut wallet: String;
let wallet: String;
// Calculate the estimated time
let expected_combinations = (32 as f64).powf(prefix.len() as f64);
@ -300,7 +289,7 @@ pub fn generate_vanity_wallet(is_testnet: bool, num_threads: u32, prefix: String
}
/// Generate a series of `count` addresses and private keys.
pub fn generate_wallet(is_testnet: bool, nohd: bool, zcount: u32, tcount: u32, user_entropy: &[u8]) -> String {
pub fn generate_wallet(nohd: bool, zcount: u32, tcount: u32, user_entropy: &[u8]) -> String {
// Get 32 bytes of system entropy
let mut system_entropy:[u8; 32] = [0; 32];
{
@ -332,10 +321,10 @@ pub fn generate_wallet(is_testnet: bool, nohd: bool, zcount: u32, tcount: u32, u
let mut seed: [u8; 32] = [0; 32];
rng.fill(&mut seed);
return gen_addresses_with_seed_as_json(is_testnet, zcount, tcount, |i| (seed.to_vec(), i));
return gen_addresses_with_seed_as_json(zcount, tcount, |i| (seed.to_vec(), i));
} else {
// Not using HD addresses, so derive a new seed every time
return gen_addresses_with_seed_as_json(is_testnet, zcount, tcount, |_| {
return gen_addresses_with_seed_as_json(zcount, tcount, |_| {
let mut seed:[u8; 32] = [0; 32];
rng.fill(&mut seed);
@ -352,7 +341,7 @@ pub fn generate_wallet(is_testnet: bool, nohd: bool, zcount: u32, tcount: u32, u
/// get_seed is a closure that will take the address number being derived, and return a tuple cointaining the
/// seed and child number to use to derive this wallet.
/// It is useful if we want to reuse (or not) the seed across multiple wallets.
fn gen_addresses_with_seed_as_json<F>(is_testnet: bool, zcount: u32, tcount: u32, mut get_seed: F) -> String
fn gen_addresses_with_seed_as_json<F>(zcount: u32, tcount: u32, mut get_seed: F) -> String
where F: FnMut(u32) -> (Vec<u8>, u32)
{
let mut ans = array![];
@ -365,7 +354,7 @@ fn gen_addresses_with_seed_as_json<F>(is_testnet: bool, zcount: u32, tcount: u32
// First generate the Z addresses
for i in 0..zcount {
let (seed, child) = get_seed(i);
let (addr, pk, _vk, path) = get_zaddress(is_testnet, &seed, child);
let (addr, pk, _vk, path) = get_zaddress(&seed, child);
ans.push(object!{
"num" => i,
"address" => addr,
@ -380,7 +369,7 @@ fn gen_addresses_with_seed_as_json<F>(is_testnet: bool, zcount: u32, tcount: u32
let mut rng = ChaChaRng::from_seed(rng_seed);
for i in 0..tcount {
let (addr, pk_wif) = get_taddress(is_testnet, &mut rng);
let (addr, pk_wif) = get_taddress(&mut rng);
ans.push(object!{
"num" => i,
@ -394,9 +383,9 @@ fn gen_addresses_with_seed_as_json<F>(is_testnet: bool, zcount: u32, tcount: u32
}
/// Generate a t address
fn get_taddress(is_testnet: bool, rng: &mut ChaChaRng) -> (String, String) {
use secp256k1;
use ripemd160::{Ripemd160, Digest};
fn get_taddress(rng: &mut ChaChaRng) -> (String, String) {
// use secp256k1;
use ripemd160::{Ripemd160};
let mut sk_bytes: [u8; 32] = [0;32];
@ -416,37 +405,37 @@ fn get_taddress(is_testnet: bool, rng: &mut ChaChaRng) -> (String, String) {
// Address
let mut hash160 = Ripemd160::new();
hash160.input(sha2::Sha256::digest(&pubkey.serialize_compressed().to_vec()));
let addr = hash160.result().to_base58check(&params(is_testnet).taddress_version, &[]);
let addr = hash160.result().to_base58check(&params().taddress_version, &[]);
// Private Key
let pk_wif = sk_bytes.to_base58check(&params(is_testnet).tsecret_prefix, &[0x01]);
let pk_wif = sk_bytes.to_base58check(&params().tsecret_prefix, &[0x01]);
return (addr, pk_wif);
}
/// Generate a standard ZIP-32 address from the given seed at 32'/44'/0'/index
fn get_zaddress(is_testnet: bool, seed: &[u8], index: u32) -> (String, String, String, json::JsonValue) {
fn get_zaddress(seed: &[u8], index: u32) -> (String, String, String, json::JsonValue) {
let spk: ExtendedSpendingKey = ExtendedSpendingKey::from_path(
&ExtendedSpendingKey::master(seed),
&[
ChildIndex::Hardened(32),
ChildIndex::Hardened(params(is_testnet).cointype),
ChildIndex::Hardened(params().cointype),
ChildIndex::Hardened(index)
],
);
let path = object!{
"HDSeed" => hex::encode(seed),
"path" => format!("m/32'/{}'/{}'", params(is_testnet).cointype, index)
"path" => format!("m/32'/{}'/{}'", params().cointype, index)
};
let encoded = encode_address(&spk, is_testnet);
let encoded_pk = encode_privatekey(&spk, is_testnet);
let encoded = encode_address(&spk);
let encoded_pk = encode_privatekey(&spk);
// Viewing Key is encoded as bech32 string
let mut vv = Vec::new();
ExtendedFullViewingKey::from(&spk).write(&mut vv).expect("Can't write viewing key");
let c_v: Vec<u5> = vv.to_base32();
let encoded_vk = Bech32::new(params(is_testnet).zviewkey_prefix.into(), c_v).expect("bech32 failed").to_string();
let encoded_vk = Bech32::new(params().zviewkey_prefix.into(), c_v).expect("bech32 failed").to_string();
return (encoded, encoded_pk, encoded_vk, path);
}
@ -465,18 +454,9 @@ mod tests {
fn test_wallet_generation() {
use crate::paper::generate_wallet;
use std::collections::HashSet;
// Testnet wallet
let w = generate_wallet(true, false, 1, 0, &[]);
let j = json::parse(&w).unwrap();
assert_eq!(j.len(), 1);
assert!(j[0]["address"].as_str().unwrap().starts_with("ztestsapling"));
assert!(j[0]["private_key"].as_str().unwrap().starts_with("secret-extended-key-test"));
assert_eq!(j[0]["seed"]["path"].as_str().unwrap(), "m/32'/1'/0'");
// Mainnet wallet
let w = generate_wallet(false, false, 1, 0, &[]);
let w = generate_wallet(false, 1, 0, &[]);
let j = json::parse(&w).unwrap();
assert_eq!(j.len(), 1);
assert!(j[0]["address"].as_str().unwrap().starts_with("zs"));
@ -484,7 +464,7 @@ mod tests {
assert_eq!(j[0]["seed"]["path"].as_str().unwrap(), "m/32'/133'/0'");
// Check if all the addresses are the same
let w = generate_wallet(true, false, 3, 0, &[]);
let w = generate_wallet(false, 3, 0, &[]);
let j = json::parse(&w).unwrap();
assert_eq!(j.len(), 3);
@ -626,7 +606,7 @@ mod tests {
use std::collections::HashSet;
// Check if all the addresses use a different seed
let w = generate_wallet(true, true, 3, 0, &[]);
let w = generate_wallet(true, 3, 0, &[]);
let j = json::parse(&w).unwrap();
assert_eq!(j.len(), 3);
@ -649,7 +629,7 @@ mod tests {
}
/// Test the address derivation against the test data (see below)
fn test_address_derivation(testdata: &str, is_testnet: bool) {
fn test_address_derivation(testdata: &str) {
use crate::paper::gen_addresses_with_seed_as_json;
let td = json::parse(&testdata.replace("'", "\"")).unwrap();
@ -657,7 +637,7 @@ mod tests {
let seed = hex::decode(i["seed"].as_str().unwrap()).unwrap();
let num = i["num"].as_u32().unwrap();
let addresses = gen_addresses_with_seed_as_json(is_testnet, num+1, 0, |child| (seed.clone(), child));
let addresses = gen_addresses_with_seed_as_json(num+1, 0, |child| (seed.clone(), child));
let j = json::parse(&addresses).unwrap();
assert_eq!(j[num as usize]["address"], i["addr"]);
@ -690,304 +670,4 @@ mod tests {
generate_vanity_wallet(false, 1, "i".to_string()).expect_err("i is not allowed");
generate_vanity_wallet(false, 1, "1".to_string()).expect_err("1 is not allowed");
}
#[test]
fn test_taddr_testnet() {
use crate::paper::get_taddress;
use rand::{ChaChaRng, SeedableRng};
// 0-seeded, for predictable outcomes
let seed : [u8; 32] = [0; 32];
let mut rng = ChaChaRng::from_seed(seed);
let testdata = [
["tmEw65eREGVhneyqwB442UnjeVaTaJVWvi9", "cRZUuqfYFZ6bv7QxEjDMHpnxQmJG2oncZ2DAZsfVXmB2SCts8Z2N"],
["tmXJQzrFTRAPpmVhrWTVUwFp7X4sisUdw2X", "cUtxiJ8n67Au9eM7WnTyRQNewfcW9bJZkKWkUkKgwqdsp2eayU57"],
["tmGb1FcP31uFVtKU319thMiR2J7krABDWku", "cSuqVYsMGutnxjYNeL1DMQpiv2isMwF8gVG2oLNTnECWVGjTpB5N"],
["tmHQ9fDGWqk684tjWvvEWZ8BSkpNrQ162Yb", "cNynpdfzR4jgZi5E6ihAQhzeKB2w7NXNbVvznr9oW26VoJCGHiLW"],
["tmNS3LoTEFgUuEwzyYinoan4AceJ4dc21SR", "cP6FPTWbehuiXBpUnDW5iYVayEKeboxFQftx97GfSGwBs1HgPYjS"]
];
for i in 0..5 {
let (a, sk) = get_taddress(true, &mut rng);
assert_eq!(a, testdata[i][0]);
assert_eq!(sk, testdata[i][1]);
}
}
#[test]
fn test_taddr_mainnet() {
use crate::paper::get_taddress;
use rand::{ChaChaRng, SeedableRng};
// 0-seeded, for predictable outcomes
let seed : [u8; 32] = [0; 32];
let mut rng = ChaChaRng::from_seed(seed);
let testdata = [
["t1P6LkovpsqCHWjeVWKkHd84ttbNksfW6k6", "L1CVSvfgpVQLkfwgrKQDvWHtnXzrNMgvUz4hTTCz2eX2BTmWSCaE"],
["t1fTfg1m42VtKdFWQqjBk5b9Mv5nuPo7XLL", "L4XyFP8vf3UdzCsr8Ner45sbKSK6V9CsgHNHNKsBSiysZHaeQDq7"],
["t1QkFvmtddEjzk5GbLRaxW3kGh8g2jDqSHP", "L2Yr2dsVqrCXoJ57FvC5z6KfHoRThV9ScT7ZguuxH7YWEXboHTY6"],
["t1RZQLNn7T5acveY5GBvmhTWh9qJ2vy9hC9", "KxcoMig8z13RQGbxiJt33PVagwjXSvRgXTnXgRhHzuSVYZ9KdGUh"],
["t1WbJ1xxps1yQ6hoXszV4j7PR1fDF7WogPz", "KxjFvYWkDeDTMkMDPogxMDzXM12EwMrZLdkV2gp9wAHBcGEcBPqZ"],
];
for i in 0..5 {
let (a, sk) = get_taddress(false, &mut rng);
assert_eq!(a, testdata[i][0]);
assert_eq!(sk, testdata[i][1]);
}
}
/// Test data was derived from zcashd. It cointains 20 sets of seeds, and for each seed, it contains 5 accounts that are derived for the testnet and mainnet.
/// We'll use the same seed and derive the same set of addresses here, and then make sure that both the address and private key matches up.
/// To derive the test data, add something like this in test_wallet.cpp and run with
/// ./src/zcash-gtest --gtest_filter=WalletTests.*
///
/// ```
/// void print_wallet(std::string seed, std::string pk, std::string addr, int num) {
/// std::cout << "{'seed': '" << seed << "', 'pk': '" << pk << "', 'addr': '" << addr << "', 'num': " << num << "}," << std::endl;
/// }
///
/// void gen_addresses() {
/// for (int i=0; i < 20; i++) {
/// HDSeed seed = HDSeed::Random();
/// for (int j=0; j < 5; j++) {
/// auto m = libzcash::SaplingExtendedSpendingKey::Master(seed);
/// auto xsk = m.Derive(32 | ZIP32_HARDENED_KEY_LIMIT)
/// .Derive(Params().BIP44CoinType() | ZIP32_HARDENED_KEY_LIMIT)
/// .Derive(j | ZIP32_HARDENED_KEY_LIMIT);
/// auto rawSeed = seed.RawSeed();
/// print_wallet(HexStr(rawSeed.begin(), rawSeed.end()),
/// EncodeSpendingKey(xsk), EncodePaymentAddress(xsk.DefaultAddress()), j);
/// }
/// }
/// }
///
/// TEST(WalletTests, SaplingAddressTest) {
/// SelectParams(CBaseChainParams::TESTNET);
/// gen_addresses();
///
/// SelectParams(CBaseChainParams::MAIN);
/// gen_addresses();
/// }
/// ```
#[test]
fn test_address_derivation_testnet() {
let testdata = "[
{'seed': '95b888ec34bc8bd9fa9ed85fe5d81098b7326aa230bed52cc41e940c2664d894', 'pk': 'secret-extended-key-test1qvc94y54qqqqpq8dek8kzzj8p9algn0x527np3fge269jnrw28yvmhkyx6k8mcmde0v4lnw34ds8ecjd0wjld7vqznxn7mdq75vrynehr6z80unnqshqnryrnkvemd2p8me2ttgj08y4pr3jddffndcupxq6caxuhaeh9wgvpnqge9vn30jfj65q4pklx6q2xmq5n85pre3u630zza7k2h722kperqfl28y5uwhduxgagr3gjq8fjprkn05dz2pw2cn5zl4sjyz9lhg69xjqn', 'addr': 'ztestsapling1gptd43m0nucwvay39zx9euvcl2ez6ddu6xnqdv2epjfhtnqq8nvrv72s9v803m63yy5jkaktnp7', 'num': 0},
{'seed': '95b888ec34bc8bd9fa9ed85fe5d81098b7326aa230bed52cc41e940c2664d894', 'pk': 'secret-extended-key-test1qvc94y54qyqqpqxrjyzancu5c4h7wcqjss7tuxl3grjq9pzs478w7qfy74t2tdeydrz54fq75y2c6s494z46sz7vjfssn4t9470l828gjjnjmr2ehq8qjknenwnf7k7f697y4fv22maatklmngu25audf0glu0all08lrhqff8u0gvlfqxgdfah64vg9tud7c5avdkcqa38mrdhza5rrmgpsyfkspz4myjrhty4dy3en3rxvarncuup3dkzqs9fng48qsp38s5ty2aqnzlec0', 'addr': 'ztestsapling1vt9p9pu4yr8kv2ljja7wq2sennvwu9e5scu03q6k2afq7m826yqehp3kr9s40nyd2mcwymle7sj', 'num': 1},
{'seed': '95b888ec34bc8bd9fa9ed85fe5d81098b7326aa230bed52cc41e940c2664d894', 'pk': 'secret-extended-key-test1qvc94y54qgqqpqq2n0jn9e36f52p793en8cj5w5le8f9nlv6wm9qmnmuhdku76wcwltdagfky05xatnuv3nfs30wqu38z4h53e4g7hsl4q2ftz8ahhlqjy7jenj9sn3en09sn73xqla30kwme27m08njxeva4az0609w4xqz2mhprc2tapa42murm272l0gcrep4tevm2gfe2kzgxj2076nq6r6wj65le4h0ct56ezvt0ccwhyszkgxatdx6d9shk4um6t634q2d04szre5eh', 'addr': 'ztestsapling1hcnhcnjhj0hrnytyv9rtaza9dzkasn37k8g6ht9rvgq60dm0jqfdsxvrgcztx69dyt4pvhedkka', 'num': 2},
{'seed': '95b888ec34bc8bd9fa9ed85fe5d81098b7326aa230bed52cc41e940c2664d894', 'pk': 'secret-extended-key-test1qvc94y54qvqqpq95hkx6uqzyy5hs2nthf2dvr7as47pz7dk6nvr6calnj2tknt07fjvuv4n8zrs4ez5tl0pptdwd0h5xr6f8c0asmsx6wnjgvx0fj5eqhw3c08g72nfl7ysh2z4td4pvfhm5esadq7n46nt7h0ae4exkrjsp5e86p47p2qvum6y6k2qfxyz3r3v0mdls84kk6pndpchfsa4d7txpg53tumxd2cv3tx2e3wzqnr7l8vnzkksq3adqr2hrfq93gvy78mqtqpt28', 'addr': 'ztestsapling1qp2e5vtwkzss4902mmc9dff08al0360q5ytpmz9qmrwtkdjpy6v8u3yk7nska6xujzvc7vm3rs5', 'num': 3},
{'seed': '95b888ec34bc8bd9fa9ed85fe5d81098b7326aa230bed52cc41e940c2664d894', 'pk': 'secret-extended-key-test1qvc94y54qsqqpq8t3zw2y4uejtfew9ec285pkd3vfjzn8lh9z0dfwfnvhvdgv3fuqgm5p5gpszhqe5lskpve462m4ffrxnprwnpvn0esr79rzmwzwa7s04ht3y0m3ywllunzk5gc95qqvy5656eqzn7l35dlxc4dehmwnec9ucehqqvqyh3ma5maqsu6pv52dsalugvcqw6rdwgzd6d86q8smggyqkgevxqjkz4mrey46yllfm5klsxserxhs7m04k7y74zvszewkkqsa2uhf', 'addr': 'ztestsapling1z4ts6phgufxzu3lxnegmep43nxd7tv4r5xjavgdn5psvjwpct95jc5kq6ffv9fdmkq2jyfahqfn', 'num': 4},
{'seed': '87cce4fa25d7b24ad2348c1300f8c7dc4827515a35e7c39f2fcd054ea1ab79de', 'pk': 'secret-extended-key-test1qvv8kw2aqqqqpqys5u3288xczy3dth7l9kghpcxsvg5mjc5yar75wxynktt5hfm2alex3xtfclt6zxkrk0ky5a0l6fsxsn3yequrvuexjepn6t5fgr4scjdz3k5kjt3j2lwzmgv9wsalf6zmc2vkaa2s8jng6xf2f6ndsgq9f86wmdg8x046tuws764wk98hay48mplh40ltknwud0gvuq4ucpvvmesm5m52dxjyw32gsufjum4f8aazd9e6a0dgefj79tfasy2x66gpzpavw', 'addr': 'ztestsapling1588cxnf3jyfe62sfaspfy53pwnf8zglam0qnnf5ndnhte4ur5skuufncw93sefley8nzjnzcad2', 'num': 0},
{'seed': '87cce4fa25d7b24ad2348c1300f8c7dc4827515a35e7c39f2fcd054ea1ab79de', 'pk': 'secret-extended-key-test1qvv8kw2aqyqqpqp9aqw6ff5fe3yftk6c0qtts8qjdkcr056j87xh3v8ktlvnxed7u8f5jjsrxfark6hshpljr3jgy8pdm83ew5ga4z40v7dfp7q5esgshvapmnp5atrly6l8nwv96egwfrrugwk9zvg9su8h6a7x3zyyt4sp8mhx6dgzefv9rtk4llrp6x0f200vnu8a9zl0nyv0uhadywg4yf6h8nam2akca50wzgeg30t4qtmy5t2n4hajcc0afcsgkh6pt7p6e4srv9qkc', 'addr': 'ztestsapling1dlgr9wshy269h4tx70anfaz4uswx8z5470zkegwu34nu5gtvl74fee50gdmfm8tsp6t95nfupqm', 'num': 1},
{'seed': '87cce4fa25d7b24ad2348c1300f8c7dc4827515a35e7c39f2fcd054ea1ab79de', 'pk': 'secret-extended-key-test1qvv8kw2aqgqqpq8rwzynx9yd5ywcpprckglunr3dz20qc5edm7p03xaqnrhxehlx6ntrcktxj4s2stlkfkvf7s2t4f3z0ewaxxnupr2zswf4ujya3rxs2n5v2gtzymlal6lln8h3ghk80vtfc0f0wylrw5grzd99sg7vv6gf6w4ew7rwc5lngauzfwzeeykd37utg2w822anv3zp05dyge802tht4krtzee0ktaucfxssqw9h420tu43m2r4rtveavwdpxaqu4jd0psj9j4hy', 'addr': 'ztestsapling1k6ypwvdhxurmeckwvnmc0n7g49rfh9ejq6nnqt44fwnf2696aulas537awwc2rlccecru2axmgd', 'num': 2},
{'seed': '87cce4fa25d7b24ad2348c1300f8c7dc4827515a35e7c39f2fcd054ea1ab79de', 'pk': 'secret-extended-key-test1qvv8kw2aqvqqpqp6ar8atq7k3cvjyny72jf3vc794e5gedqluunf8q0su6g8z2e23t77yrdkf5dkpmmua5ztqqve9d2vjssdnu8wpmr6vyl42ugmhkpsz383r9tknvc6ahx2em8j62h5w9ldlqxtpd5v96jrmzd6t4mpvcctr9m6l282xuvmp77cmzrekg7xwdaj70nhmlrwel8565dmlqc699z6ds7u2c4aev80xevkmltfyzxj6etktnkldvwqlmjuf3e75mwe70gnaupym', 'addr': 'ztestsapling12d4g8tmy6a5gue5nxyxkj3uwu0ewsckrnd5saaqhrx54cc3fmpac9lfqt7u4dre2f6fdxj0dl7z', 'num': 3},
{'seed': '87cce4fa25d7b24ad2348c1300f8c7dc4827515a35e7c39f2fcd054ea1ab79de', 'pk': 'secret-extended-key-test1qvv8kw2aqsqqpqp7eveuynjc5q9c5kwmxk5n0atzhkx74qxcf2nduq0gpchpjyn4n2l6csmkeh3lk7eweuc62uyc2q49nj9ezhyavdy28a4m563ft0fst63ar3ytg23qvs0rwh6dz7vymkm6dkdcevp7qpavgqltu6ezxuq2vh68yqculz8vh383fsetkv0x4s9dqrhcke339vq0f2sg5glm75k00td05pcz82l7e6z6vr5ekrapfcnmped998m62hcfvuafeuxw4ug5fc7mu', 'addr': 'ztestsapling15lddvl4p4ejp5lx9w2dwhtunt5kppwq57g5fz0jyxpz6jqwfjelhcpmnulg5xpsrgtgzjx7jgsr', 'num': 4},
{'seed': '18ad78821cdce1adc843d35c7f44c8a6a9d334f2bb015a009b29b386312d5399', 'pk': 'secret-extended-key-test1q0lh790aqqqqpqyg4wyjp7t2ypsadf30gvzvgq4qgtnnlffdutdsg5r5h04ze0q9dhr2qmrzpqkfhk87aknc4myfjsdg28g6chfxp4sx2k0200t99rkq3u57lxmfwymg3dx9vhjc5uh5524mtrhp4e9pvwsvxu0fe32jrncq9cf8zqdapc0l82nlw53sztu5l8k9czrrmnkdelww9ychalw3hhcqg53xyc39aaf43jjdtsfreyhcyv3a95cmpa9kyj93xq3zx300tpg3dq72c', 'addr': 'ztestsapling1c4af06lpa30zergu85mvuxkxn6prsye46vw84qznvzc7pgu4hq4gjwt43fvllvdh6aypkewgryr', 'num': 0},
{'seed': '18ad78821cdce1adc843d35c7f44c8a6a9d334f2bb015a009b29b386312d5399', 'pk': 'secret-extended-key-test1q0lh790aqyqqpqy6s9x6k5j2ngn3q9k5cl2qhkr37smr2t5hgjnycwmnuff3fmw2d8t5nwa50q7y5xw2ap3zmek83dprt4g0rc4ezfas79t69l5vk97qxl4upjyjykqypu8emt4nylzmtarv9jez6zjwf2rd75qpzxgyc3sx3u5l4q2lz7ltuq29yh3zxqx3h58jtnpzd985hfysrmlvumghgmm524xmr73ht4jv7kfq55lv90y8zw2c4y4kr3tx9z3g9496sywp2hg79s63l', 'addr': 'ztestsapling1vqgvwtjd0lxwpl37ppvgrxsnmqssvptwtte6xag76az4c7jdrxrr04mf3xc7pu3pwp58zxq0krq', 'num': 1},
{'seed': '18ad78821cdce1adc843d35c7f44c8a6a9d334f2bb015a009b29b386312d5399', 'pk': 'secret-extended-key-test1q0lh790aqgqqpq995sf4u50r7w8d3rjkzgl0cs734jwz06aq6pwtcajy7r9tpuqyse0xwtxaeavgs5pcexeaaxtun3hxf03dmj9u3473eqtj5te80x8stkgjajshyjaernd2nza29a2z2dzmp5l5jlx2g4jcnawu5565vpqqqujscy54n2fe0xus25u2yppj45aczf5jkg3yxt470aykhm0q2lx2n97tsg28j02h9lk4nlhmmq5nt4kv5jqr08452zgppxu5s4anrjs0ae8j6', 'addr': 'ztestsapling1qn9xcy7a2csynpsqyqec5z6nkax2ud3jzxju9fe24s72fw74pzcft04qq3xteszv79a6wfls6ek', 'num': 2},
{'seed': '18ad78821cdce1adc843d35c7f44c8a6a9d334f2bb015a009b29b386312d5399', 'pk': 'secret-extended-key-test1q0lh790aqvqqpqxz64828w9h4yxe3synl632e79k6rhd2atdanlln6zmgxlzjt8fqp8rvlppslj9vtdk5gxreclm8kmmmxx2dhwemk0hpulengmzjc9s4kyxklqehqpyljajftr2ug6mlv7qdjre8rn8ycfgvafeurjgxyqqvjm5wmgz8px3n0qg055x0m042vmu65skmrlqh79ve5rlavyj6z3uxnupjsfukqy7k6yvamsvknlhmuvd87f2vwwp424cdwunavep4vgjxfelw', 'addr': 'ztestsapling1dcltlz6kutc05xkv2ldapjx55phte2vztrz2em446h9j322d5m9w89mc3m06dlfkkgwqw0yer5x', 'num': 3},
{'seed': '18ad78821cdce1adc843d35c7f44c8a6a9d334f2bb015a009b29b386312d5399', 'pk': 'secret-extended-key-test1q0lh790aqsqqpq8dxw2u9gzuwz6qc9a539f2qzpc3nlea48nlek0f3rsvu6czdxapeeguw86pn2k69c2p65dvyckevdrlg6d6wstvj6spt2drnuxqpds32qplv8fsxkemq27j4enjqv0sqyxq7lhjsgtkhmalrd9fcvgc6cr324g7256wtu687hwss690mycrt3rpsu08qffq2fflc23vty2q6cjq2w3ap045cc072nrrr3a99xrz8a2lhmgfg7qm87qkegu09uur0g74nk3e', 'addr': 'ztestsapling12xqmv94ys6n6lkw7mm4ygndun3cmhlwy4t6ctaghgq2hrykd6me9dfslyg7e3zzmzwlnqcwrx2x', 'num': 4},
{'seed': 'b1e83b6dd89145d2d30a086b17c85f7b8a027dba30a1667aef8b66a1d9c6dab9', 'pk': 'secret-extended-key-test1qvjd97tpqqqqpqxcpfdf4d3y9e0vsf95udeky69vcsysg545cr3pjy3xq5stdd9enc70j75vj2lzg9hcd93tq5ehcsym30a8lcncafnzs5hl6v4hjzuss0hfyaae5xupudd7tnnd5hk4k4sreswurt24gp30h7jetpnp8sgzvzg23g9rztuperzjnv3jw3dt42pqramw0u5ah9frz3yjqr0axxyeu2t826v0mkvej4xe6gfpkr7tgl97vdcgyk4k23hs3qf7wvpltwqrlmw67', 'addr': 'ztestsapling1u2lxyj535dt5v6ee2vxr7k7eec0ut0n6hsl35l5dm52e5k888e9ut9h4j9nmdc3lvqdywptkvkw', 'num': 0},
{'seed': 'b1e83b6dd89145d2d30a086b17c85f7b8a027dba30a1667aef8b66a1d9c6dab9', 'pk': 'secret-extended-key-test1qvjd97tpqyqqpqqcwzvt47jgd2jn4ghqpfczydx9n2qdgx8yqnm7c6xp72kqd7wyfwn5la42378etwvaa5wxxlndemj2h9xndw63vhkqlq7slvjavzuqxtenqrrarvja7sctwjj04l2ck2ekhgkytkjsn2gdvkehussf66gynk6pdaep503qe7acvzuev7crsk4tqnxsh4ght2qvxzxvs4kvyaa9qt4wqp2jjrueaa7aggpvnh6f70htd474fat07963ztl6akj6w5gsfdvlq', 'addr': 'ztestsapling13lhlvphjehn3v3w9s8y0fkjk3st2utapegum78jxdnn7k82q359sy7s84ls22mcr7gkzz9ujz7s', 'num': 1},
{'seed': 'b1e83b6dd89145d2d30a086b17c85f7b8a027dba30a1667aef8b66a1d9c6dab9', 'pk': 'secret-extended-key-test1qvjd97tpqgqqpqp2apeq85267phgdudj78dv0cnpjfs9wm483u30h3qn2ufu59hfx5aj4xqmzdme0xuwkd5cx37t0vg5ctv2qyh43say7fsyqfgk2ltqxhjlyq39xvx6auw9fjj8hsn7a9uy646n3lvegtelhvjlcp5cg7ctwgh0lf42wnx5efg88us38rk0p4w5sgz44tffp6upeut322ltp7fle6yeahes6uqvgyw5qulust8qs5nj0pfx5qnatawnndxj769g30qrcz7p3', 'addr': 'ztestsapling139d3n0qxkfvqqzyd84m0mk886mkpaztk9zcpr7elezzuvnwqqukh33cph9vq6aqe9vtlxppxkty', 'num': 2},
{'seed': 'b1e83b6dd89145d2d30a086b17c85f7b8a027dba30a1667aef8b66a1d9c6dab9', 'pk': 'secret-extended-key-test1qvjd97tpqvqqpqq5y3zf4fa0g9fqsqkqcy8l26lq9fq2hfue9k5mk0zuar3r2aulk7eamv83wp3w62dm7y7gcnmvn7760u2z30fv0p9gu3x0p045kd5s0wesmy9pc9kmylfvyhrdecgvqm3djjxgm093rv48neenvzpkt4g2574k4g2z0dn576enchyq3uwgtsqws8nff73smlux9q92auwgvvz7prymu9lv9e3sgjxrh8gnv729t6gxnylj30am7wx9kjt5r8cnp6sjta3ed', 'addr': 'ztestsapling1qjnummr3jqn9e78muy6yasw2aaseyc76t6cxtxd3ys2ycrcn5rtlpv5w6ha72ljd55mm5uh2z4m', 'num': 3},
{'seed': 'b1e83b6dd89145d2d30a086b17c85f7b8a027dba30a1667aef8b66a1d9c6dab9', 'pk': 'secret-extended-key-test1qvjd97tpqsqqpqrzyu7n9tjavxvxtcz726ud0lyx9r329vjmdu7vyqtqseu42ceh32n7qud70m4x2cjzknvtnw60kjwqaceqlyzdhxg6uypsf7mh9p3q5fd0ck4kknrss6a6x7znk58seczq8jyyd9mclggefx0d7schuhqf074xsghpdvktr044cmp5t8cl4k6dxyrvh4lm4pqmvytlt934us89z7gc7q8sq2fvmq8mxyy9utjlpwz05kcynw0kwgwr7eu6v73fhhszkf3mm', 'addr': 'ztestsapling1e2hr08hwr7w47ahwyc06zygjdnp2erpjas3r4z96hhq9433y8d6lmf8gurs7p3ch2g72sqlr4vh', 'num': 4},
{'seed': 'e9bbc064c0f6caa20879da5e1fae80ba988552b2a250dae5fd1b44f1ae165a16', 'pk': 'secret-extended-key-test1q035xys0qqqqpqykajxmrvecmm65nqz9mknkq8z2hvn7lkp9vpnr8e309djh3h8mlagp86ytvwtp6wxlcdlwz059cjuygv7wx69dkyptre6xnt67zxus0uhesmswex8wcadrt70ug4dv7e3pkfsvqkg6gct8tlay8xwg9pcyhgmyv0kddvdkajnczjmwtu82ssh7q06ezmzdupe3he04sk2x453fmv0r229ya5e2x9a99s4qnqvswvhsykeekm4vft36nkvyzkdvs6gz6gv3p', 'addr': 'ztestsapling1fqvxg9gc38me72xm2nde4jzdz46zma6lpqdfagypfxqw5kmlwtt7plsh3vvcgwj66a3xzl6wn5v', 'num': 0},
{'seed': 'e9bbc064c0f6caa20879da5e1fae80ba988552b2a250dae5fd1b44f1ae165a16', 'pk': 'secret-extended-key-test1q035xys0qyqqpqr67h7xdj32mdgv5znre2pmdm2amc2hgdqgm0986y7y2nyke4estn8kugt8ensc4f3asjtxrznw9p6knfy0w9em5s7txygj2kyqekasj59zu7akvzvf2q5egmcckrghplupp4keh3vn4n8sgh0dqz5pl3c88gte2ccke3cnrwrgzr2gpzxwfzuun84ngchazjvpaumcsxvafgvy7gfzdyk5jlwfgyhaktqdmejmnd5ktw2mzh9msde4dnwpx6cc8gqjyrsdw', 'addr': 'ztestsapling1twx5dhz96magseaxxq4zdkrehgjs3vtl40ldzvyp70qk97kgzhyktfa74zw9a8sygu2pjzj7umw', 'num': 1},
{'seed': 'e9bbc064c0f6caa20879da5e1fae80ba988552b2a250dae5fd1b44f1ae165a16', 'pk': 'secret-extended-key-test1q035xys0qgqqpqpfa9c2qdx9maxdy4urqvvapjtv9jrdz302fqemddt229qp7p42xusf94uqdxvd9xu38ay2886qnnplajwl4a458xzm9v2hlzhu9ueqkr0kra2hk2wxnh8vpl630mpzlyxyyv6uk560t0tl6wyplqpxlyc8wh5fy5pfx9frfk68z3ntceedk4tgpecnc09ggzp6hlq65gl2v7ym42xwsjcylrcx2vjxazv79tvcyhvyw3770h5ehknkcuwk3v6vx7gwgtdjk', 'addr': 'ztestsapling1ew7ht352r5c7mcmrkstekskrc4fmx0vfu3vvl3tur22lyggun58lxuqqdecmmanmwgtkzk597ff', 'num': 2},
{'seed': 'e9bbc064c0f6caa20879da5e1fae80ba988552b2a250dae5fd1b44f1ae165a16', 'pk': 'secret-extended-key-test1q035xys0qvqqpqxg98wkn7mxuy0hgk78mysqvz36nndupaeu6z94tfypl8xyfwtvex7cwdsvzpem8sys3udxu9amntaqy4aauzx8kf7q3ec8d337jnzqrye6w98qq8hqlrv4zwu5pntza83tysfvr320sc6hhp7y7mer5tsxal7dye59hfs846rsc5tzzya8crel6kzmd73aqta5mhwhkjyctu88dnl66kpggfxulk70ulh2yl3nynqdgznf42fgp079eyym30hvvvqtkawl4', 'addr': 'ztestsapling1u4s7j6p7r8h0rgl8naddfe6fyrdml9jk09jy274x4swt3rmtjdjfuuqg06yxnvj2n4fdkl9yshn', 'num': 3},
{'seed': 'e9bbc064c0f6caa20879da5e1fae80ba988552b2a250dae5fd1b44f1ae165a16', 'pk': 'secret-extended-key-test1q035xys0qsqqpqqrdcmx0en8rhj479e9fpwk6afw6g5g2t6x0yzvwtnq0tt4gmvxt3d0wtarpdxf673yg7munp2qfm26z6fawql984kppj7r9sek0k0s4tymjhnpu8xwnxc8ng8e9p6z8pzlwwmnwrn9nyz6auplpv2vd9splxruqz5l2ew7nxhrvtp3m5m2qjawpz5fu5w8trdf8lapqydtk7ej203jutmthgshazt4647cmm4nmz3phsz68gcaz74awjka0acle6glslttq', 'addr': 'ztestsapling16jy7l6gljwve9a2srmcpzrlxgkqtagxz6tvep2v6vgj0fckvgm0tm2tu0a2vk45pd2s6zy6cnqf', 'num': 4},
{'seed': '5956035daff67270bc37ea6178d7288afc39151738e29da8d3008465f70c8b4f', 'pk': 'secret-extended-key-test1q0azmr3lqqqqpq9fn4dr9a2av3mfa8yxh7fqj4q4z96gqmfq0rqlwvtjf2gke2vh7zl639wce7dqmhqt8cd66ygsqg8g5up99zxujrnhqsrtltkpwjgqymzw6k850hp3h09z8ehcyv77cqejaftu2s8phjk2gmgm6rk5mjgr4d4e4n8zgc6h0dh3hjlrarv2ex5cs2htcgukmfcj246qxpzz2k55ql9h56w26nmg297ekghv3lu3nzgscllrdj8gxqtq20knrfs3axcpr7mrx', 'addr': 'ztestsapling1tq02egtacv2uxcp3g07e8fw9eupfegr3pd9dayt6fh8exh0gsvdsge2d57j0ax039cv9s6t0avw', 'num': 0},
{'seed': '5956035daff67270bc37ea6178d7288afc39151738e29da8d3008465f70c8b4f', 'pk': 'secret-extended-key-test1q0azmr3lqyqqpqr9ql2m6l869zh3gv5lk9zr3v34m8nrn608plyr06jx4vrrekxsnf490w7psewp9uvvk0y4pjuzz2hj0elay39cjdyzuyzqvrm4y59qne73p5cz8hm9xnt3sndvce78c4crqcqtdd083pxk4wct2mr2c4cvnypddca3lmxdvu2xqvc8upmsk53up9ppwftkqtytym6z9n9apulcelzd0te7j669tywg8lu4lnkfevm28mclkd3yh028d7pm4sxsawqs42raw', 'addr': 'ztestsapling105ndc8aq8mhwmgxs29whype8k4v3ntl7adwsuqh2zkqk9c0ra8squffu2qljhs5gfw3vv86vnxy', 'num': 1},
{'seed': '5956035daff67270bc37ea6178d7288afc39151738e29da8d3008465f70c8b4f', 'pk': 'secret-extended-key-test1q0azmr3lqgqqpqrwmc76gljqrp4rsdd29qw0hr8n6x9y23mmtm95vvzrlr6926d8p2dvy7rhkd2u59l3kyxfuhacudtpv4v9t5srr9t68qdft64cuemqt2w6lp2al4lraz6p9ewjwtf9ksjnge9x3j4xppg6q6n77hhum7cgwl5zeaayz04fmpdkjr7dqkwm5fq9jv8kl3eh8kta3q9tked336z4hs6a24ccmnkwyevqhqc8g2ye357nhnad5czk24ul7ugeu9cg77q2x7eun', 'addr': 'ztestsapling1n9vqkr2yuuqe9ll06w5zlyw4n580szxm6dlqcrlv3p8nqztgqdnu5hfuplvk0j85ls756ym2vdz', 'num': 2},
{'seed': '5956035daff67270bc37ea6178d7288afc39151738e29da8d3008465f70c8b4f', 'pk': 'secret-extended-key-test1q0azmr3lqvqqpq8qluq9fnfj6epzsh2yvxjhw3ne4lhgy3343045zhnmmuy9wz73mw42sqkdaj5zfm4va05e5lqkhnargl8knz4ldtg3xeu49qrp4m6s36kutsgall3kg9pskpt7adkdp2umy9vgazxhh05rrxs5se38dcc280ktdtvf8m6k5ckwyjva7uz03cfjyj3l2wyq32kq0t9fpw48ry0cdyfpc280zu8th5zzxgq0rhsgu3txs9ak39auwz38f2fj5duau4s7ugg9r', 'addr': 'ztestsapling1u606czrjhue3th4ar2u83vmsal5s7j726h6q2vsmdr8uh7ldl7e7wzs0858vcmp2n2z2sz6c9hr', 'num': 3},
{'seed': '5956035daff67270bc37ea6178d7288afc39151738e29da8d3008465f70c8b4f', 'pk': 'secret-extended-key-test1q0azmr3lqsqqpq9ea49eyfn53pfe3658yag4qge5ure9afm8u40famc7c8rzc6e2ccm0cx9n8dur8vy9k2g2lkfrv2l2l5vt3pvjvlxnnq2hffdvnq8qx3p9mqtyrxd0xcfakw8flmd8qrplfrelgxf6ns3qrtr8e2d0ksq88nw98yvx953hazsu4jrk8tluzxr3xlp90y0pa3u5684533nljcul340v5v4gws2s4gfz4ps5v8gwul3d88uu8gcpcdaesgyy6z9l37gykewhy', 'addr': 'ztestsapling1u04jz783g394w7c2yqw9s8j8lmeph2jh8vtzsxajwhmmc7x9kyj0cwzk0nssdnfmuf9ng4t4vmp', 'num': 4},
{'seed': 'fd9f53ca20aeacb726cfb105e80517c88b750bb465d878096931a49d710a292e', 'pk': 'secret-extended-key-test1q03m9xvqqqqqpqp5wrvr7remr0dt8e07uc3e6l522mqt876e55y7576c47g30txypgz9vdrtmnwptyk6puqtukn02pjcvjunfhw3635nqvllhwsawgkqj7gta8fsze5qqh7r7ac2spvucs5n3xgdz7x9nrum4ux6p438e0gyt38yt6pmcrhxz40drg22uz5g8rmnl73d3xq97nkezahwztuzxhe6k0eayuraqs9gvrkx7zenmeqf0pax5r2q3t6ecln7k5dg99anh5gyfhxv9', 'addr': 'ztestsapling1aua8teg2y95cf7uv7jhxalxl6lq3fvq66tvtgnnwf4ylua3mv4ugasrsgay8wcsa7k6q5gdlfw8', 'num': 0},
{'seed': 'fd9f53ca20aeacb726cfb105e80517c88b750bb465d878096931a49d710a292e', 'pk': 'secret-extended-key-test1q03m9xvqqyqqpqzdnksellua7grk26jz58y98f7h9z6h0wqwj2l5fxckzmlhxak7c850mshh8lj3yvaw4llw35h73uln83s365te8gd5xt93quqtnl8qeksu2n8jdaurglu4kyzcznpwgpqqy0mykjurwpera3pn3medvcqddem58gwymjw0clum0xke63qcz3fshg9sl4grwjwkrltd9a3n0ql6898sj2g70y3gx6m587eejjzxwcm68gd8dec5a80geqe42y52azslpwa93', 'addr': 'ztestsapling1wnr7frqv230wxs2678k338w5cfhykypmg5w8t45zckuzhwwrlvaagx24yq5lgwh24f9kyuqtty7', 'num': 1},
{'seed': 'fd9f53ca20aeacb726cfb105e80517c88b750bb465d878096931a49d710a292e', 'pk': 'secret-extended-key-test1q03m9xvqqgqqpqxf4qxlww2p60y3pt9efar7mwt5ms9qktfeqy86lxv5m9mjahp5hk4upszuj6rlghuj2mrs4j6pefp3stvjx2n7zw2vazu4pusl45rqnlcfe79uhtclhn20swy3u2mal6cnl8tp9hs3vagtr8una5r97gqzsnj2wps4kwdh8gdgkp6eymkklwvld5n9n332kr6dqecwpn90kxn5ks6mweu3ckspshpu987pwx0lgh2w649k8gwtk03feg7a9jfeqtstx20zh', 'addr': 'ztestsapling1v3c626ekmtuulnusflxs7sdqx83r7f0t9cw3spfmnzqqzpk72y73788h0earvq54hv6ejwp78mm', 'num': 2},
{'seed': 'fd9f53ca20aeacb726cfb105e80517c88b750bb465d878096931a49d710a292e', 'pk': 'secret-extended-key-test1q03m9xvqqvqqpqqu5ypf2jzr02q2xwsm252f5x8lvdu666wqjt4z4v5y2a4k4sd8qahu28nsqw4452n9ppxvlt32s3mg44lz6dvncu5uxhzq2g7lf4sqhwndlt47ks6j3yfgjpgnv6ur3nsa7e958hj0predrawhjmt6g9gv3kr3rnn5wt2772dwj99ht8vujpu74qlp26ekutatrv3kmzzv5zwrldzttddlgxym25pqtfwhh420kt5lcwp7gdydwr2rm7k0dn9xe0gy4gfah', 'addr': 'ztestsapling15cy96drhfgg3ddl0wawwnxlfc98xmmphpud3eyw526hn4k73degx53e5mhc0709kymecsnxcqgd', 'num': 3},
{'seed': 'fd9f53ca20aeacb726cfb105e80517c88b750bb465d878096931a49d710a292e', 'pk': 'secret-extended-key-test1q03m9xvqqsqqpqzdad9vxkxxhad6a5z4andxmf2pl89hvdnc5gj3nd3hud9uanan6umuvd9rstyrlgvgtq8yuh00dtftk4zuc843rgm428rykdaarxqqzah7fec90kjju402sjgau54ytfhx2fhqee5wfamryep8jal6jtqq995d0rz0m2uyq83maxm2yleyytp628g98uq05h5ueg0gyckktm8f6ac7hhmzl5qhgm8vqvlp2tf6ppnydnx3ftlw7qjp83xca806gwc3therq', 'addr': 'ztestsapling1vamcajdehwv09t9zh8w3mqp7uvz7uu2nup0h6ftursx78lydulyq89rkqq5gv2ay8cexzfas96a', 'num': 4},
{'seed': 'adcf3a9943e30da937d2159fa1050ef01550b842ce470d95e21af5f03acd080b', 'pk': 'secret-extended-key-test1qwuj3p7yqqqqpqycv8e2lkz6etfgkw5cg0lhfe07qy8a2054zun6yuv8dpdy8a87kfzf26e2w944gpgxyksd8w5nh0uc6vtj9k3unwy2yyxejv5zjzlq9ggwjfxre0sdxwku87edjh0z2c43nt54evzyw9fw7deln3zra8qr6x6upf0xsdhz8psl95jg0zggqgdhrqm2up0mde5lllxng9008adeyd6fy2vsn0e5fsljl2j3cq8xfu6fyptknrwgwsyzzy8mvwv4gzqpsdfx6', 'addr': 'ztestsapling16mfp857yyg3p45fqvnwrva5xdk55hsrydphw6vs32aswupz5c2rcd0qerw0nv9qzkpk95mee3v0', 'num': 0},
{'seed': 'adcf3a9943e30da937d2159fa1050ef01550b842ce470d95e21af5f03acd080b', 'pk': 'secret-extended-key-test1qwuj3p7yqyqqpqxud2npep6yxmyjvslrcdu3c6m8xchvephxfzm70s9gr47k6679a32c4hun42fws7vr8euf5y4wqn4fh3zktsnqchn86m6j0ks0z6rsewtnqypdhw6wuu4flzjjj4zjt0zyxx86jsv8mcp9ct8qkayn9uqxnj88az7u3upee6mc7eqeusjutkfmnpue7d46w92p5l5m4yu9ftzds5xr4069snlvhwxzucx7nknrx5mpl396svtma7cnvn6pzpn9v8qlggnks', 'addr': 'ztestsapling1c4p7ycww6wmd2xhstnav0ss5zm5cscgefw949yjuwumxw7at4gg267qack40uu69nd2e6uz76h5', 'num': 1},
{'seed': 'adcf3a9943e30da937d2159fa1050ef01550b842ce470d95e21af5f03acd080b', 'pk': 'secret-extended-key-test1qwuj3p7yqgqqpqqfx6yqupkydqgrs4rarc2lkhlr7crk8l7324pmpxf38s7m6rjfvrnrsqk8tkwtwc6d55v7pt9npsd362tuq44zkqsakjsjcpvm3zpss8zxcner8lrxdxlehgm3daavtcfclqqe3ech4njap5umpw7vjpqqefkqaz3675273qa74akfp3v2c4mgk7stlgq3m5ra3agucx5w29f80qrklku984qtwsp8g2scu0sumcjmkw44nz6e5vaue5ettp2dgwq88zrqj', 'addr': 'ztestsapling19ep44qwr75m0r5k9ngwnpp5wqcgdg293zjjuvxdcjt8ag6w89qn5ydw39al898spjwruymc9dgj', 'num': 2},
{'seed': 'adcf3a9943e30da937d2159fa1050ef01550b842ce470d95e21af5f03acd080b', 'pk': 'secret-extended-key-test1qwuj3p7yqvqqpqz4stwtjwdv9nvm7hqlhsm0jr7ksjf4w0m39mmv5zcdxqduzlwvhx0s2prwx7jvyc6czujzm5k2hxng597ecax5yz6deuuelj6ldcms9taez0tfmm65mmm7d64fp9xy8tdl4q3z9pyqhetw32t98gjfdmgxa6vpv50jg8lh2xlyzc79gnj5qdrk2yqvzmdtduve5crnzk5pme22lq02wqc8jy0mjug30p2rgnf7qpkjjqx4gskv08xzn3mxd99dhdsp6tf4g', 'addr': 'ztestsapling1muhj5vl3qxk94xah7whwsfytt36s8h302fugtu0fy44w3m8kcxgt3cqtwc5qps2jhgeqwfg44na', 'num': 3},
{'seed': 'adcf3a9943e30da937d2159fa1050ef01550b842ce470d95e21af5f03acd080b', 'pk': 'secret-extended-key-test1qwuj3p7yqsqqpq8fp7skusxym3n9526lxllv4yqlyrux4wtkjhgutvhzutedd5u6y6a5g0mnxkypceugrm9lqlp35wvw67w4mlrdwjscfe40zqfea2cq9tp78yxs0k0f8afaugf0n2fqvg6ew5hgmv3hllm49cq59664e2qzspn5twtjwm8m2l9t48y0avd82f4ma3zp5nvmwfrdwskw28k2g5rr70csu9fvq774m2tdt8y8gswq9qzx3cjncyyt2r9ssgn86zpa0tsjzm8vw', 'addr': 'ztestsapling104rsjgwm4xj52szkqfu7jpjg84r35v7pmf96849x9ky2tru4lwj2fr0ymffg6zr2tnfdqh30cnf', 'num': 4},
{'seed': '90d7f0830eee94874bddd8158b727c66598c2d3a8cce254003bde4b32085929c', 'pk': 'secret-extended-key-test1qwtg0t3tqqqqpq9mmnh2fx9jcvlnqgr3v7f3qepflu97tv54jy9ynz46qt3rfd7zrsgd47uprnk0ky68r0j6smqlzsm7hzdxvfqkha8np3m3elp26sdquzs82hxc2lkwakau7jnd0aj8udjx9zjey9q47z3e7esd3z3ldfcdl0fanxpeklp6g6xdpwwgx27see9uem06dw0vr26r4mjg0wlhgealnh26y9gywhl809pn06d3cctqsfc5pqfdqf2htprw9jye3wqxn2s7dpyp9', 'addr': 'ztestsapling1wc2l3q76dj8dalv66d9m0njv082s2axnfqv8v5l6xg9cnq2t0xr5dglnj7lev827rc897vlk8rt', 'num': 0},
{'seed': '90d7f0830eee94874bddd8158b727c66598c2d3a8cce254003bde4b32085929c', 'pk': 'secret-extended-key-test1qwtg0t3tqyqqpqxade6znwsy458pwdyhj2yjage3ey8yrjg6gam3sfxjspw0gpadmzdvhzv8j2dcjl7mq730xzt3zsr5lfmc7n47gm5lg2huktlqhnuqfvera4ehw8ndquesggnfyjpur0xzafy3skgpmdj3tayghq7qycc9zsawzwlghgwqfnkxpv7l0cmzfm0jf6nwnk5tn70kwzhe347jvpphh3h8nc2tla665pekpdn8k5vjav3lsm63ywp9u7ldtjnpyr9vxmsupj53q', 'addr': 'ztestsapling1jezs3xretzsaufj60x6hlsd39v2x239ek853gkc2mv293zgqwnca7n4at9rf4829ynhzjppg3em', 'num': 1},
{'seed': '90d7f0830eee94874bddd8158b727c66598c2d3a8cce254003bde4b32085929c', 'pk': 'secret-extended-key-test1qwtg0t3tqgqqpq9ywqyz7zq236eg98ru6tj6xz37yyc7t63kxgqu77nmkchavppdt33yserrlplcmhghvx872tgadw0w9w2zk74mzd0pdcttuguzz32q58lml948hcdypqnm4dyhg0yguz02dq9ps49rnt4nl3vs3ahelkspphjuv44pklcfavr5h4wqq8p8llvgdng23m9lgxzkk3pxjx3228hdfpwmy5m5f3qgyxep2ea6avxtjepd6qy4a5srufyuz37nrrn7emqeph3tq', 'addr': 'ztestsapling1hndvu0vmfqxu5s5lau3fme524z244apeclu6kcqzxmrqknqm8mxc48n6vyxdzda0ef5yvv6dwu9', 'num': 2},
{'seed': '90d7f0830eee94874bddd8158b727c66598c2d3a8cce254003bde4b32085929c', 'pk': 'secret-extended-key-test1qwtg0t3tqvqqpq904hgz2cwhe922awy3peky4ugue7wgerf9nygh6rvmtkzxpyxq06vp4hnnvwn72vmqwjr5ln636wv6q9h80d7qny4v8p4my24se9tqup9faqnm4xw824l3awx5km3t4wnxh4p0hd0k4c74wytu94gcdsqdg4cwnxuj560u4n5c7t7c4c72su6fxalrcsd9an0fag6au4tna5rhz48pc9ldem333pdafya4srqu4hneusucaujdwekd8q3jy8mmyhct74yu7', 'addr': 'ztestsapling1mvu95u66jjpr28euw4amyz9r9euqa2t3ys0aheparz4yss68cskcrfmhfgl5rwsq7rgy569xuc3', 'num': 3},
{'seed': '90d7f0830eee94874bddd8158b727c66598c2d3a8cce254003bde4b32085929c', 'pk': 'secret-extended-key-test1qwtg0t3tqsqqpqpdrauw9dflegchsc8nas7pwqrwyq3ptajpzfctgt26ez3u4s784p9qk2mcr8f2hfgfnras0vcavxkg2zlkjwyu64s8geq8n36ken5qzxejp5ecufck25dle4vrwcr5npes6lk7k5g4yxsrsyj3dhtgsdsfkha4mnepy6zqcq7d4gw4jaaeh5jrfmedyhjyhzj85ymj3s3mfnd0a9djy9msj0uztp2nt5rml2u3xfqvd8pfluw8d943lra0lchmfhgcymudn', 'addr': 'ztestsapling1q7vkjwlq2ryr8exauhr9nhe8v7mvgnlgqnzurrggymh7x49jkar4l86dhy2vn5h5uk3nkvwpczg', 'num': 4},
{'seed': '677e6bef143a07af95ef7d961bd7bd8ff5a70dd6292467fd6cfb3de5e3d35780', 'pk': 'secret-extended-key-test1qvdasrk2qqqqpqrrnlppmqryqqryn66sc6lghzwda67sq0hphsn23qzzsyjdvt8lrascxkkq5ykcjeg6eukmzxhx5cm0tt4qawszdgh73gp50nv44jtqnd8s6ar8c2nw4xkleay0y4dk775526ncwmcqpsfzddwjzy8gqvgqqlfk7kx7y55ftc79h8tm04w8l9jnegxcjkyay260hkj9sucvspunl53shrunfjlp7rk3y6y4k3lvhsfre6qj7prckp0tnulznmncvks8laxef', 'addr': 'ztestsapling1ed5fwr9lr0vphwzl463ppt507htngwddwy587pes6z5s7w5lrqezh2uunvd68tkwzprawjr8f96', 'num': 0},
{'seed': '677e6bef143a07af95ef7d961bd7bd8ff5a70dd6292467fd6cfb3de5e3d35780', 'pk': 'secret-extended-key-test1qvdasrk2qyqqpqzgzlec27svvp0c87q9hrjqjwe02vun96x5lzes9uu4utapgeycrr9q4n9dz36g7z24rcc6rn9r200kr2mzlylpwzr0fhsvyqcqjz8sg3e6ztdklr2f2c3r2ymglyeze5r8ezkxdfy4uqnprusrrryh5ssz74w8p2g0yeglmvn6ma5ehf43gq36sy2awkeujl8ge2zu3z5en3ed9af6m3ysg8e65qrd6us6ethrwg0lnm2de9uq27s0su6fe9rurqg52ctzn', 'addr': 'ztestsapling1vmsmffn692655ph4ph5gx8thje0s8ljnwcgwfkjj3guyae0uxuealdpchd0qkpd0tcjdzgh7hzj', 'num': 1},
{'seed': '677e6bef143a07af95ef7d961bd7bd8ff5a70dd6292467fd6cfb3de5e3d35780', 'pk': 'secret-extended-key-test1qvdasrk2qgqqpqytyrqc8tuupnfpen9fyhgzvyglflyzpd07zacvaj4jlrdxf6fq2xe3wkcvzqg5wuc6h29qdepngh07ymxlml5f402p3x23ppfcr29qvuhrju44czfxy0zelqkphcvpqxazesvedksmmt6w7qsdkvrf07gduejs4qzfwurppeah4swvr2n4pmu9m0v2s2s3efckl84uqf8646mev9xsa8lffy63p7ynqynwpyahepts93p8stgwvhzjcfa4tdcruaqmfwnyf', 'addr': 'ztestsapling1t7a45f46h26gmuzj9m77n8zlsev4jv3m9el44paxm7463fljf98dqma2ht3x2nwrtzg2wzy56cu', 'num': 2},
{'seed': '677e6bef143a07af95ef7d961bd7bd8ff5a70dd6292467fd6cfb3de5e3d35780', 'pk': 'secret-extended-key-test1qvdasrk2qvqqpqzgvzjkrfkw76khz77grn48cswq7fdretqlt8j5pdz50hdfda7kwc2gw9z2xk3sr0k2aj7sm6avc82fxlpkgje06rs3q2zway3exhvqpk9k0dh6zwtdkr9avm7mcwfnhp0yxhcyas09zlg05c39e738pyc92f0neq5spdldppxydvy0nqtl0ay5erkzfj5a6vzzmseha3uryl7mzxnkzhkuplqnueyldrfg4yl5jaz8qjhmy6uv465j6c8sj7u8nxcvfhyat', 'addr': 'ztestsapling1nkyw8fazxnfqyq9sxx67v2ha63gsdcxxq3zgfr3paxp3hyn39lk0hg2yz4d0wgtgk50su4cl3ey', 'num': 3},
{'seed': '677e6bef143a07af95ef7d961bd7bd8ff5a70dd6292467fd6cfb3de5e3d35780', 'pk': 'secret-extended-key-test1qvdasrk2qsqqpqqard3lglyvdgddac6kc2zpul67rzsggkkv309v8r4yutm4atuytlw4arf4n2kq7e9x89atnthp9u2cs958mshn2jknr203xpxw7c5sge9jxtyk36s0kaa008wq8w022dhua7cjaareh9mzkpysq7njnds2y22502xh4dmzh502f2uwhqwhrz2had8zqvg6tm5sd7klvd9zcr9xfvnwyvg8vcdtvlfk3p6afz7x4jzqxgzya88xnp8c9a6e8l0hkhs42nsfe', 'addr': 'ztestsapling1cxyj37x5zeqwy054g6lvgpncq99j4fnaa60t9zwphgm3kat5g2dfmszd6n3fnzj4t4uucqly0r7', 'num': 4},
{'seed': '48e422dfea992716d17214d5b11fb62274f6f3c337bae58d84a9216c71689118', 'pk': 'secret-extended-key-test1qv4uqrrdqqqqpqxx7asm3xtn2rdggag0kvgpyy4npge88pfasfe0uy43c0z95h0daxhzgvyvcz3qsruga2yrrm3re30yvfgakuzg2jtnw2s7uw37lt2s0uth9ddg02vmzw9s2hwrtp0mwvupn5d3uktc0ju6nuhzjnlt53s26vx9pur2ke67ey3m3dc5wckxr2qngeg5fpgpxs2jgce5mnwpr5zxzvtp9ss8tlvesv49cu5yzj59vf5068c6yjnd79zvu85zukmjanggwr5tv', 'addr': 'ztestsapling1vk8yxjf4rx09acf9x325tjqa5jjr28nvtzt65gt29vdre3kdfe8vwnv58cty9lcv5uwawf0xxxj', 'num': 0},
{'seed': '48e422dfea992716d17214d5b11fb62274f6f3c337bae58d84a9216c71689118', 'pk': 'secret-extended-key-test1qv4uqrrdqyqqpqxahgajmdnf9jj9745nenx437ewpgwt6vznnfcqy7xfrp53tsmv797agg39jgx3ke3pfchdluc3ulrrvztpvjkpwlnjhf3mtn0p2xvsc8uxuy29scc3czrl5xepf4s6lkf58fhznch5fwwqud2c49736kg9kmzkxy4tajd4sptdsl28hrt7mv0ed2fely6zqyltfe54uzn8pv7kdc75vgtl2tsyyr0nww8e0fxvmlepq5edhr4ml57m5vxf7syqy8qc2v487', 'addr': 'ztestsapling1zt3aeyuyw0cymha5xcu07s5clgpp8nyzxtz8qftl9wa8tk2lka6vsj3zn3qxtd8e0dc9kvf6s87', 'num': 1},
{'seed': '48e422dfea992716d17214d5b11fb62274f6f3c337bae58d84a9216c71689118', 'pk': 'secret-extended-key-test1qv4uqrrdqgqqpq87p2gfkkap6fpgz5w8kl799qfddfy8fczg325nexpxqajycue3scweh0rgr3p4qc40xel6d0yuwfm7zd2x2lxaw7ffk9p2n33kdtkq6nfp5aqkpjsndwkef9m3e66cwaxl8ggdwu3k7ptu90d7jku4ktcykuq7mddd7xag52lnaga025aqrdmcjymvmq0dvx3sxvvph0zf082wax3w53qjtvdfsnc4gzynljev43ww2mpxa3wvafr0lxwxns2hqmcankvft', 'addr': 'ztestsapling1zuq6t2ye30xhrwt29rz0v7lnuqlv4ucvtc82j2z5fgpjcxlvzxszmhqufsjx75lxpw9kzwr8m8e', 'num': 2},
{'seed': '48e422dfea992716d17214d5b11fb62274f6f3c337bae58d84a9216c71689118', 'pk': 'secret-extended-key-test1qv4uqrrdqvqqpqyljr0v2kzaa7mvewt486dk726ywq9lrepet3cthw8wul4nem4n4j0ggh4k25lkpdmckttvtwkzdy2hyeca3p27f0vjvnk8ne4r6zfqxj3ehtg6vr0tqlz6e0474x4e4vue4yw9tcdlrfe7a6njt3v0uggz2j2053fr9dmyw2vyr5cdy3jrft0ag2r9wqw8x09q46mv8yuxrafm266063hvy0pkcduhefwv42kk3tt2xfgj7ezu76h3p27yefr8lcg80kn7g', 'addr': 'ztestsapling1fhuc4ge3rn6gpu534eya86lfslcxtjjturvs2jvylw2tx7sjfxttuyryzxkg34szv4z3y7mlduc', 'num': 3},
{'seed': '48e422dfea992716d17214d5b11fb62274f6f3c337bae58d84a9216c71689118', 'pk': 'secret-extended-key-test1qv4uqrrdqsqqpqrd024g3rq8v4v093fu486fghrlkhs0nmhyhmt66qtsr8q9z7y8ypztvftwu0d9dq55t30n5ayjwlfjgalt436n0mvtg8a2e0m4vensfsf585pagf6h28rqgszw94lwmaxsz6pxu7rl2g0ueu8gxq253jsfdqc3wcv6xspp6fq7l390hq8kevyaunfp9q47n6wudxfjv3zxnfl0zl2sc945kpltdk5l5vy6uhx6nmd8w7fxgae0xy3xtfdzpz4gqcqnj82z9', 'addr': 'ztestsapling1kmskg92tj40kj470xkh96fldmshawze28s6w73s8pa073333vs0kfa768t4tqsu6l52w7feqmlj', 'num': 4},
{'seed': '7aec228cdacda36f2d5296530d46a536b10b22c1df17a10bcd42ac5377d0f1ea', 'pk': 'secret-extended-key-test1q0wgn6l8qqqqpqy2zsjhg5p4ptggek3mkwqyzjd4xhar6nhzt7gzdmra5h0lfd8vcgkfx0vqvw5357lf4dr0lkpahw7rj8gzxvt38mqfvlypdh605n5s34gjkcx8psmrrzqmqgwlfa9tuy69h28xh9amkw6r7qhn25lf7rsvgg9kfjfcdgl8c7m2j6005w9dwa9zz4px67mmeklzwrrnuey6jhct3ugyt738797kjpu8fj20cz6scnvcq2alfn05hknkf7mnj5v8x0qj3kxcv', 'addr': 'ztestsapling1thk7wjxeukv4h95y34w6neaamk3eqjwhattpka6rlk0dwg9ygwhykr5kzrueyut8020ncm0xset', 'num': 0},
{'seed': '7aec228cdacda36f2d5296530d46a536b10b22c1df17a10bcd42ac5377d0f1ea', 'pk': 'secret-extended-key-test1q0wgn6l8qyqqpqzpqneukju8lv4s4a5syw95kku75qxwe37rk6jqtsh0uqnv0r3c4gamychkvh3um7p49fsvke0xp7wce4qslvy2eqm3087jgrxn7rkqs2mrpkcz02tnuwath00gt88r7pdza9y8fkrmkausfa9lk3xyx3g84ytm90nahmqdlyewx7rd7yd7xeuhty0gj0r4wdllqfdn0vs8u8v0amwaw4dce96z4ck8jgkxfqal99zvsn3epnau0tdltwvehrt34ysu504fx', 'addr': 'ztestsapling12v3p0hpmacqgya44nrh3e020y0te6jl2ykx6u9wgpugxw8n9uh2d3nv7yk78d77df7zauvxx3ly', 'num': 1},
{'seed': '7aec228cdacda36f2d5296530d46a536b10b22c1df17a10bcd42ac5377d0f1ea', 'pk': 'secret-extended-key-test1q0wgn6l8qgqqpqzzxex8lnaeztk70pjk58xf2l9kwuzl5fwqxwppfj0z9c6p6t2jc2902r6309023gjysy8z52z4793nwxprqurfypxy256wpnm09zdspa3llfmjqaknrtjqqtyztwgx00k53g0k3nkke9l004eqe8ffczgqesrx5w9vf0eysntdfcetu62rdz294pnya65xlzxl4ck7fun6zx4m96l0fa57m642ujz58wku0lnfh7h0vl0yulm4cn7y03jhq2u286qqtnp89', 'addr': 'ztestsapling13x8cfq2qdvpg4h2jpkfj37k8e9ksqcdn3pg585nxrh5lnxmfnnnk9hxeyx2u376x0tark362txk', 'num': 2},
{'seed': '7aec228cdacda36f2d5296530d46a536b10b22c1df17a10bcd42ac5377d0f1ea', 'pk': 'secret-extended-key-test1q0wgn6l8qvqqpqzg95h5u3l69w26axge6epe5tvjrm76ukr96x6h7s3rl05sh24el3tx4ca63hrgnjn3rdzvx5t0jf7c84zy9easg5cxl9hwsrgj262qjy57cg45dmgu2a5sxky7k4625q3sfxhwyamzs6ej9g9ms5kwyygxht2qcdnhkxr8u5t4xwgnskuld4w3ldtkanhjv4qneqchyplhy3ynz93ehhmdssaeuhr5jejjsgkq0e66agg8lzc4shy60jmxwnpgfcqafqvs7', 'addr': 'ztestsapling1j57yfgctpxe5fjwj360xwkye82r7l9zpk6llam9pk3x0hqc324kf05hne47ttu3phn29zmtz3kz', 'num': 3},
{'seed': '7aec228cdacda36f2d5296530d46a536b10b22c1df17a10bcd42ac5377d0f1ea', 'pk': 'secret-extended-key-test1q0wgn6l8qsqqpqxl7tvcufdfzhpq5h6hffmvdly7kvnqvr73ksufy027763v4fy895zpx554j60r6e8an6cf4hxyfsgntn9j2rt9r4ek4hw2pgq0wwaq6z5tmkuyqqva05znfmhlhuxagetvzvgyffv8c3p4xwty3tnjgegp396wzw34aukyvuw9uf7xh55pkhr0pdwh4mcj8nrevz5y9n6jqas7aea87xqkqtnxay3l0fcy5agllz08kkvn8kd4y3g5uv7qcgrzaeshvcur0', 'addr': 'ztestsapling1f6c0f80zq6usux9zkqs4qqj59q60vq8w78k7q4knztsphh2mknz2nskwq53q03wa32q7zrf0c47', 'num': 4},
{'seed': '44010d33ebe8c963acfa2564465753dd1fcb7e2b1d9d696b5cdcf63370683366', 'pk': 'secret-extended-key-test1q0dl3wlaqqqqpq9my2k694dkwedtcfgwfc5cnghys7npwxl2k3xuy0hx48kzxdkjh8lwpxnudyd964eexnuk6xkeng3s67cjq7clc60vnetk60h9dghs2uz30aut42ayapx67z653qr5ks8k325qp7ca8cwsvfgnksx4lncxccuk6eey9ltdd2dfrqjd3gly27yq8euasa46z3hngm8eyer63490yqef23unvn5upca8chvnysf84p3n45tegundqjt4p4k89m9uzfgd95ejn', 'addr': 'ztestsapling1r42etx6tcsd66hr2nezftt3ze5rkqranj6098zy7qfheyx7j6fj4rs3l2jsdxxkef8pnkntfd9d', 'num': 0},
{'seed': '44010d33ebe8c963acfa2564465753dd1fcb7e2b1d9d696b5cdcf63370683366', 'pk': 'secret-extended-key-test1q0dl3wlaqyqqpq9snxxtkdr4h7gfdfylypcnued67l839805nrx5j6yvffrrm5a90e55xmj5s9qt8zd0a9sgg9qs5qrzu4e27ejzynchlm5f8juyfu6qzs3dqd6ugxk4cq7ez0sp69ec2llfue2csmyq0sm44937qnzgkact3v84pv72ghrcm6mnm4dek05dc86l7aa3zzyxu8uq7t4t8eez70mvqt36ptdhhk879fmlp2rhkva2uh0jftu56u7vvqhf4wcpyw0snpchr08m5', 'addr': 'ztestsapling1aavrxzu75kfe8tzt0l5vmv06esw6sprasf2e5u30c9rpunmnnp00r977rsce7fsgfa52wk48ewv', 'num': 1},
{'seed': '44010d33ebe8c963acfa2564465753dd1fcb7e2b1d9d696b5cdcf63370683366', 'pk': 'secret-extended-key-test1q0dl3wlaqgqqpqx2qsumkf4lu3x55s78z9u6gw7s9535ae6ssv4sue7rh6cswf64l7fhkc65y8my825f6lm87m0m2mzwm5mntxnk2z2pnfvlg5ngkk2qpjy30sl4ypdmd3fvkh0yw3eujjaedlt0qdtj42tsuhljh0qlkzcp8vwgelrpzpswnu6lqw0j7l70738nvdwfw5zj9gf9kehxfk5cpp967epn78ly05a9twm38pq8pw05jrxj3h7723m89859xchjz6s6xasa9vayu', 'addr': 'ztestsapling1llg06xzjxcwxhyceamkngtqkct6r4yemmf7nk43nvfz4acg4q9el6xt9y24tkqhr7znk2r309yu', 'num': 2},
{'seed': '44010d33ebe8c963acfa2564465753dd1fcb7e2b1d9d696b5cdcf63370683366', 'pk': 'secret-extended-key-test1q0dl3wlaqvqqpq8n08z0gcnnw8qcqpfm0e0wfkl3vgs0jfsq2wc8f4rtkxvvynxzlffmgjldfpd48sy0mxfysheyumg0t2em06lzpqfrnzuu7aea978sj25k8yfz98ede4g9fuxg4ve7g5tz9deyx4h6mxf90cu2lnu6dls24tjwrz7exmyavk4ch0z0ajg7lsy6y00anccdpfc65h3vgvxj4fckz45r5jnzkeevqmtqah52tu7xz00kv7nrxh0akshkp02t3jp209sjxr2k4', 'addr': 'ztestsapling1qqppjjy45f643egf4y5d9qanmdke603vga9z97k4myj5zjlq2f4x9tkqf20zm494zy2yuhx7u3v', 'num': 3},
{'seed': '44010d33ebe8c963acfa2564465753dd1fcb7e2b1d9d696b5cdcf63370683366', 'pk': 'secret-extended-key-test1q0dl3wlaqsqqpq8k658uyr5jc895c86lyf7wv4sgn4pe8q2c0gpl26wjw6dhe7q995j49tndnse0qyt49e5u5ekm7jjsa0v8m4kh27e64em9242da62qjmvcfeel42nnywwy9dg63r0fc9cpkce3lv33ueeyr4uasemw2lgd344kjwa27vwmhnewze2v2dsvk788d2q92kwz7lvsw0gmacae9uav5z6m3duk88r90lt8efpgesp7fq3nky4v2a2jyakm2wmkd4typfc3ye0pz', 'addr': 'ztestsapling12z58mxmkge86mkvsydrm9j8qwh3cu543l5kzgawksdh4gl3ff42xx9f5uu6pre2vqgd4cnwx73f', 'num': 4},
{'seed': '4d449c1a84edc1011c003c8e85ff8523a61c39e3af045caae3645cbdeb9e9ace', 'pk': 'secret-extended-key-test1qvf9q4w2qqqqpqqshswrj4928tnwk2j0zrg0gy2006jl5mmdavjf62tqke3m7zpeq4fegrt3z3y0h2mzqs8a2vyk6pnhaggan5jl9ff6yeukhcfqnc5qhn7rz82k0c3dqhxkt60eeturd2h3tyzpaqq3482w0s9kthdvhgs8xfefkpk92tvdvmscgadcrah237t3dftu39wveux4pz8c698yqyw26yy9r90e4frgvcqvctnene9khtqnymnq8sn2rskcf2cx77hx7fg4gnduz', 'addr': 'ztestsapling1tfc754x4sjsa9fqk9wul2wmamqeqyzlxlscgngpv2qndj8xsrqzzmvuun8kfhauckxthqekcv3m', 'num': 0},
{'seed': '4d449c1a84edc1011c003c8e85ff8523a61c39e3af045caae3645cbdeb9e9ace', 'pk': 'secret-extended-key-test1qvf9q4w2qyqqpqzjuem5wthl24p6epljqs34jazrw28ffta463lejknfkhakkw9hew9fsp88h5t9twyh8l05lvu7l0t4sjq9yfckk4ksm37zxl8729espq5fyfrs6x2xhan53n52wf5dmxnv8lxamfmurql3z76s6p8a4lcgsmqzpff2gd2trd2lnkw5et7tr0j9q2str68r2c6007az6dvlmavvgv3qg95jfqym2s80fw088wwcuts6kw6wx672em4yqrka88wagrckgcgl2', 'addr': 'ztestsapling1jekr7zp3zkmqd9wx6ue23h0jmkztxs6hp7qe8kfl9zkdut2dwmp30wwmfjen5m83e5enqkw7pvh', 'num': 1},
{'seed': '4d449c1a84edc1011c003c8e85ff8523a61c39e3af045caae3645cbdeb9e9ace', 'pk': 'secret-extended-key-test1qvf9q4w2qgqqpq8renshjg5egfje3s3uhd2m6z9287efjm3wcaw6j53w2x02uuq43hmf798r3srlhleg3hd0sgtyt7p4cf5nj275k8rdtnm2fyc2x6tqevh3rr9zlh84a9w2ve6g7neg3s82z5y4cqjxuzzvm0en0ftahxstjs5hvl4eplc6ys8a4p0jnm4443c45qfylvexlddl5vrjwkrkhc8ru7acxkxwrp2fv8gfknlcnx03sdl7t6amalehh2drx583xwvfxaqj2g03p', 'addr': 'ztestsapling17ncd5lnjl28zxz3zc56mc768sgsupup8zdzhk6sex50zcpkwdu7vlek35sh8d9hkax3jvvz8q25', 'num': 2},
{'seed': '4d449c1a84edc1011c003c8e85ff8523a61c39e3af045caae3645cbdeb9e9ace', 'pk': 'secret-extended-key-test1qvf9q4w2qvqqpqrsljcpa7ju2p6na0kgf9hvdnt2kt94nhu2xdmau8wz0sk8pv59jrhy85etctzueyzdqnf8t9mjz558la5pqzrad852dmj0v35dxa5stk0yklce459t0tuydqz2akyzadlaek977xapnqedlu522dc8g9qg2xaudkhwt5g9jmzqxxcyl5gmvcwkx3q8j5hl28kuetxhqwnzuu59dra0htjdtzjg6z5auwcwmd2utr609j3gu2kznty3wxrl3zqc9zglxvw8q', 'addr': 'ztestsapling1zhqsx4j8cwnptwc5qtr59d4fzfd9wwl56uuwkc4ns5vq8j22t4sy0k5wrvgfyde7lrkukmh2m9g', 'num': 3},
{'seed': '4d449c1a84edc1011c003c8e85ff8523a61c39e3af045caae3645cbdeb9e9ace', 'pk': 'secret-extended-key-test1qvf9q4w2qsqqpqqqa2qnuv9zujdh898xgprfcsvenwfyptwlywx7cd6fc6rcpcweq7aa39s30895fgdy2an36z7d28jn2dm8jzvp9w9ln3mn4pawqcasg9gw3zljcqjc4syfa6j2g3mar0d8m652rn57s765pnxxd8wmmzs9m92gdq7474ckcl8vx794thhpvu06ydf8nxfwdcnaxslnzmfu345f6s863qqyh82zl7e5t3yqhx92jkdrdhcm94hmhfmwpn0n5kkl2fc0c624k', 'addr': 'ztestsapling13lc54l9385ahjl9r88x0c07hjvrls3clwuclcarhvle787t27gsdd2hqghyf4q4hpyqlyncqksw', 'num': 4},
{'seed': '857b71d04bb259edb4b241cc6c56283443ced897bff1d116d9eb660def74e1a3', 'pk': 'secret-extended-key-test1qv3us4ypqqqqpq948fdan4rz9vg5ang9dyp0ezc39hqrvhke35uee42y9hhzzqrjnhhay0jkm0unpnwsy242s6max63hred3kfmzy0shart39f8txy8qaynznn2mmxrcwc34u0m2kts6x7l2mq4jpdd0nay9hy7j98v97jgzxfth7n6wxtwjyqgusecnl5n450t3f603q5evd27f7n7tlyqshvhx2p7xgszd30xreuwd9qhuv3xf5pwrglscufphfjxuuscjktkqstqneef2j', 'addr': 'ztestsapling1tgraz5jp5cr6fst09yu6uuf5ezwph2p3574t9fayhlzl8s3tewvxqufregtlh5m9tjqfsdaas63', 'num': 0},
{'seed': '857b71d04bb259edb4b241cc6c56283443ced897bff1d116d9eb660def74e1a3', 'pk': 'secret-extended-key-test1qv3us4ypqyqqpqzvrc3xy3dq54vxlnfxd9qlshput0efc725fnl78rtxclqhymd7xmxt7hztn9vyn56syvu6nlf447gyyjkc6hyke69lrctgzpdchhkqffk49y0wspuy3tqrld7rvegwjkcj362tjxwxjmhkk87dvjkstlqq42p5rc9kyp0y2q6mhu665p34v4dc2tx67lwhw3f9jdz9rzun2tkt0rptqn3ekum2ssstdz9psl38kqdg9l30xr6umuyn82megvfz9kghed9cg', 'addr': 'ztestsapling1x7hmldz57f03sl65mk5pvxann4xa4r33z2ut2mjcqyczfx5crk7u5h96j9smj2yg77l4xnpgunt', 'num': 1},
{'seed': '857b71d04bb259edb4b241cc6c56283443ced897bff1d116d9eb660def74e1a3', 'pk': 'secret-extended-key-test1qv3us4ypqgqqpqxw497plmj8ekdjfw3wxxj7d4kue6aly0hy8xnavmy4t7w9w2lmghr2sx2ex6rsx307v32468whdhgwmekfgpf59q87732xsdau9ckqsyr574jh5evjguf5jsmae84q65aq4lk4ymvy9h5v2q3qflm0gzs84c0vt60mg2psnz98m5kjmakye654pdv6qhw53q227lh549vdaxahpyaqag0uq7fdv236e58kdp34el4d7v8re3tyketwt9ky4n58rzclwflj6', 'addr': 'ztestsapling1e2ct25skx6m46dh8qzr8gl66euwcljse8mnwchzvvg5f7a2r8v2cw9uk892vueh2gschxrsrara', 'num': 2},
{'seed': '857b71d04bb259edb4b241cc6c56283443ced897bff1d116d9eb660def74e1a3', 'pk': 'secret-extended-key-test1qv3us4ypqvqqpqxq7rrcvnrdx2jnmyrylawdt2a04d7kupa84jn49xt96yeahusyja660pc5evtt44lhn9hpxcyu0xw2k9w23rv2y7d504rk0l5uhwzsyh7cms2pp7n7tl423zd40d96m9syep2c8at3xp463pq8glkm7tszm9yr2ruq2p6kulv27xu6nn3cxf9rs4gu6e2wl6zyadr3cxnslgjxlyftrcl3au57sddsmdutgl5ppuvwk92alg0eg2sv8mqxnvt0svg07p40j', 'addr': 'ztestsapling120m7nk4gn2y70vgawq4dhnk8jv20lv83xtenmt45tpu520k7d3gfxhpk85mh93dd7wu3z4v6dx3', 'num': 3},
{'seed': '857b71d04bb259edb4b241cc6c56283443ced897bff1d116d9eb660def74e1a3', 'pk': 'secret-extended-key-test1qv3us4ypqsqqpqqdy73qy9da7duvh4ws8aeyhwce9x5r03cgmnuy74kkgv6qzw9xcd6wwzycmdhrm90ehvu7h5wdg6dnwxm6hy60hetestugq02eu0xse4mvl3nnhlmclf4nl9sds5fhc0vdxn7lvpkxt3wvm9du8ksp0tc86cdfnrkc7ska7xmdddtrznzq44eaepggt3nrfvxm6vs5wk0hwexkvj4yslfw5t0wd9qeg5yww03lsuzlnc7xgr6q2x2spkmah0hcyrcvc5gfu', 'addr': 'ztestsapling1c3uypm0s6gntghx7j6shplgd6vlzlxklle6dexmefffa7d5cjzxgt0dnc524z9ye7vsg747up20', 'num': 4},
{'seed': '98ba58c3cd977e68258cbc07c0aed076dd24c747052386060cddfbf00c6a436e', 'pk': 'secret-extended-key-test1q0vvpnpmqqqqpq93ljfu5l2e9y5qdlv94cg48t2hu7n0qgjuehggylynznzyq8gjd449z73rn08872mmy2v0n9t2pr8tjjj9zc5dwhhak5xf8mkw4qjqwv2my0gdd9xmv4m4ps83m96djtj0kcufuyu86dgn74faq8pkudgzkyw40mpf6sxz9j0565ud0yp8s9q5qmyg2jfrm8exlmdpth6c7pyz8xxsaj8vp4h3y9gnqlqs0pd94xkks8cq3vxrrx3u3wd3rhkys8cl9zw6u', 'addr': 'ztestsapling16zygpt855af7yhwcfjx0jzqmx639k9hy4zly47dha5sfs922cp6s95mmm4uymh2pgaauwu7lzjg', 'num': 0},
{'seed': '98ba58c3cd977e68258cbc07c0aed076dd24c747052386060cddfbf00c6a436e', 'pk': 'secret-extended-key-test1q0vvpnpmqyqqpqpllzd3k5gttsfhq96u6kk0zlr3m3rkz46u5dfqwrzqv2te9lhgssqz7nzkck37zevyvyxh8xy8hge46ahh8zp8032ewa2482uueqvs5pf6uretjc5sh84s3zsz5l3dzr85yqmwyfclvqccfmwxz258m4cgqpl3gzczea6jxaeds2tv7zesxvr9keq99t4eavvcws4c4shu4jy2n8uuwe987lpy70jntvwftpgfsrmzajt6l03f4m3jxzxsdkn3jrs98jmgx', 'addr': 'ztestsapling1quguq58flp4vtvsywvjw5aw75jpcwxhvrr0lymdddr3x2p39f08lm78vkns8u9uqclm5287959g', 'num': 1},
{'seed': '98ba58c3cd977e68258cbc07c0aed076dd24c747052386060cddfbf00c6a436e', 'pk': 'secret-extended-key-test1q0vvpnpmqgqqpqpzhtvzth4ydyp3l3aptnvs03c8dsr6jk5f46272484q9htw9cay6sgqu8y8ae07qy2hjmdprq7n7g9q8rkvvgxkyncg758k89pycsqnfkxaued7s374nghjvdktt9ds0y7hqpranpeghmkl0hmph9hlnsv3akvgu8e60645670r0d9wtfjksc4sc7lz9z6h683thhfyv952f5vxyaweqy760yknsklnakwz94gpr3p9z5yzvhmg5uzda38p45nxqsqnates', 'addr': 'ztestsapling1rq905mghlxlhgqrenarctnhuwyweq99h4qzxrlyxx0nfv8ltryq80a6ue92elkppe5ddcv7znx4', 'num': 2},
{'seed': '98ba58c3cd977e68258cbc07c0aed076dd24c747052386060cddfbf00c6a436e', 'pk': 'secret-extended-key-test1q0vvpnpmqvqqpq8f4e43yeus2pajmz3avukvkva56w90fgdfgu8sqzcj7x7pvntj9ga8hk2vkav5432j7fpd4xjew40eslmuesq94dv2d3a24yz7s9uqcvjjmjeqjvnxsyv66dc3hcg40dxgh2j75ugld87v3870j9u88tgzl0yr2cf48mcahjgx2pcu2sdh8w6dn7txg6mqfpw88sy7uca9lm34mdl2vc03z5rykquq4krqu2k4hp574m47z4scct6p52rkz00wv8cx6z8sd', 'addr': 'ztestsapling1n9tmhecvj7ymgvd26229m2hn592aq3xw0fx6qf2pg8efa5kkhscpg8z4lr6xh0aqhff9xww534x', 'num': 3},
{'seed': '98ba58c3cd977e68258cbc07c0aed076dd24c747052386060cddfbf00c6a436e', 'pk': 'secret-extended-key-test1q0vvpnpmqsqqpqpr3e7jp2vg0dswrhg2lmavgdkzwn4a6my9xwmgmp3hqdcc9rzneph544ph6pdparwmex4ltn34x6cf7jykx7q0h5twek5twk74mg9shrm4fj68923qhprslcf8rwh0rt99q4hqgfzcz3dzz0z24sc5adgpvllmdj90p2stz95emfm0zrrdv9cnqfa57e60h9p0gplvn66gx0r57r6pnk8ufd8tyq73ddakezet08xjkgfcr9q054t39c53th8mf6q4p2r8c', 'addr': 'ztestsapling1uzcnwwe8jx7c8q8cllufru544zw3zgagst69te2zzxqj6ssr57zdhmaka602r97lvheuzp7vvg6', 'num': 4},
{'seed': '22deab1096c8f4f464e7dbabe7ddf8f664e376b96382ca536a92683ad58e3a38', 'pk': 'secret-extended-key-test1qdza300uqqqqpqxyh8pk8pyay8d4epkgap0l676xgz0a22fx522uwrcnlxn34mecu2qmnwhc73cvceu0uaru83hevd04cgvymjguj87pzhkrvyl77x9s6hf9drce8tr83q7em09eemjrd28m4emwvk5mqqn68d809yyxgastqaa6hwwsfj0ajzw5v5efjkd0lpgs7gwawh22xpe6qaa3ry46zlnp4wpgz9l9xpwvp08ut7ejqvywmd4dklw5h423qw3hef8hjzfvmkc0grafa', 'addr': 'ztestsapling1e7262k0yg2w3annfsm92uh899jy4m4gm7thnggfna3w46dglcthx342upumvazykv6nfkg448n2', 'num': 0},
{'seed': '22deab1096c8f4f464e7dbabe7ddf8f664e376b96382ca536a92683ad58e3a38', 'pk': 'secret-extended-key-test1qdza300uqyqqpqqlugu3zqncl2u0497qzfzern4uztmp8nkdtx290q852ee47eyw66am46se2ag0y82qhry92xuw2p09ev6fykzye5v79qwyf0dkcx3qnzznzepcxpcqj8h55uhmd64zhnsqqzfxhte35uck2v36pryzdesvwwqmpl8gqsd5qqyy66z4ncd4rjgfq4nd6dwaaaakzm8037puuxlj3u85rpeflwjgzl6fw7wr4zjrkhesr7wmlhhva6d3s5fyla3hszqt8shdh', 'addr': 'ztestsapling132dwvu8lgjvlq2qq4vk5uww8cj6slu6uglpzmgs20mx0jcyjdey30rlcxphgyrlzhcruq6ej5f2', 'num': 1},
{'seed': '22deab1096c8f4f464e7dbabe7ddf8f664e376b96382ca536a92683ad58e3a38', 'pk': 'secret-extended-key-test1qdza300uqgqqpqpnrz57dgn4tucv5avcw6u0shd5zvcuetfkpdmvmypl3ws9p56t24se5yzc4chw2wvlm5sru337sj949l9kxrd3dp4tghfffgp9ayfqf9dyszu6deaflct9e2659j7w6tvv9lrxrpzmzucwdqqy4ld0z9sw6maact7larxu7ar47dw3zag4dznaw6geavl56fgm5z05fdjhnnqh4vumdcydjyn3g9k202tytjkrd0wh2qjuw3nzsed82fhl029jqag4ylry5', 'addr': 'ztestsapling1aj0ayd6983mqk4sntsnja5ra7w2p6qx2yzexpzqstkvfx6aamjaslzjlwsnp5m3r8gwmujzzvxk', 'num': 2},
{'seed': '22deab1096c8f4f464e7dbabe7ddf8f664e376b96382ca536a92683ad58e3a38', 'pk': 'secret-extended-key-test1qdza300uqvqqpqrwza9evc7xpyd5kgqsfxpefsv4y0asqgzyszpa4cz4nkvmu245hvvhuzuqywvc6hcmhtpd2xye0amdx27vcvh436cpy898cdzeveqq89d7d7w04suxyjk6vhrj3eyxheupcvq59junggnsvsex4vtahwqqzzlzc8x52yjsvex48y3gf8d85fk0fx69lvjzhdha5y69m2mxpwmahfe0e382f8txxu60wvrh9v9pg4zucrq9uzdyefmt3mvjjfezkfq8yhcdj', 'addr': 'ztestsapling1n99d4udfw3elfxvkqvxq2j7gmv36fp2m66qmz6yhzslh0h6xkkx38eqjscwwq9ygh4mr5lqsf6h', 'num': 3},
{'seed': '22deab1096c8f4f464e7dbabe7ddf8f664e376b96382ca536a92683ad58e3a38', 'pk': 'secret-extended-key-test1qdza300uqsqqpqq9q7u7awcr5d55np99j5c2f0ymr4fkafdxzqvwgz3x7l9ug5dyetfmclxx5f9nglv9qawa6umlxhm5hynmtcvd7f4nzcaqy94ml4pq5uw0d3a802v9yxfazd22lnj8fl0jjewe0mdakfkla9w84u8hzccp0024j6mhm9rmes9qg35k6wy2rd3n5y3lnegn42qxcr38n428juvhl84279gasg2pjr5wtam6p90luekwa5eqah76e6w55hqp0rpvrgqg9najp', 'addr': 'ztestsapling12l7z8ax7wsaxl0ggfuzjy2p5dx82khk6d0g7s9lsfqlxddlun4fw90qpd60fftw4dapgwgkt6vk', 'num': 4},
{'seed': '3be9fe5e5f94a70103da20d5e23cfc76a4e93ed8894b6aaedfe7b960d7ca21fa', 'pk': 'secret-extended-key-test1qwnq8dx2qqqqpqy7r3hptwxx5p64vcyjh7u6e04qw8gyxjwk3z97vm4yw3twwsd3jwlff5hctz87tg2sg494q0tdl3r7s2ctgf07he9yl05aznmqmlfq39kdfmku4xjs7cplvutut4gmaa5am6ycvw2up2uqhqevxpjpcyqrekch9l4az5lny88k33m4x9m2v3gze84wzg6lrwf2yun9x8u63nygezxya0ktr7uqlf4tm9x4axt9eslarg3q08j0qhmant97fkxh83cthum0s', 'addr': 'ztestsapling1epplgxqc6u6r2a6j2a69svrvtwgt0e92zzpv724x84eug74j9n9zh5yf2wl0zqwdymp2gax6wtm', 'num': 0},
{'seed': '3be9fe5e5f94a70103da20d5e23cfc76a4e93ed8894b6aaedfe7b960d7ca21fa', 'pk': 'secret-extended-key-test1qwnq8dx2qyqqpqxzvu9fktm40fl0nr20lwk298jnfy6ex5hm5fv8r0z5r4w7rx07tm7hwxktta32jjj6cuu6hnudwkktnfmctjq5kf3sdupkp6edtupqfmaf3p73m0nntsd3kymdcvp9ea0fg36pdu27zm4h9jr8nurrd7s2tgzp4rar4xl7adcr72v46hxzzuv78u0yl8kg76wpy0vrsfw9wejt8ve2ndx3ysltkn3elalgdzpcp50045xjl9evcku576hjkv340gga2w0zz', 'addr': 'ztestsapling1pex49j2psjr49ntuzkqf4vgr4mwmf07rthw4u6u92q038fa53yuecahzatlhnf9a6lhsu5hj3w9', 'num': 1},
{'seed': '3be9fe5e5f94a70103da20d5e23cfc76a4e93ed8894b6aaedfe7b960d7ca21fa', 'pk': 'secret-extended-key-test1qwnq8dx2qgqqpqpfha65jcng8mlrzjlxteetvlc0a909epxdfj7nllmcryy4s8ldxcelmelgs7p6wrw4a7pdcjkja6grr69vgv4tpkrvatrau7xzxfeszzvk63jcmvf4dyffterc74lvup7skyhx7lc52ednpjyqqa4k9zgqdrj4d359wtlv7aw9z3ny9axkdz4p62y9kzw3udtema2gxypjf59dgy3qgc4akyn4w8h72jukymhv2j5n54qyru8uhke3k59cn57j2xc8xje0w', 'addr': 'ztestsapling17wrxcjhtehdcrc3fs62u2083qx4j7604rykdvqtrw7p36txufc9t7h97xcyndeyt594zv0l6666', 'num': 2},
{'seed': '3be9fe5e5f94a70103da20d5e23cfc76a4e93ed8894b6aaedfe7b960d7ca21fa', 'pk': 'secret-extended-key-test1qwnq8dx2qvqqpqz6q925677pg70ngr7av3qd4m4kwr0zj8n60pqzz3eerf6xx0apuzz3jaatw5at6trvmg7a4tk6kdau3hkcwxylgkvnut03yh8vty4sve4jj57lawx3qr534eymakpeylteq7n7yf3av5jaak2eews4n8cpt4my36uh80dffqctn5a6u0u3pvyt65qmea8vgpzp4qcf9yjyu09cgkmuemx8d2qjq9pqkh2clxxxpq7p6cc9aja7ef9amhwgh7amluswc9su5', 'addr': 'ztestsapling1u2phjjv9k3p63qsfnsezl0u0fykwvuyku054e706wtr3z849z3evgvuqxhfhn2glp62wskwpnmw', 'num': 3},
{'seed': '3be9fe5e5f94a70103da20d5e23cfc76a4e93ed8894b6aaedfe7b960d7ca21fa', 'pk': 'secret-extended-key-test1qwnq8dx2qsqqpqpr2spxud5en3eu4juwmlzutx3sg87vgy8tnrwg47h65ncshazd434lkt2306lhpqhd3xpe6che8g4dkm4gy0pkeasdrqehghqhd3ws445s20dpr8hxumj69hcrmj9u39hrv2nad2aheedz9zkdrry234cxqg4uask52cu78qp4emfdra2sssequxd9tj4pfvy6062rzwdj7r8tts0y5wucqxlv0vv7d2pv7r7atu6r8fn0l8aupux8ux7du6ce9fgfq8eyh', 'addr': 'ztestsapling1m28js6vtelhtfvqk9zux99w5r0aznv8g60rdaj77kj4l74yztkqt4hr6llyts8245zv2jnkmq6f', 'num': 4},
{'seed': '7589b0ddf4f132674373089b1ccf0db6af158efd4c0296f3c570b080e072cfde', 'pk': 'secret-extended-key-test1qd78u090qqqqpq9m3n2r033djuj00k200sdnu0j8j90pn8t64wxwevlz95py7knlmh8uev0mxqppjq4h0czr8lvsmpalq58d3drgx3jjun7es3ws3l5q46tysr0flq9acz48ljn0e7ful4ugh9kptkkwmlt48nyemh6wgxs9tr0yj4w4wxn9s5e4m408w32ypng6zpnrqnxxpqsypuxazgthycshcvj0qpz7mfjptrj2nlje3g59e9jlvy3qg3fyuc4rgqejfym305skh74uw', 'addr': 'ztestsapling1wtzmekdwdwmsxrws9ncrwwsd43uxa4xwhg7afvwrk89vl7p7fkku965x55xkuneumk7kqsng7kr', 'num': 0},
{'seed': '7589b0ddf4f132674373089b1ccf0db6af158efd4c0296f3c570b080e072cfde', 'pk': 'secret-extended-key-test1qd78u090qyqqpqzezf644dkny9lh0qfhekfga9cvtj4fmjhzf9rapakf2kx0k058aqzfeu7sjc86k6j50hcmt0lcqfplxmv7ewgcpc4qhwydc4lcjp2qdh63dde2a9nysl0r03cwlnyqymf8eu0u5gzx732rj2x2nqtydcsyevuqyjdwq8mfr77vfrh8efk078wkvda7sty77ncmtcwvrmjpta2vhj37vyymu7ggja8pxaqtj0vjyhfkhykuxzvpeur40yug5mzfqhc3vau2c', 'addr': 'ztestsapling1hzjdffsf89yunxgscmgxyhnrte7zt3gh4crswsjwcyzyrrnvmr9nymr0dj9tyk608phrs6tgq0a', 'num': 1},
{'seed': '7589b0ddf4f132674373089b1ccf0db6af158efd4c0296f3c570b080e072cfde', 'pk': 'secret-extended-key-test1qd78u090qgqqpq86ntpjrwrge2ejqx3jnqcfwjh4gnhuzvva4jn9nazeklyp328xjx7lh58fr03lmnr6yrq4j8ycqm7ncewx6nejehdehwqrc8un5upswf3vd0vk6sehd5e5mn54vuunzt0vkgalkv9u6duxq29lvjerfwspmutdrnr5tdnq5vfnc4m7ynlmpvsl05wxt2rre98u5uaz0yjea0nlkqque8hlv9h3xtd3eerg0sqdfzw5q3avn64t65vxmyj42fqppmca40w3z', 'addr': 'ztestsapling1ygqykhcll4sz88g4e7thrxc59j2305tntv274kjevm58zv355mzpf0zk00nhq94q3yxt60d8r9v', 'num': 2},
{'seed': '7589b0ddf4f132674373089b1ccf0db6af158efd4c0296f3c570b080e072cfde', 'pk': 'secret-extended-key-test1qd78u090qvqqpq9lvcsx3dr044ft735q5zqrmdmq0gtucy2vquts0tafqlr3scmvh02qaxf5yl5ww06gdwuy5w6xurfclrtftfqd64mjy87gnnqyf9js0kkln0amg7mc43gsg4c0fe7pdysldh9ps8nujd0877zcktc3ljcx8ssw4j5m6j2gsyq50rh4ld8drx3yeqgxl30jd3fmuldj863hctt4cv0pf3ukfurk9slqnlrel7urdjnpjq80k9rfx06xa5df65xf32ct7u9nh', 'addr': 'ztestsapling1dk36qdaajdpspw5jcpqhhzvws0qm38gkjujzdj5jy57llkxulpjmmenmace7y099d49n6vxma8m', 'num': 3},
{'seed': '7589b0ddf4f132674373089b1ccf0db6af158efd4c0296f3c570b080e072cfde', 'pk': 'secret-extended-key-test1qd78u090qsqqpqy7ua70wjkv6glyjcy90ef58yk3fvhn96akqlwg3ptzungje9wsgygzt5a07ypwde7tzcdue3sy25cnpu9sng6nw3nxjd5t0yt6ur0s2ara7dwulj6237fkuf32hcjnrfnsn374h25jaesmspr4n3gpcjsw6hs65fgt3au3hz28gnn9h7dg9ejn540hutf4gut99rqlnwsx0qh66zcklehjeyntsr6ptz5nxck97sejf6dfdjxukeq8p2kmxpt29kgkhq5cn', 'addr': 'ztestsapling1sskuyzkh6eauf5rytnhrfgnpm4n5mstgxcywuc20jq49f7nk8cphkvn5sfshdk22rgn6whhldc4', 'num': 4},
{'seed': 'd2d9a450962c8d8e2ec62d07ed2574e4058151aa71ccee14788ca526c87535c6', 'pk': 'secret-extended-key-test1qd5ezlhfqqqqpqrawyejqhrzly8302j8vqlnxc5cfqde8f3289un83rpshcss7hhysurmctvm6kqhazdjv4296rlpw5pkc2tczkx9qgvr78z4c7hq5hq49fru6gqzk5e78qma66qth7m38n92te9vsu5wclmrmwtcvxhkdgtd5ppyvwa4pr8vln8rvzzsyktuur8vff55kve687qk0a5l3a4a838xe3t0tkn2fgu2v557qnejx0jfpphan36rdxx8vt5wa78h70h2ws0a0jsz', 'addr': 'ztestsapling10k6tmqc09e4sytmc4fcxh8hz0lwcqpl8smw25hkn6ztkl72t2wdyhhp7f3va3rkhdwt3y8ts0k3', 'num': 0},
{'seed': 'd2d9a450962c8d8e2ec62d07ed2574e4058151aa71ccee14788ca526c87535c6', 'pk': 'secret-extended-key-test1qd5ezlhfqyqqpqz32j8xf23zmzz5vvnzm5de9wjka8qeygq4kaau9cgemmp3s8g6f9u7tuaph5xqg49850dk6eynazh090tm8k3ddt6vllejrxnqfsaq46uez4zwcmvfcqmn8rvvt3qu79aagghjdrvanfks24dgcfdkg4sz8akm68sp68qc2qzkn9sy0gdy3aqxmad89prmc4sl5vdeld3axx9lmtkx4wszv4fz5a897cnur424sauwkva0rsfuzxs5xfvvv8vve0qtv8l0d', 'addr': 'ztestsapling18wqp6ryna8xj22jzx23p0at3yg6lky4u3mn90rfmttlqcs0fdtskstk4q966z4cj8e2uumjlqm4', 'num': 1},
{'seed': 'd2d9a450962c8d8e2ec62d07ed2574e4058151aa71ccee14788ca526c87535c6', 'pk': 'secret-extended-key-test1qd5ezlhfqgqqpqxjf4hpj0dj6080pnxa7kz80nl5n54kshuc7ftpjrehjgauvpe3njvy8fyuc7gc5dugjg4esxlq7x75gyd3mqtsskhsxehr9fh0uxcqe6c80wswxtqdpqkpcx43m2cgu7ksyaz0t86na3t55xt0c2k7l6qtmssgdp76pqaln4pp5rx4xhp4z0yank9afdpxgsykn6lrwg0a22xhpw9sdtt85cmnfjh2tlhktdw7z5vjvfd0urd5w8tx88znrkcu7ugsevah3', 'addr': 'ztestsapling1lp295k3gw9egu8w03egaq00vlcza283udushqkq7wf5af0avphhxffza7q465m0g5sl7snt7crv', 'num': 2},
{'seed': 'd2d9a450962c8d8e2ec62d07ed2574e4058151aa71ccee14788ca526c87535c6', 'pk': 'secret-extended-key-test1qd5ezlhfqvqqpq8eeeqhmlk4cwq6sh5a4ty3hjg5jgrs7k3mjcf22cpfgw2xe4zj88kkde7tqq829hr54fh4yna7chz3pp7f4agrau8fumkve5nyecmsyll55c5e447dx03dz9cth5es4335xv8e06h6wsfd8vpa8ktplmctsgal46huerl7mhc8y6l4r2cjfqtl2p7hlv9zzagqzcvgzwpszw7whqltczewjxud595llvx3w4jffctxxh2d9h9fd39e9xuvadzdkkggxffj2', 'addr': 'ztestsapling1w9rdtvcceqq0q5tha2wfek93036n0uqxxv4xvah9935j0d2venhauyd99c0a85djsqydw8v95dr', 'num': 3},
{'seed': 'd2d9a450962c8d8e2ec62d07ed2574e4058151aa71ccee14788ca526c87535c6', 'pk': 'secret-extended-key-test1qd5ezlhfqsqqpqzaqgpldyx09xw4ne32nn6yzms6rcr2ysquvd75q63hmzden7qvhaeutmh6jhhr9xt0cfd5s3namzsv0cequkeycx6a5gm5cs8ycjqqdwpxtnv75zqns2n8psmnuvtt43jpus2hz77sd24j6zrw26hnpdgz9dey6m84r6us3msklht5d6jzcz6hapdpu5ycwxe3vmxjqmkjpmguhecqpmacu28qfch5p6pdfvqxskvju2ccqr5kgd559nqpkeywwys4pkt4z', 'addr': 'ztestsapling1hp53xpdczuepyqzv2ms79ggnqggph3nd5zpwuepvflj7lfrjj2pgswf5na4yxakucwdwuqjrthn', 'num': 4}
]";
test_address_derivation(&testdata, true)
}
#[test]
fn test_address_derivation_main() {
let testdata = "[
{'seed': '56b923ff35452781aec5aa47dddae8c5af83d01eadd7c1c115f76c909de78b88', 'pk': 'secret-extended-key-main1qdelx076qqqqpqzgcp3chz8lk5dy45nz2xhzvmr4lw2ygfgyxguf9cn3lq95znpgk4ym0eh77d7znkgftnt5fj8qnp72vjamp8h4srhydwjdr3n9v30sph5wucxglm9xpse44wde776ave55g5fwh3ar6ajlymcdvl6queqg6645aah6wgd4zqx8qxvdjy2u66me8qfqs9aewkth267h4ll2flmtwqt6jl9mjktgvwkvs90agg9xk5gxfl97uh96rmlh9s58w3h8mnqxwvtvy', 'addr': 'zs1hgxld2zlh9jkredqknr3d2y6lkqh7duppr6wxh8sxgqc3pjc8sazgpr5cpyedqwz3v977kwtpfy', 'num': 0},
{'seed': '56b923ff35452781aec5aa47dddae8c5af83d01eadd7c1c115f76c909de78b88', 'pk': 'secret-extended-key-main1qdelx076qyqqpqyzgcp5y5jp2jtcxw3ldes8zvd26qzxmcf6pqdfttxw4cwwl9s4rj6ru9g6st8u5x55l4kx0l2g07ak4exe9j3nxv0h0ka7fh2qsuqqn9uxu5ft4um5r0a37gkxzsgr5tukagfe8mrgev5lk75496849uctrxrl30q8dhvjnyn88lkwqtf86lmmc54vj2zfek6ysmj643hc0z03cnvnsn7ffzclnunf09rkgex3xg2zkz73wwwfx09edj3tsn03q2qcnlrmt', 'addr': 'zs1xsgew36t9ycvravz5u3kr7rrp9n5nutamqwgcjmyxxtsnzejhxfkpr6c6zc2k0e73gvgg9qxj2y', 'num': 1},
{'seed': '56b923ff35452781aec5aa47dddae8c5af83d01eadd7c1c115f76c909de78b88', 'pk': 'secret-extended-key-main1qdelx076qgqqpqpmax7ruu7x2qfletsdwtrdalx4hg0zuf738jul4yv0yzsyg5ve4zc4h9r87uyuzs4nrg0g35mkeq3f9ejy5m6h0yphv3dw9c7d4v5szkptp6vaphfvjk0vvt9zz9z93x4lyu7fdx7p5277g5e9dzf48ysrce2axlu9r8a5wlxcegylht0dpktcc4sr9l0j6hrl26zgw502dh57efna5x5d9xly9ry906j30sktm0t2lw4hxaj76ec4eutwjtu2lfc5nzad7', 'addr': 'zs1cy4qm3g5qfexsq0dr5fegk54ujv6n43frfypxt0agdcfummn4zcgnqa2dafp2vxlj2fscee3rlp', 'num': 2},
{'seed': '56b923ff35452781aec5aa47dddae8c5af83d01eadd7c1c115f76c909de78b88', 'pk': 'secret-extended-key-main1qdelx076qvqqpq8sne0fmmvx26yglengumagrz29d35j87yn3xy7kl46cp7agfjc85ggaxztdparx0q56xnkhuwz7m6scttaw52vkh8lmrz2lms7d0ns9kkhgs3ft4negznuek7rpx54lc2q8gs87sjkp2det5j9j95dezspd8qs98c3gylsqkv2gxa75r4pvwxtpev23uk76rv5pmvw8dg9rdn029jy5f0jvphfrx4v0j7e6kw6ag0u00ntejlyalx2y9r7s5j2s5sc2tp02', 'addr': 'zs1lg97f6m9qmyghx3ttnzqq349sc487jj7a7nwuj4thu2szh5agtcmfsall8vwctspsavqkfjunjk', 'num': 3},
{'seed': '56b923ff35452781aec5aa47dddae8c5af83d01eadd7c1c115f76c909de78b88', 'pk': 'secret-extended-key-main1qdelx076qsqqpqx3c3fldyxcf4re097h8s2ufznltf04gkg6z2qukk9srg7axftxc6tzu2xy8urwhueasgw0nxhwa8ejtqggh2rcxdceu6ycxpc8af7ssv7ygym5lnahtfpzxrsjwevj4fjs74msysycrr3m4kfzcazlyucpd7d9k0ruukml7cpuvt20d0gguuvjutrz44w6k763x3282uwng3pxgjxqrjhylrpx7xydeg5qs5lul57nxjaef383hcmf5vza4f8f72q9m3qm2', 'addr': 'zs1z9usd83pajmc6ecmddg8lec0psy02rw3j050uajqsx4zqvea205vqagturnl2sh2tu8rkejluu0', 'num': 4},
{'seed': '6e5d7a6488203f958f0a520592a635ef11551482111b898a260a73d4edccb4d3', 'pk': 'secret-extended-key-main1qwf0p9euqqqqpqyhns67lmfnksgtp6d8rpkwluch29mkysgvshq7l3qqp0tjjsf7enavlrffd3xa0wlj3c2t8cpueve2fhh5apmzw8u2w2ssj8e0me4qjac4rjr3v9hz6nym2kz37th2zz0ue3f2fpvlez9t8lr23wkl22gg7dyhuc4pcm0p3sr6xxxnwn7hp77l5smzelpjh732ggqhdg6cxcrrvnx4v8qs8pgjd0afung3jd8ajrsjqhc2wrpfnhs7wu497ec8zgqlssnct', 'addr': 'zs1zghlvqtrtafah8hsr7d2n9rgtu60v5svgmqdf7qutfh8zrazeyudahw0ycu5tw64ugq52acpvs6', 'num': 0},
{'seed': '6e5d7a6488203f958f0a520592a635ef11551482111b898a260a73d4edccb4d3', 'pk': 'secret-extended-key-main1qwf0p9euqyqqpq95emfy67ua77f29prm7v82ucry4lpq4w0c7z649kql59qtpluexs25ec209x4srxrma9znewarzppp2hen2tma2ag6h7eyqymdhhqqwc0stdxaw34zh7vdasjlxq44r6vfqepjec9ylhekmd4ssydrrlsqzyuk8lyxlzvjlkugcnq0tcwzkmtww6m4mz4e3nvxwhjs4euhfus97qdsummyl6g38vekph0hhhtytvru7m5u02ek3zvzsw02akmdgvs6ktg9f', 'addr': 'zs1fxmt509xlec9ay3uk5uzk39cdvwp3anq5raevzu3n4vk20tl4v8vhyrckv5v6ue7ynw2ktkyaea', 'num': 1},
{'seed': '6e5d7a6488203f958f0a520592a635ef11551482111b898a260a73d4edccb4d3', 'pk': 'secret-extended-key-main1qwf0p9euqgqqpqx2m65l70lvgrud2j6zg86nzhrax0cl0g9fxchmct626sweay67wzq4m9t8n67vqsuwn4cylv0z2vusy26pwzpfqss83qcru4vctnxqfejl847ele8z2h2t4dfzfln742z6jsc0cad7jjdcrfla6aezcfgrghfm78nag2z3fgfstjy89xxz3lec3smvrvxyr47qca2uq2j2cklfs92f3dy6xehg0dx50rmtsf6z4pupzpy42fxn5s07xpm30kqdk2q3vf4tz', 'addr': 'zs1c9muz56ujprf3k8cryqnwue0r43y2yj6x4lxk7pyvr0x8urdch0xlr30ue470h8qlvl4ycw2esc', 'num': 2},
{'seed': '6e5d7a6488203f958f0a520592a635ef11551482111b898a260a73d4edccb4d3', 'pk': 'secret-extended-key-main1qwf0p9euqvqqpqrkswgfmw0f6lyxrkrzqn22277w3t2x44h7wkqlnp2gvtcfqqdlyu96mf3v6zlmzag7y9c9mgzr4fh6lh22s57lfhzldzqs3kyp0crsdnpnfvjfe6jj0cftktyfmnphsf45ahkj9keslqdzf6mc6pwsews9yv3kv2x4ahw5x2pumhtuelu9skzd5hh66jnd878tn3t2d9dnhyu6x6vqfxkke6cqs9httjrguds3mmape5m40kp35q00mse0rgrqynqrrs674', 'addr': 'zs1m37ualkfsg6etp3g0vaju4szpk6gd5fhmd8evqmygyc8d9v5f5duckswkdt5w7zmnwehzeer4t3', 'num': 3},
{'seed': '6e5d7a6488203f958f0a520592a635ef11551482111b898a260a73d4edccb4d3', 'pk': 'secret-extended-key-main1qwf0p9euqsqqpqqklshhyhtjt2ujjf8ucapdy3w2pk8km8jpeux7nvsz9du745cu6zt0pgdqp2jvq4gg9df4fpgm9589ag5ty04na5j5679sphep2n0qx8ha9jqnh6nx0qs6n34ne8cl09ndh268rfvgev4y3mgmv9x233gyzf4dejphxd5j8r47kmww0ysh7q3ny6dxvsuke6403tt7t0nghyx7zk0qlzgpp3777fc2gffyk9nfaumgghdpqcdlgkx5ect77fwjn6gqg3vzt', 'addr': 'zs1vvfds6zxs47fk809jlrtkwsvplg9608rwqcqr5ts009pyxythj6k2kgnwz38xpw36myj56e6nzz', 'num': 4},
{'seed': 'fb0e1064251a1ccf76929fadb239ef288b0fd46214280ca2c4b4e9623cc7a52b', 'pk': 'secret-extended-key-main1q0hxyejhqqqqpqzdkmea2zpcxekm059k3u5c5d5hq6n66yfp60mzexwy0atzxsctjwt57uhj5czsty299tlgszlgef0m8wxgnlr34yzveq9aa2m444zstyf0uxa0j4j52demygl5tks3u5xj34nljzdvv35yj3jvu2ull9c9774r5m58yh5u47l8j575grk6v0kaxg2e4gj8vtwcuuehjatjr76ask7r5xqzcppmqvlmpvw580qqt7jar3ymx2duwa6ufzmylyczfts7v4tnp', 'addr': 'zs1dfz46xx6eflzkumga7ptqr2cghj8pmdqjawxtp2cse98uvlzjsyszdn9ejfu34ql607rjfm43uz', 'num': 0},
{'seed': 'fb0e1064251a1ccf76929fadb239ef288b0fd46214280ca2c4b4e9623cc7a52b', 'pk': 'secret-extended-key-main1q0hxyejhqyqqpq87l9uvt5x8mtfxudgxknwx9m2fkglvpt4qc2jz8cnxzqykd4wzw55dv9nxagthvaz6xu2kk4pp2lrp89ceyfndqsyfkqk7sz5ys5vs6veunjpfp7h8rjchgqurlcczzpe0e06tk9cd94mpd049f9q6h7qt2r4em269hkxksyu5ljcclnpmugffdjklrmanw8v4fqnx2glveqdu2e5545f3ew3d0fypl2gttqhq0zsxhwxe0z7kswz4akugg9cjftcth46yp', 'addr': 'zs13kdfjksuh9hcpsm6lj6jeeqkkak24unjswsjuwgh8xew46yd0fag84w26llc7t0mrj3n24kd5qt', 'num': 1},
{'seed': 'fb0e1064251a1ccf76929fadb239ef288b0fd46214280ca2c4b4e9623cc7a52b', 'pk': 'secret-extended-key-main1q0hxyejhqgqqpq9gyc6sf5tvs8zfy9ukhln8vseq7fk3t9fnff6m689zhwc93tkrthrsks0uxlr29cnpw8vr84vr7v694caf7r4gutuvvu89kg2e7gcq0ygwg75aqwdnzhanqjw4hn5se6eehmwkpgnjt4l8fc4vfy63vqqfl72gqzafg4f2zl2ssq7ex642r99z9d93ne0jwzqh7nyr4ep9cc46cgphdjvf5kyna44677metyg5mvznsgz0wsy742juvzkdr9h37usts0yru', 'addr': 'zs12txfhja0gn67z7agreppeufxrpn69ep0aq4nvxyhc9389vnpttdgq9hcucsmex8nklewx3xn2l7', 'num': 2},
{'seed': 'fb0e1064251a1ccf76929fadb239ef288b0fd46214280ca2c4b4e9623cc7a52b', 'pk': 'secret-extended-key-main1q0hxyejhqvqqpqyvgzavxclsfl4cx096622lpv8ugc3tp3fkr72hhys0nlz06uszszc0kx5dz62rqphfgagv4x22s724t9f4scnjh5azlupyn7a75npq230d8m68c3jxkhc6sh82swqnptcrm7d4aydn67f252jhnfpqnhqvgtpt5d9c23sfxqstwzrks86mmyqvc3mph2lfxzrarll7a2pjf8cyx6xfk7gyg8m23t609uk7gxxahdfceq738m98d02y4l4s23s97mct89cle', 'addr': 'zs14xl8d8pxmn9jyha3u2jv0kal3vua0w3n8gxgg6nc73ftlw92z9w8vq28m97nyc37tkeq6nx2vpq', 'num': 3},
{'seed': 'fb0e1064251a1ccf76929fadb239ef288b0fd46214280ca2c4b4e9623cc7a52b', 'pk': 'secret-extended-key-main1q0hxyejhqsqqpqrkhpqtukfdmusykfk77aznxvtkm5ppgr7yynjqy8h6xqxghaq8xp5u60xc3cg3glq3ydtxjm2l6uynjqlrfnzmpg826ef0tn77lrzqzdgsqxj9y4pngdyum0qmfmjmsys8hzljvgp205c4psx6segv5dc2dq23f8kslfrmftkm52mnx9wxzllgannherpjqz64lexa9dqx7wpngyattxf4w08y7ha6aufqzjee98twkpmmeagkv5e9m42xhfxjftcfpl82j', 'addr': 'zs1yurku9pq3yrz0aqum0le439ukyaxllgf38xh4lawnnkxfv5h2lkjhplqkstsw2yc6y5w6cz3eqh', 'num': 4},
{'seed': '80016964757febcbb2fcb2300d85fc4f39b3bea02905b9e8befe401248fd7016', 'pk': 'secret-extended-key-main1qvh68l9jqqqqpqyfvk8aqnd6tf8nznz8k3kqdlcl429j2v7pcjuy44ady05xj0leezwhypk290q6gky3upm50d9ee2waqlswq6nrlwqqlsd8dqtzke8qxs73jvr9kwhn4jwqpz7w59vgazqjdphqttm665r7c9a94yxt27gvfpkzg32mempk2ej24tv9t0p9drrea9ymun2tq27d0ygaa5vyxz8sr6pvv2mkfzgxlw54pl99hd7nhht8ajmhxv87vfayf8x9pap2kxsnzknf5', 'addr': 'zs1cmsn7f3fcefqpzvv5tfy4n2xtw3expzuu0t5676mkwag82yvg6f6lh0mh6mhht9nu7mz59ed8jc', 'num': 0},
{'seed': '80016964757febcbb2fcb2300d85fc4f39b3bea02905b9e8befe401248fd7016', 'pk': 'secret-extended-key-main1qvh68l9jqyqqpqykp762wz9m3t44njexzq4wq6r6gkr60s3psg4x488nree90jwggjenphzdr6rptmxjmtwmgjwxctdwdr6wemxnmtml7d99nemff3gsfd276gymt76tdguvr3td36lzytsf0w725uczj9v6zw4a0hmqnyc90qnfr0kzk8pqhk26y8ehz8w2v95azdd36r7xv74wrnh0rwf7q3rcj347v08k5thlrvwqm6qvth6vc8dg0rlgdf4s0g5a6rgl9dh3p5gu7ggfu', 'addr': 'zs1ua7yfqrwwyxklz3c6z5yqa6pwf3lgkpk482eje7nsszw8fe9uvmljpfmzxxma7jeegmg7lu8u7a', 'num': 1},
{'seed': '80016964757febcbb2fcb2300d85fc4f39b3bea02905b9e8befe401248fd7016', 'pk': 'secret-extended-key-main1qvh68l9jqgqqpq8n0qqjr03mtv9cd63hf67s4w5wcuc8v33nnhssmpc9f8fp04k6xkx9mpn6cz4wptx6ppzdw9ge96nwjnhl2ap5dmttc4gtngsxl79sf8d2hx3mrdtsuxcd8ru6km4vnzexfxu375t9akvzac52xtlressyysz94w3k6ufmtdnme6udfrkuy9nmx8pmqlg2fpl4k6q33f0yye4gag2teyp0j7fglch92vhgwk84h8ayh0e7cftwgsxvygc62fdwyns7rqs0y', 'addr': 'zs1gtdpmfkswlh2fnhj5vx2qtusgdzx6900qsnj27kjnytc7ncr5x84jsac8aymesq9g58y523z2rk', 'num': 2},
{'seed': '80016964757febcbb2fcb2300d85fc4f39b3bea02905b9e8befe401248fd7016', 'pk': 'secret-extended-key-main1qvh68l9jqvqqpqz74fnrstus4lw9vzeyysp9gaq4lsjgq8vy5mwl3vz2yl7lv4vud26c83jt6mfsqzc3ygh3y9jyy326gyumg757av5wx5mscz5zp97q3w8ul9hyx70ln7mgglqcuc90xdfl436slfty3ett69wta28f0qqr4qngf2e4xahgjfshzdkn647xan3n4gg7f75nufahm6h90mnjum5c8q2jg7vhlhtea2x6hkstqs7kgd5ryuv9c6g5wwd6pnseyzjnzns3vte0f', 'addr': 'zs19nwg8n5vr7x2un5gqmyx6gtd4zep6lnwddpm3hxvel4ya28ne9hcjum30yf5xu54vlpwq64tupd', 'num': 3},
{'seed': '80016964757febcbb2fcb2300d85fc4f39b3bea02905b9e8befe401248fd7016', 'pk': 'secret-extended-key-main1qvh68l9jqsqqpqq0wwh86rf57tsp7qxyc97hafgktynz6k60ugw6k6yn2r63k3a9csf2l85vh6gmukzsc5l79xes52f6hg837qju42k7ajrvuldlx46shhp5ptpzen5lc03gu2l0azu39nllxd9dj29ug3dw3l6xquq4txc9swr6cgyvq6d48g7xe58zxyet5j7hjvgy4zqutuc9a8446u4s9eh0pxwjqxuhcx3m3gtg4v0w3wq6fzw3p2zmet6jkr5whc9zl4f0yvgfl83e3', 'addr': 'zs19hr50xj09gt7x6m2lskzlztnh4ds7345qznw732cczd0hz6xz9r5wpr83cuvmp4tj8fq76wc78x', 'num': 4},
{'seed': '8eda4a72d266cc162699261b514e8f1120740123f25090432561c5b963a96091', 'pk': 'secret-extended-key-main1qwnk2g89qqqqpqqmvvs9axtm5yn85n3zq42txsuvfp3kgaqcjkaznzpe6pd7jfh3kuptan73jrsr43feu2u20u88ntqw480g2j02f50tey9tsu3a02yq69zc2849mc30gkq6uggpl5e0n0074mn5zy2a5zmkjpcmjs2fv7gzzj53uqrscnqqkandam0ggr2hwt33s9g7zsl55k6jnlfh46qhry54kqm0l6nn6l4xjsxh8e4h6quzctllcwcze35qtrkwdvvucamdz3scne88w', 'addr': 'zs1223t4t4xuwfedsjenuwq3xvw4c4xnx8ctm36ddkrprnwyrqt6wnxvgsenu4hvfsgc9fcka8dqnd', 'num': 0},
{'seed': '8eda4a72d266cc162699261b514e8f1120740123f25090432561c5b963a96091', 'pk': 'secret-extended-key-main1qwnk2g89qyqqpqp5ngvkx65mwa0c0y7crjj44hmwdx3zh94gawle4a6s3xsel9etmtx8787s2n96jktslf0gqqnqdx22ez7umhp0s4yau2fmadqza5qsqwmc9urp3zvcffpezv583s6a28s8vwzk4qrdzm7msjjjl95uy0qvk0ey6magkz039wl5w6dq9r96v9s37jl4am0ll4jjsy3j22lgu3cpah55g9slazhl62ux2yps2wgfy8duymt76e58hj96v4hls5qakzsx06hfd', 'addr': 'zs1a59f6tlant2fnvp4rvw6fxj3gth2mrjsasxz3qvkctxglfppnpnghrxr5thngd4ryuzgqz2ny68', 'num': 1},
{'seed': '8eda4a72d266cc162699261b514e8f1120740123f25090432561c5b963a96091', 'pk': 'secret-extended-key-main1qwnk2g89qgqqpqy65z4h452ue6raeldfdzvx2qsp8lzema236wdy87ksk423ckvutg7eaeduwtq2gmj0zxhhka83gwz25egap0cs2dace5rgjzcqp2aqyv3w2gsn6vvjf5p8auew4hkk0t5g2fwyytrx59hy07q9hlzsr8q8q9rvtwumlsq503g24k8gmtyumf0kgeyvtyaxhfse92hsws4ut3qq5hrjxq6gzykcv3qzgzpphsw3w00qe6d8gtgckmmywtzml5sllsqs9750m', 'addr': 'zs1t7rl8x5wkkh0vszhed5z526058c7ceuvlgdap70xlwqk0e3hynjz47j0hh76qv8anptc5rcx38l', 'num': 2},
{'seed': '8eda4a72d266cc162699261b514e8f1120740123f25090432561c5b963a96091', 'pk': 'secret-extended-key-main1qwnk2g89qvqqpqx2v4hnepx6px5r7upsgv3lnjmtgz3fg3m9az4g6eqlg0n7sed8akkr54xunq8pldj9804rc43xg5g0psnccaqx0kcgdtcwtzxjlejqv8h2n3lxxpwfae3m0q8g3hmefcdz27c0fm3zccd2mludrskaw7g9tt0fpsf8tcj8hg3wxzlfjhrgkeef2apusdh2zes8zz3mzsjvtnjxnlq09c22y5hxzgxa6j5cje96fpkku33ew6nj6mek9ehj552jxpgkk39re', 'addr': 'zs1msjhd2cutk8kcj4q9av8wdmlrnu22nxvyagqtl6v29wkqerpw0tkn3m567d9j4s3hv0q5ajyd5a', 'num': 3},
{'seed': '8eda4a72d266cc162699261b514e8f1120740123f25090432561c5b963a96091', 'pk': 'secret-extended-key-main1qwnk2g89qsqqpq9xeacc74yhamflky97lsvjkdkfed6h3zye4k2x4a5zlkpukyhg6y34rnf9hvw0f4u6xptwyn8kqhmrtp92yeaj7qyctuxs8urckylqj4zjvwg8vzkrvwevqx3ktar4ce0vhg8lsd2lw9st4g2ts5h5yustnv8v5g36wzkaw3ef6fftrh2y2padsxcx0fz03468z7rg959ydly4t2v7ztrzkrzceh7a8pzrkcf0d89drf6ghnt5p2px8h7ld0e8w4cd43k6d', 'addr': 'zs1qdje4ljeh020mf3rgn7wtm7xllwgl8fua9la0mwpnld3uktvy5mceskh480th4dprzeyj0kg8cl', 'num': 4},
{'seed': '42345f7de093cc855f780a74099ff94fcfd86dcd898ed617bef1563eefcbc4b9', 'pk': 'secret-extended-key-main1q0fawh83qqqqpq82jxgghq4zkzmjlnpc9a0lkg9xusrmst0npug3q4gku83aq28hae2aq0ts8y74gm66s9dvrq0kkelkkrz8qfsjahy2v269x7esn0ms0c94ga79ma34288r6mghw9840kh256xer76m9gpxhsywj4pw5ngzl2tx5px5qq7yf52ftg248mhxucg9ranw82uzfc39qad7reqxgl67jm6nlzdzn55ht6tqds6yhgvzfc3eawqnem2dhe2zfmyjmkvnesqdkcjlx', 'addr': 'zs1crgh8mugvnjdy6adssq559f36zc6du79ef27vxgunw35l5vr5kq6hpssf4tzm5j6n6uavtr999t', 'num': 0},
{'seed': '42345f7de093cc855f780a74099ff94fcfd86dcd898ed617bef1563eefcbc4b9', 'pk': 'secret-extended-key-main1q0fawh83qyqqpq8w85ttymk0u6u3kgdm8d8khxuufvj0sysnwjc799f3q2xnmhzrkmpa3u3x9yyzesz74fg5ym56mll6jj6w4udel24tl8y6e9p7u36s6sxkqx3uwzg6h9n4q4ektstvz9fntywa8szewvdan0xq68lzv2gd9kx0hwtvn7fnzq2tlq3u0pgqnklc20etu06jkvey8h42qggtuflxyr08ynh2gu2d4te3ms3pam6rx28enpg7yvquvkhvmrwr8yzwrngzd7cfv', 'addr': 'zs13zlmu476w3ul6gwjmg8f2f3fg6dxllhzetl4qk8u5vk4y5853jw4t9vpaxwswwmqs75k7rt0x2n', 'num': 1},
{'seed': '42345f7de093cc855f780a74099ff94fcfd86dcd898ed617bef1563eefcbc4b9', 'pk': 'secret-extended-key-main1q0fawh83qgqqpq9ucjhnv38lw5w3rpdrkpespql487zglf33k594jf7ztyc23dek6yqh35jyc5elc5t5r62cgjucp2c8fyxand2drkz3sdf2y6k3xs5qygkhlxs0026z8487865we0pl7ay6pa9tnmqgtv92gt5dzdz3xagxdzsdj2ugwzceurcu6qmqf69e00k82xpzkhk8dp5rndusnm8dzvc2snwed7zud5us4hvw7q3zmujctcyye3me4ct8fth4wt074cv6hngl827yr', 'addr': 'zs1fmlg4shzngeue805qruwrwsd20vlxapm7ge0zyzpfnx0cum2znqgsgll7r3fj26rz9qnucc5rqx', 'num': 2},
{'seed': '42345f7de093cc855f780a74099ff94fcfd86dcd898ed617bef1563eefcbc4b9', 'pk': 'secret-extended-key-main1q0fawh83qvqqpqp6ygpadx2gh3u402htyu44dm9krja32ewrqsj65k3pkpnee9gelwr3zmk5nujd0ma48fw9xc07j9nl6zssvdv7ajknzpjesmdsdkcq8l4kggfc6e4pfvsllz38p54dw6h579j9xvtk34k0tm0gesa93psyu8wq3ygda08dse9na5j2hkg94rjp8fcvxcdv7v505pj6up0s9qpj5v5ywnw7ankcm5kyvvzdsc7349m3dkcf9dgds7raqy4t35vtpqsyzjvg8', 'addr': 'zs1uar5zeynpmfs7h7j7lmltc70fqv7fva0cpdzzzy4g428tw2d0097hgk67q3qf7h0hg7gqa9pgsm', 'num': 3},
{'seed': '42345f7de093cc855f780a74099ff94fcfd86dcd898ed617bef1563eefcbc4b9', 'pk': 'secret-extended-key-main1q0fawh83qsqqpqxqqehfv6j0whfwkfxd03fv83xvf4q9wzhtp3422gv3520jlzm07smjpg55rnssec8suerrntp8p039mtz8tv340w76m53jdwp7g38qs22xtedlwzckf3efmnf942vhy7pakjrsnmrvwsj8cjphpuk4efcgcjdlrkkjqvr8qn0vcyykq52cmz7swgw3zvvf4v89zekf0vn7jaty8fm9yhdsqa2xps6dw9l6whda490j7jyksvxzghmq743xhegvv0st65xnw', 'addr': 'zs1ca37qqrlnszrg0aaga785dgl0wazcj8j9qhukkdgvz3rgjhu68zmw5npc9vf29hcsw2sk0mgzlq', 'num': 4},
{'seed': '4f50a025829824fb8b74a05baeec877275d7261216a55f6557dca9ae30364370', 'pk': 'secret-extended-key-main1qd7jq3m3qqqqpqxuy7npd3erk380h238dtxyqrpwehdq90s3ar90kp9ql7tgud7rrn42tf2vgcmfr7mmh4cfxrgt8uujy0wl67snrauu0nqqfz3zldyszxwqxagw68dq5zkmge4gmsrsv4slv86uqrmv8jf5gvyqg8ewtsqf86ldxqx6q7l64ryg2l48v5wv7eazddyctw6zasm2hjkh6ztcddhl8nykfqgj3a268xz4qzlsc4fmnswmpd2vwm3f7v69kncx8fty77g26yqkj', 'addr': 'zs1lqmr6gqhvpvq8cy7f0l3kvac2zsley8x7wg67ckx5u5lynk9lml563y7lwep6vkvq95vcrdmmy5', 'num': 0},
{'seed': '4f50a025829824fb8b74a05baeec877275d7261216a55f6557dca9ae30364370', 'pk': 'secret-extended-key-main1qd7jq3m3qyqqpqpuxq7xjaq5la46kp8maf7j3ejydrjsudhmryetd537cd2maqmtfqykf0yj9m9gc9r6y3r5pwfefq9j8gmnu0af5kxsu8k2g2dkdfpqam6je6km2caardtmxdtdlfgc3g2k7leral7q4xfwfh5jk8jvydqyyj2w654dycnx0d3xsucrx633u8zyssysgqczpcppth5lcurt6hkxzrnv7afphjsepvqx2yt7x8u695jmzle77wapdnzrn44059hzrzqh70pt2', 'addr': 'zs15gk7ce4lmz9wnz6dscz2dygy9f48z7tfehd6gdvsxs6gnq8g0ayv8qdklqtyesn7p26lxfp83z3', 'num': 1},
{'seed': '4f50a025829824fb8b74a05baeec877275d7261216a55f6557dca9ae30364370', 'pk': 'secret-extended-key-main1qd7jq3m3qgqqpq8ja9d7hlz3vu79nuaq4zgr7xqwgnesdl2vjaaf0j7r8h5e03y5qgrgm0dvmc8yfn9rq6k2k58pr9xcd7p379lpvh7x2ym003qc44mqpcajthxjfwtxd9g9h5eyr9wk9t76xahm50eftdrvx62fxfdn0ks8rf68336xhgynu57k5mmhr7xlxetc9yahf7nk0lsae9ckh3fspd2gsvv2kv0n99d0zqjq9v3se4pe88d67a8njy0fs7ktdf9rpxd2vegp5u789', 'addr': 'zs1nhlg6uh5lv39cjnf3tshzpr95v9vevfzun725pgymfhptaw9sc6qsk60mhfan7adh0edwwhhv2c', 'num': 2},
{'seed': '4f50a025829824fb8b74a05baeec877275d7261216a55f6557dca9ae30364370', 'pk': 'secret-extended-key-main1qd7jq3m3qvqqpqxmezycz7rt4czhgdke0ktx4j2qrpjwc2zjv7cclpvxqwkmuakx5vs78l08fcvj08g0rpzmmhhttwn08eh888ch7kly059ke05a8tusxxdppprpek2y469fg27a0q4c5jprqmlhuuq4swdr9qltgvaadlcd8yyu7d7rtqaza7tyfquxva32ezn9qcvm2gwngqdgfclylhgxfwvmqvpacdr94u99m0mcws7gtlmph457k4rc3wmx062yjlc386qm8wgjmjdch', 'addr': 'zs1955vuctmp2p3sfylqg0klsexqg3e2jvf0r40as8vr9lvx8qmux6nrsn7gtyt57r7zdfzcu9cszm', 'num': 3},
{'seed': '4f50a025829824fb8b74a05baeec877275d7261216a55f6557dca9ae30364370', 'pk': 'secret-extended-key-main1qd7jq3m3qsqqpqrjudctlusnkatx26puj0qfn86t0d8c5lar95u52hun89876m8tu2ypels5nqtu37eld252c9q6p0cjl9kmwkl289nxddy7uhc4plwsc2tk72s7xctjw8lfxvr9q89g7lgrzk2k7rh02uua0258cruuzzgrfr5jt7n2dhuzmuzakn4dw3uv7pfy692ce0l85xutmt5lkdv7q325uz35lw028d6u94eufp5uvmgdvzvewe56d05qmc83qd2vu72g5gqtzx00q', 'addr': 'zs1jdqeq43uf2qwc3qpdk9eg8d2nzc8rp55j4xr7kzyddmzmvuvxqt5ap8498hf7lymyutu72e4kp8', 'num': 4},
{'seed': 'a6c46f71a56efbcf04926dfa538a07516b1bae9e4fcffd2c817930c69780e857', 'pk': 'secret-extended-key-main1qdllqjvmqqqqpqrzsk4xg0rekdw5znsaptkcgkqhza9kwgxfpq053znpf59j85hr74sartrsl3kx5s0ne8u07amw0q5gyt9zjehs0vxn6p5g7eeeafwq5wc30z2j9njy6qz9saxm4r07500l944jj30yjyervdfcdtwdzcqy2twz88d0v7xr9fd2wvm77zkqdk3cf8llzfsj5pa0v6ruh4k2g79qcx74auv9esp87mleuzh536llutunth8fvu696hcvywv2k4nydpcywpad4', 'addr': 'zs1gmanmcpzu2pxmkn4jkntfmtc4gjg3d0fa5xhyfhfzd8snfnjjwncug7yx9tvtgnt9yfyjw3tukx', 'num': 0},
{'seed': 'a6c46f71a56efbcf04926dfa538a07516b1bae9e4fcffd2c817930c69780e857', 'pk': 'secret-extended-key-main1qdllqjvmqyqqpq937nnsd236c6m2fr2705d0p0xfp2vt2eamhjalzjcsrhfd866632sxdz2j5ljwr6sys7ch3xdlylmu0kagu93rxtt7tsrxpf8zrqlq3d5z2vgxr5gn6ler4zuku8qdh758hrmwqhy9afaan4g7ylu60pgpta62k0z3h9w3la8st2x7ald9azlfl5xslym0mh7287g7hlt229mp0nv3f2hnw24n2gv0jk2hu69xflrs7txlp4hjeukryt4va5ux60gm04rl9', 'addr': 'zs1fg8jg33zk99rn93wd06aa79fqvlrnamurszn7fwuqzwn59hac8m52dhep7f6mf86j9gxct9qwke', 'num': 1},
{'seed': 'a6c46f71a56efbcf04926dfa538a07516b1bae9e4fcffd2c817930c69780e857', 'pk': 'secret-extended-key-main1qdllqjvmqgqqpqpdze5gzd4ck0vsctg9qyfd7kq750wzpj975c6hxat5ey4hxgtpapvk98t0fkqvw2z8k3e40z4hnvf0kvk2ccldkda0greghqhhlj5schp63e46p45v3rtesq8jekwr2prpezt3xzt0gy6kkwgdwp9m7tqt59l9fxguxx9eyd4883m3ry4ag4hpsaz6wt7kma2qh88td9jhpkwl8qmd5wr0lypvywx6vuwv2u4dffl7vrgg9qwjnxatlqxq9g0dtdc458fjt', 'addr': 'zs1334s2zkajvefqdq0xexwj6s0hnafsfap8dmhu67zhgcmgas7y6ztkcjnjkjeju0u3lnfs2ltpzr', 'num': 2},
{'seed': 'a6c46f71a56efbcf04926dfa538a07516b1bae9e4fcffd2c817930c69780e857', 'pk': 'secret-extended-key-main1qdllqjvmqvqqpqqm7dss27x3vts05xrsjszqc3zs6sjwjgdtvn3pd4yyjdxq8hfpzjcfypwgnnxlmny8gk7qe5twc48ffwvgje3sanwgf8lcy7etu6ds59v5fhd445jhlyk3d9xac9ymxhuxc7tm9r2gh4gnaqnp8uqxjaqz9ls92sngeqwlhhskk9yaam6tdmyrswxq3egpvp8m6e9xajsasv0cptsycwpetdmu5fnu7g0jvkqf3jhc5fnmmn4s5gwt6v9c3ws3yjqsztl7h', 'addr': 'zs1fumdm36sejg2sf969vq7f95cnfdyahccekfrgg06ykx2ukv6upam8aw53dd5le2r9y9t2fjlwhf', 'num': 3},
{'seed': 'a6c46f71a56efbcf04926dfa538a07516b1bae9e4fcffd2c817930c69780e857', 'pk': 'secret-extended-key-main1qdllqjvmqsqqpqr9wezvx8ekg32aa9fj4rq0kq6vn9wz6w3tze0ecmxlq9p8vm5u9fu6tn8yldsyhmya0u0pz7eej23hfkjp5h6anq26mvcdfcsuvuwskexy32em8n0gp4qzpu898zpkmyvr59al90xak5u3w5emn8sre6c822hctn02pwd9y4jw8frpk9lyy5ydtlf9ds5fpghh8e7p2z8eksqncc0exu079slw0kkl5kkrrgp332lphxd9j7xdc6wmzyj55c6stlc0d5e4f', 'addr': 'zs1fszkv8ywyrpcd8qpnv489rrul8xwrf362sg3prx4gu305sm4ehuunvsf6ux8e558qn8a7ztzv0k', 'num': 4},
{'seed': '158c512478e525fdf38fe91b69c4e1302726b863119fef4b0ca17c255ead337b', 'pk': 'secret-extended-key-main1qdnmwyk3qqqqpqp0hc3qwluzlgnhrysehj297mgjff5egfza3xvhy824qccnak2ew64mfm893a0ngy6zcy5u9hqdqtqhvdvd4muf6m245pk7x9029r4q88hypr6c9mtflruchv0s3dcffa4vaz0v7ze6sxclvv72r8gvezgyat94da2xa93wzyntqmmqf3d0nnw4prpw9zgt5ys3cw9lfqjvgjp9trx4etp7luwy8su5hptdaayn45hy6kk60yryrf705zuhdezmpxgp5w308', 'addr': 'zs1qyf9n0avyflsy8xpv9xj54nl0fx3dtknlxzw2gqz96wwsz35j9a9zpa0aezp63wsaxd6qs8a26z', 'num': 0},
{'seed': '158c512478e525fdf38fe91b69c4e1302726b863119fef4b0ca17c255ead337b', 'pk': 'secret-extended-key-main1qdnmwyk3qyqqpq8zkq6gt2vkr5jzpgmnusm3ah0v8rw8m3c8z2p3fmc7mvsjsex3tzjlm2eka9fs932qwxxujyacnuphqnkzj204qxqlpzt5rlk85z9svtckgujs3ync0e6ervs327kndlnxu6v3wfx9v2mheqygrzg056grhcwkw87jxrxm9hyav60m2s3w9s450xvj4krs35pvf9u0vgkkts729u95y8n33kc77t63cuf9yx9wem6crt74gsp0xr2k430mcrspj6qlq2faj', 'addr': 'zs13krk0ndyduvfypljp5ryya3ucvx3tc2jtcdfvzxy3e9cpc45p52ww36l4r7gz20z94hdg7k3n45', 'num': 1},
{'seed': '158c512478e525fdf38fe91b69c4e1302726b863119fef4b0ca17c255ead337b', 'pk': 'secret-extended-key-main1qdnmwyk3qgqqpqy2537rhtu2tux980095wpne0vu0z6hetfmn7tvnaw4vnrzeeajjpl3wmvnva9srxdnhhqdjcjw3n6lp8nv8hlg87ftrwlkr0e06gpsjapf2ls7ax6yc4kczd700cg570sx02cgk7zh2q0nau4gg4khefsxhhacs3kmkltfgqckzmcyegm470la3jc098ny8a4ptyuszneur2zclu9udw3gfepgphq85xlj2mlj97vlyc57af725dr7wtfj8zcu6lgq0hxvw', 'addr': 'zs1exhdvzae53fhtc2dgmjx6ysdv54yfyqseelhalhemw2anxfk3jqgxhj2c2z6hx3nxv7rcqv0f6s', 'num': 2},
{'seed': '158c512478e525fdf38fe91b69c4e1302726b863119fef4b0ca17c255ead337b', 'pk': 'secret-extended-key-main1qdnmwyk3qvqqpq9z2qm6kw4qdqg8peujc6v292690jhq0924k0ujyq6a7869xlsm64qsywhanyzegns968ywjes8jag9379h3ug3ucjnh7tlw8aw43gs4m692w9x2vzd9pva0x4f3rurq2c6ffdu5l7rxg79d93sv26f6xsttm5wa2g48ppg73xkr9pv5qmfqy4aczrnw2yts4760alfesgc26gpl73mnfx4fr7jdga9hza9m7dcpckqetv6sdwthsg2f8q8g5956kq9l8dgv', 'addr': 'zs1sr6v9mand0pcshmgdrsv20xmecrty03r6x7x2sa73sj4p6kgjztyjcjecfy2padf2gc6uvfj8h4', 'num': 3},
{'seed': '158c512478e525fdf38fe91b69c4e1302726b863119fef4b0ca17c255ead337b', 'pk': 'secret-extended-key-main1qdnmwyk3qsqqpqzct8854y4sxk8jgjzvdyrjxmzuhjdj0rdtv0w9w9s6v5lcc8rsxwg50dtqck67mg4umsd7dn6y6k7jjljyvn62hnte8vx4azgs7ejscwex8c0rsjncy3wvtl646nccphxuws489t63d2grqrd66jdnenct3z068vuku5ku8m6zfzqmhf578unftq9kre63d9jarf2jtkd56zpxzsnp6nu6fcvh2jtgra7n5g6jnrq5fnnk83tl33296yum97usy6gkkclrv', 'addr': 'zs1093htq2j6qu748jpylawu68pc6ef5vtnlc603mu6qaxdu9gnzp7zg7h49nsh8n6q78yjvuhce65', 'num': 4},
{'seed': '9fc4c3853da069eb2a4438ece1dbb11601e1b519b033a0640fd6735a67c6a5da', 'pk': 'secret-extended-key-main1qwqdr6jjqqqqpq9wd05wxd20eandzf7383fgnrw0cxx93ut8f3533eydl83flp9s7xy6erk6pfkzw9qe37hrnyveyz2lzmga0qgztdpu6cxv9n5ymg6sz07dwdl28523sg9758vhag92rrgzq9hw0q2cn9r0c2slha6epwq2cf0zlj2c446znycpx362z93649yp0nmtq6p63r8nxgak89r43k877m8ldzvjjcfs9u2frd5z402tueadraa0k04v7a9mdavstdnyu5gzrrhe9', 'addr': 'zs1znnlc5gjq7cwh99r7n63a9sqhy6c0jx9s83aw589zg3sgqcqn0s00ynzuj5tg7c2a5tw2nr9ywy', 'num': 0},
{'seed': '9fc4c3853da069eb2a4438ece1dbb11601e1b519b033a0640fd6735a67c6a5da', 'pk': 'secret-extended-key-main1qwqdr6jjqyqqpqrlj43wh4c92dwjh9afgm90jlgsp2wd7fulutnfaguv7vsdcuvyftce0ffktzde5e9prlzs5e7ug8khepgdt00mfxxkmdfm8va6rnyq06uqtcl9f7psf6qydcmvg42grnqmxfq9xqkfqdpntd7x4t5s5hsptyqhq40ufjcn5qdpzlzeeqxy3fg49t9pznffm6az6jddxxe08jwth0caepurqyss3v0k8tgrud735nwd9p7sl79yc8ynf6k4v8m744qqvcq8t', 'addr': 'zs1twtmfm67rl5uurylvcv57705h2tkucwgmyedxkwzkjuvs438uudyag5psz9kue4wwut52vhyfft', 'num': 1},
{'seed': '9fc4c3853da069eb2a4438ece1dbb11601e1b519b033a0640fd6735a67c6a5da', 'pk': 'secret-extended-key-main1qwqdr6jjqgqqpq8v0c7z65c2mw28etf8vezcmh04rvvc8cvpmzlkvuhj54lf682duxjfvt2jcvsulwwx2ffqaj7lm0ug7ekd8z2kpkduvg4cgu0e8glq2dxa2p48e6x2mctnd8j6723h6yyptffp3zk52n0unswq2n0zgdsphl9sddjtk5pk2wcx8khrslu02kjn0n9n7g3ex3kplj7cvtz6u8jyr525pt6t9wp7j4puhmejaz8zn780ccqne4njf5ywzllklnzvy9qj52dzx', 'addr': 'zs1a79euahkczl68zlu8u7nk8gtkhfl4nnchlq40xsdqkncgt7dq6w3uyvf4le9lfsl453svks5m27', 'num': 2},
{'seed': '9fc4c3853da069eb2a4438ece1dbb11601e1b519b033a0640fd6735a67c6a5da', 'pk': 'secret-extended-key-main1qwqdr6jjqvqqpqz29lhre8gtp6hdlwac88ch5avmz4s0kqq2pr4zehpl8wu6dvhg9ekyv7ez9szlfpns3r9526cumtdjqwvsls09mjenna56wmwmhuvs5rks5xqvxkek2pt3mf636fhlhdy9k703xl6jtjhhlw05wgk69xcgu99amu9cxr90uyhyu7kffk5ty248pdcf9q5agndtszqem4m20a8q49gzlk73p2qzslptx2nz6twvlezyn06z2jdyz3kjjefc2wvm86qdumsva', 'addr': 'zs1nhvewjgc3p8l8vs36lk5h7z480ysf5cgdfr0435x2pfjt2y9m7ranh8c4a3vt8qslqjvjuu62hm', 'num': 3},
{'seed': '9fc4c3853da069eb2a4438ece1dbb11601e1b519b033a0640fd6735a67c6a5da', 'pk': 'secret-extended-key-main1qwqdr6jjqsqqpq84gxv5z0neh70hek3mu3m3uxfjpxyea6rthg6zrr9csnjajkk6ww2zwperg8n054glnm2llezwjsa26nx0q04hv9a53xf763txhr3sep9elsmk7tutgu5jkxut7flldlg9eng57wdwd3g4ctupra5ezggq2993dl46555ppy43avl5604vvl5j3gf2qqztxpgxk4dmk85sp8l0ldw8sa7rw8m6gl0vrpfakap3qhzsc7m58lg6s6sxp32gr6y42wq27q3wm', 'addr': 'zs1d63tkytz7rewcy3fpv4tj6j2q4f0uut43uv2egwywght730rycghcfnkeuh596n4rlnnvwcsegh', 'num': 4},
{'seed': '70283b14ca02a45995b5847cc62cf6e18c7ef415061268f9893c2fa093443a43', 'pk': 'secret-extended-key-main1qwtk5quuqqqqpq9c4xrcq3sjffmlmgsghpzqjfrrp3z2g2wg07kmjrj3numtjjpwd4ajpushgamwsxa53sjj59m6y8g5e9vvtvcpqz0px8ykxwwtyx0ssrzqrsahcu0lc0amt88pndxnwzah5dnv67xswjrc80leutzfzeqwglsmp5rkxmr4j2yfh3x2a6q3mstugutsef982ymetmnrll0z6zmlst6apxnwvuhvevyv68wp3htf0m4pxsxdf8zwghfyxdrzz092twc5y0c4l', 'addr': 'zs1rv4dj5hk6h9sc6cu6f0fpcyrchzmhdc5qvvljgw00tmquanu2qk3r2mfcfu6e3f9g2cvw2906xt', 'num': 0},
{'seed': '70283b14ca02a45995b5847cc62cf6e18c7ef415061268f9893c2fa093443a43', 'pk': 'secret-extended-key-main1qwtk5quuqyqqpqxxgm4hl2wdnynk6htr48cadexhpq3zyjr35pf4yaj3tq377umyktn47waez99qrz5hq8250e0gaexw39h7cya0dckt7e6y8udkakyqk3g0uh6myavnfsuuh0t9yrrvn2muk0hc2vuuwukm7ate9af6dzqxt4wdnlkty6rgtravwd4dvrjkgs0dq72vayxh2jsvmx55hcwq8jyt6rs6h35agtddvdqt5u5l4dfff8wy49slcnzfwpuk53keuy5nhhgg274gw', 'addr': 'zs1mckqvvc6eszv9ltrya9khnmdxhl30gncflszeekwtq248eqrtfx426m7u5n4gcxdh9xy2deszc0', 'num': 1},
{'seed': '70283b14ca02a45995b5847cc62cf6e18c7ef415061268f9893c2fa093443a43', 'pk': 'secret-extended-key-main1qwtk5quuqgqqpqx0alshfj93nr8dhyzkyfyu75f66hmwkwt7dhe3utqlycqsn5x5x05ncjswsz0l9qcphmwvf53gjhnf8eq5lz5jm4y5422elsnhqpds5gsy9majgqga9pf30x2pgk2ddllmxzgfvdy82qqnvqayra3afjgym3gl4x3lg8w0vnf0s6vq0nsf3yqm3awf85u9ew5xtlj30ct79u9zt4a9esq6yeqzqgru05nm0znsj4724sn9r95v80snqcs2gvlh39qyzf5em', 'addr': 'zs1wxqma6dqpyx5gr5ph58ljxw6g4thjzcwz45r09t092te4sfe9kzvv32ev2qhp0mtzv4ssj373hz', 'num': 2},
{'seed': '70283b14ca02a45995b5847cc62cf6e18c7ef415061268f9893c2fa093443a43', 'pk': 'secret-extended-key-main1qwtk5quuqvqqpqzmams0xj7ewu5kp78nfeenz9kdzxgwq5ls8xckkldy5xj2dpztl482u9lc4pqd70xcufm0kvx8an67hfqexqm4ad00javs9qpgl0js35udk3hf90kx862pectxdc0h3shkpmkzznnpyamvjlrnxhyd6kqz54yncjsqq8k4nxy7z9lfzq6g97ecm86asn7xvuwajayguaz7r5vtnt3h5nnxnnfae7lcs99qj2w9xmqr3s29unk78prmkp7h2ght0ngm69km7', 'addr': 'zs1pnpjs9pacdyvd7gh3cplpfvh5t5gcl7s6gk72du9v3gjhkgvvrrq72nh4m56u6a47ehmqd6cktf', 'num': 3},
{'seed': '70283b14ca02a45995b5847cc62cf6e18c7ef415061268f9893c2fa093443a43', 'pk': 'secret-extended-key-main1qwtk5quuqsqqpq9nj0f67nh4r3lwzgjzmcrs7nskfuytwhfm37ew3etlqzgvuss4vme0l8k9j9vk5x92k5wz2zkjaa273zsawkhwt4vetnzufzt5prdq9epwhm3fjjjpr38puzg9frfsfh2nxr4rn7h9g4jx2l30sq7dx0qv5p06ugezm083qk3vsexpxhxgwlwc0l0dv9jnnjapw0mf4kwcvywqpcnysfmlhlqj24ju9wmaeuchcve3ysp44zwe0z5l9jqjk7k2pvgsheg7s', 'addr': 'zs1l4vuehxhjrxs3h7vlu5ucv9xxspxkfsahye6fnr305uws4dn7892jjvv77tcjx69kkqjk5eppem', 'num': 4},
{'seed': '38a8f8bb406836063c855df012fde278801035d693c76f076fc5c927514b6a8e', 'pk': 'secret-extended-key-main1qvflrrxuqqqqpqqav0gwam0q288ryshujq2evwd02trcxz88jh6tjkrjtuh02x4mv0xafr5p3ekkhnwquyyljqdwlncu7xeaqwd2yde7tztd6hvcmamst45rvtz693c9t5p9gymdj8p7whzl0dq00k0y3azll9u22yr9kfgyrf49jatwzk3ssdc3wlql5q9qmj9hk8e07r03kn9fuskdwx2t28crln3q74ghrarum50f5tuj540j6spw7j3rl9ahssgfw6n8zxv5fnscd8rtp', 'addr': 'zs146dmydq4tnt7frwpffdk5m023w2n6eq8ckdfznpv8zn87hkd08a8m2vpp5ypf0gtgzn2srpl9z5', 'num': 0},
{'seed': '38a8f8bb406836063c855df012fde278801035d693c76f076fc5c927514b6a8e', 'pk': 'secret-extended-key-main1qvflrrxuqyqqpqra3mqfylmhdglfycna5dpecfycv5c6psg2sj8exqradl8p990uxr3ulhd3warrn5c29j5xr7tly4yz68hq4j4cv6qlqrdc0wz6pxjssdhv80mjjuq4nf5f822n8p0x4qaj58jka572v0kp6rs48fs79rqpf0cyyfuje9nx28n8fwj62jjstgps62fj78aj7zdy8cfl0kddg9e58f0f8cd7np4nc02rsj8jlre09gev04s8rc7mckzrnffr3unk65gypat00', 'addr': 'zs15zqjw207m68gf74wxd03e0f5834lky4c8jv3sax29ry5hptfcqvrv868vxeuygehputfxn9r9f0', 'num': 1},
{'seed': '38a8f8bb406836063c855df012fde278801035d693c76f076fc5c927514b6a8e', 'pk': 'secret-extended-key-main1qvflrrxuqgqqpq970d0xmh75z0ydg990knmkh7hzsj9mx53uwnud9yy6ddxlaksulcunxvunndv2qqc6m8j2wpxmcpsfjtanrcmt5kdhqfq3z5and4ysd942gwlthy6sdvpdelpdvjydzhtghwlvrsgzv6aeaaeqlsar4cqqpv8tlgfzqgp4t3y7sx5scsv8xdhq6669nk5xvjpe7sum9ayagjqhmsykfp3epn9uvrfm7yemynmx4j48v55cxa56nl6w9a6mx44cd6ctzz3ev', 'addr': 'zs1wvtrhpv83znwgemk67qx8390ex3ywx74a9yezmwhj3axnftwyledyxm42wvm0ddrr979xykvwcl', 'num': 2},
{'seed': '38a8f8bb406836063c855df012fde278801035d693c76f076fc5c927514b6a8e', 'pk': 'secret-extended-key-main1qvflrrxuqvqqpqzyrs7u6un92w00d8nqtu5lr75wyj9rn8p36kuvl0drxzukmfpxgwhdacwllwnkhnsednjdr690f4xa30c08jd8vycc6crqfcmudqfsymna7dqt2kl8jnkrq4p4tunsr2l2xzz0raq5m89pte3gyztjwhstdh54cqp7kq32ttevapszwe8ft9akq90q400ed6eqavu0y44tmeyzf28d5tztd0lpwr6cr9v9cfurpmjg3n2n2gdxme2gkqnu6u2rgrc9ga8wu', 'addr': 'zs1hwus90jmrht4wywqlkk53u757ree2pks6tmyms88j46uzk5fxjtqlekk9apquysazt4r6cpqz23', 'num': 3},
{'seed': '38a8f8bb406836063c855df012fde278801035d693c76f076fc5c927514b6a8e', 'pk': 'secret-extended-key-main1qvflrrxuqsqqpqqasxk0s2ft6rl8xkewdfrfvpaga67g3m696qsfljefvsfuf994mpf44755helzday3vj0hp6nv99mklu4kz0vnc2v90c9d2ug0d35stzawx93uy32w4v9aehkggakgffjddazg42ke732dt482x6kf9zqrc76zlrq7ztm2xpypuzhk7lydsr404wfdltt4egr3fttqnz02z92zgf43qkvht9pl8acuml47hzkymvxznef0hsye3hvmgg206ma5njckvr7q8', 'addr': 'zs1c2uu3m2xdfvveesccljww9aqd0n8nwvfvxpgdndncn9upn6nlv20drukkcqd3kaw5sva7k2d0sh', 'num': 4},
{'seed': '812124262dbab62138dacef696d7f0345bace2f650f3cf91536777752eb1cc31', 'pk': 'secret-extended-key-main1qdvq2sevqqqqpqp3qa0kwwrph0xnytwfsk9nqmhxa7uhvdq2xdx4nnxeccepjg72euxggwrxsfvpsrx7x7tkn34v667tzg0le0lvvakc8t6v3yux883sg80zgq35qeddnkk5kvytkc8yqp5etu5ypv00gztwv9mn4fm4pvcxk5659wpmjtl2v7td5hhct0ufwcunvxe3zg787fh4gjskwu7243q5zd4tmkghaedvqg4q4jtjps494ehqfjmye9c8gr2zmcahhwemgqq98mqvw', 'addr': 'zs1h72vhyharj2jvwmf2rkhpw62gy2gd6cum2lv39p7slqy4r6tmqr9xkrrqhsfs7g5zd9uwxm479n', 'num': 0},
{'seed': '812124262dbab62138dacef696d7f0345bace2f650f3cf91536777752eb1cc31', 'pk': 'secret-extended-key-main1qdvq2sevqyqqpqygapmgfkq60s7qe4fru2f4aa209ys3snnz8z4r929k2nucj36dad9kavrjzy5wkha9q9hflh0lqvd553hmqjqjsez7sdjw9tp2xuuspvzs5qlepk2wrmae642x6txewjy78gccxzsm4h5egju3yalgmgqq56zds7249umzdljn3p736tnqv0py67ggtf0y4sfdjj84jp5lsmyrjvws7u4s78axmcd8hz0439kz25vqynuu3hpy22nf28qa27jy8fgc087xp', 'addr': 'zs1sxsyxs8r4p7ejqe7cx6d9ck7nh5vnk8fjy3dnaa5v9fe95mk8jfd08ym5nxuw70w5spu2ux3gm2', 'num': 1},
{'seed': '812124262dbab62138dacef696d7f0345bace2f650f3cf91536777752eb1cc31', 'pk': 'secret-extended-key-main1qdvq2sevqgqqpq82arfl3tpn4rgpq475gcxr6kq985dd9v92wzxwj2l6aqx357svjr47r6k9cjewu38ax77un79rna42y38pr0ylzlfc27qqdpmtqguqndd7qkcw7nujltqv6qu7emtcs7flpjgyx3ag3wpl3ymwtjux5mc993yxdnkaq03udwf3cu6nr202uyfdcztcucdrrpmau7wj8x9ud96xj5vn3svkc0yfsk7vwt69qhzqntll9n3k2my49lddfyd33x0hr9c8up8am', 'addr': 'zs1uhzpgq20lmvwmyd2323khtp3w45z7dkrxtulzjmjtrl9dl0e7pmv9sph76wta9y4f4ydu59tvwe', 'num': 2},
{'seed': '812124262dbab62138dacef696d7f0345bace2f650f3cf91536777752eb1cc31', 'pk': 'secret-extended-key-main1qdvq2sevqvqqpq9fsfju06gg2txdngl69hvh8fhduwfrqze0j4nm3c8cmk509l5ycq9qsnlkxse9p2yu92na9kajhedk3ntjghu5p40lzvwdh5wlhtws2gs63skzaj84qp9p8nvztfuuj6lyfgezn0ks98y3nrg4tavzsmgx4jh4xwzv96kt4hscrzknyyj6kvkl3sws76t3zzl8expmdj08qnvfzugd0gerc4stzft9eyfuhgfuxke6tx9acj2yjefkac04z0e0zxgv2v3dn', 'addr': 'zs19n83ju3z4k860j8aes7f9yz780q4re29wpyl9v2lddfc5cmsstefchewf5qklt4jmf93jrw4n44', 'num': 3},
{'seed': '812124262dbab62138dacef696d7f0345bace2f650f3cf91536777752eb1cc31', 'pk': 'secret-extended-key-main1qdvq2sevqsqqpqxdlddsh9f66cwjwfy2pstwtgpwgelk260mtt772f9dh0eg223zy0d8e0g800hx59kyqed2xy78v8ujyycwf53mxykf6dgrdcshwwwsqfymxg7ly9ncnr4kemjk7e2xlqvsre83mlmd2qdh3xtene8v9zsy8et5ql2el6uezpfhunsd2jarq2jctssx8kf6yfgz9em69mpe42kpgzyw7dt2ynnv899k2dcnckc8tc72gt2wnnyjd0f7l038dx95zgqu33ruk', 'addr': 'zs19d6fun0fa4gnh33nzd093dv5hslqtmg5hqs38g0ch0dpyx5745utwaq5lzmxg47cl9r258jqpwq', 'num': 4},
{'seed': 'a0448451a067243df434b8e1c4caa318e8bbf0106a13f43483ace21117838581', 'pk': 'secret-extended-key-main1qwlfvzkxqqqqpqrs4unjdaj2yyqnlsausr4lxc6hkcn854mad7zrmwmwqnq78vxw2e5rtkhl5rrms03vr6dlkmpf72sr0e73ycfu4r7k5vev8r5ksc4suzga6ep5lj4vz6ewuzsqplurrph2c568fw3vse6umvmcc2xxpzg23m0squac5lgrnrulkuf270054e3swx2aggw2qwujkskfcjmw79kcfc3pss8d2xhtg55kuz4jgkaxxttve6wrj4kgk5d8f20qzrrupxc5ea446', 'addr': 'zs1fdgdkfuu70082rdty2qmxdg94728rg2wm7kptgmhzqjk0q4d4lrmjrlvd7c209ddghq4xcxkdrq', 'num': 0},
{'seed': 'a0448451a067243df434b8e1c4caa318e8bbf0106a13f43483ace21117838581', 'pk': 'secret-extended-key-main1qwlfvzkxqyqqpqpc74yljczaff0m8x29z5v8ukzck2cje4kpd0ykgwl3t3y2dfq54tyaqaf0tgudpzwegjsgywl3f0v55srx6xrk8efjamduw9y9mlmskp4qmjzjrc528gkhnuw25uedjqdqhkuwfqzumhkpj2w23nq42kq85tj0gvy2c7pdfgwwjv5wsvdnlq2ss37teq4lzkm2h9ma2ygxutcqqla63p7d8tr8s20eh82edjmvf0ph84lzx9lhnazncus0w4xaavqynhfd9', 'addr': 'zs1hyztxd57750kd0nsay6ljehp0fa7cq46jgf49sydhm87lqug0fj3enzcjs8uc4yp9puxs2rax8q', 'num': 1},
{'seed': 'a0448451a067243df434b8e1c4caa318e8bbf0106a13f43483ace21117838581', 'pk': 'secret-extended-key-main1qwlfvzkxqgqqpq8754vg9kyxfehfzhxdf8phf3r8qkr5dldeavrc7jv7emuut34n03zll0plndye303n69g7r5hj4g7ts68m4a24ddsc4er8v9vvzlyqtr04ggw5v7tg94yvw9sqpwltwtqqkje3vyxlqn7a0utug7pr6pgy5kka9v8j26dr2aeztxndha4pxf9p848xzu3qargn0plkt2u6nn3k4ghh7fa49zq3c4fw65zed82rljndfym3w5thpkw9stauc52rrpgxrqf8q', 'addr': 'zs1d4zxdzyl4jg4wryee2mt56qapc3pyez3kxjjxeg3wl6pc5hx74p5cmjxdzgfjcf96tjzc53y5em', 'num': 2},
{'seed': 'a0448451a067243df434b8e1c4caa318e8bbf0106a13f43483ace21117838581', 'pk': 'secret-extended-key-main1qwlfvzkxqvqqpqrh2zdymmdxm20mx2zxpdxvcp0lcfnhv5p64lt0v2w50kscjjqrd7w6r06mxx8jp45lxgmu2tctkmj6nq5z7jm9wckflv47ejweq7tszygxelstd2lsfpdz08lh8y9wdqc5jaemt3xrapfpkgrffzejk9gdmluhagukk5qftwvjfctarg5fwgv78fw8r568ljua5ssny9zwvnv63pfdjh6mcmm0u4khlgx5u48fryy96ejd83aexjwncmf3ca7qtjcu6p8tk', 'addr': 'zs1gmpt7zt844l6tvhh5jkn5szwm8mru9q6y85c6x3cls5n9tu84ex8ufy2gjgm26s862es62sge97', 'num': 3},
{'seed': 'a0448451a067243df434b8e1c4caa318e8bbf0106a13f43483ace21117838581', 'pk': 'secret-extended-key-main1qwlfvzkxqsqqpqq4eujdng9pfe5cldhnpt98zrca5seu5jthxnecmdh9wmsujp3q2k5enjxu54wgf3jh9u5uta43mc7cf9qhtkvt9hy7t62vd3h6lpwsr4vqemwy7849qxjhwtmjm9g9m77whalnaz6qnkzgww737pttcvg9exew02p49vc8md484m43e36vvu0m2884fnpa2cda3zvzhw25pjkrrgl4tuujv5tzmq5m8ms9j4lcwerxr0wvawfqfnqy4v6h3qah8kcg8ydls', 'addr': 'zs14dzry0xvyy2hyk352gjn503p7dc3ejxj0waahlweurgrgnm4v99afcgwr0gg9ppe3s5c72cagy5', 'num': 4},
{'seed': 'bcf836d2ed889f0cb18c159e8ac015548954f9d0898a212b741be21ae8b05fa2', 'pk': 'secret-extended-key-main1qd26sx2vqqqqpqy50ts4tw48w2rn2gckz3grxjtgx9ew4uznzm2uf4ukfus4uuy42hr4qweweuk9mcmz6vs7ar35j2ht4zu3edulu3dl008mmz3qp9ns6n6nudevpw50fsuew3emlp9ev536xr8zljsqleznzj3qzntgjacw0qt4ztpm48a6vu73fcjkg5tmt5x3y0hme0wpvgc49tdumedva9tu26twus4ycpertlckt8khykw38drju576dsc8jkuncrjnr3f9pnsrzhusd', 'addr': 'zs1c4pt6slh7zcqw8uujepc66fxln2yv4dkswhg0ppajc6lmydrkt5y45audgqyndkde2qw2ujurgn', 'num': 0},
{'seed': 'bcf836d2ed889f0cb18c159e8ac015548954f9d0898a212b741be21ae8b05fa2', 'pk': 'secret-extended-key-main1qd26sx2vqyqqpqr6agsgxgh3dlgctjcq8m9p2a9s5k2spf4zhwglkz9nzgyp0pc36rca287rw3hr3nuyxglw9nnhja32nsrz5hw0z0ztzhdxznf959sqwwezt3fej2xfh9d2aclryjdkplfqmvsjqzt3gamzqd854f2qfugrvllztj8kwrx7c4l4ufjrm2dfj05vmxp3z7jc4399nzq3mtkv7uz2yp7fk98sm82glv97rdyz4wydg5jvzxr832n27fvz5xrt7adyczqms82um', 'addr': 'zs1c7v2decsylkldl7mmkvs7cy23efcwq9hwajrt9pq2ccu8f6xu7jqvsny8yp4z9fhfp6as5nge0z', 'num': 1},
{'seed': 'bcf836d2ed889f0cb18c159e8ac015548954f9d0898a212b741be21ae8b05fa2', 'pk': 'secret-extended-key-main1qd26sx2vqgqqpqzgf386au76yhunpwaag28w44pwmurw2v368r9av893elngdrw6p2lha5f5ehk33y9jjw8rgdsratsxpnwelp68jkg58ejwh5lm7ktqwpl29a0y2v4z3zvv2le5dvhtvsh6ac428vlr4qkfp3f5v5xc96grthnnt8jxn72rygq6a2glj8pq0mzkh32dc5fawg828pkphekeahuj0tu5lfh7vqmcmydjxf5msyxyr4ukslzvkwhkxkc9myhmut0cwtcpu0rjj', 'addr': 'zs1g26r3jmdheljga87h648z9a2995pc4nttjummjctdh49v8nzsaypduketql0ds74m4t8yx6n0xa', 'num': 2},
{'seed': 'bcf836d2ed889f0cb18c159e8ac015548954f9d0898a212b741be21ae8b05fa2', 'pk': 'secret-extended-key-main1qd26sx2vqvqqpqrm92epxrtyptkra3gunjze9g9uf48rkxy7dnlc6606ch8cu48hg8y47yj84zlych2mly2r6k35w2snygl2exn3ls24qua550ra6u0q03x3lc7s9dvmj43yh0twv3fqqlc0uzplpa9ndzyt9hkrz5tlt2qvlcms3xwxjnrhcj8mrj2vlm5qeh5kua37kunw22a85yx5kzdkrru6vcm88x7m8tf3z4tr84s35m2rkf4tq8taxf32e2pe9s9vg5qngrcy5q5qr', 'addr': 'zs13rr2ncxlzwrkw4ma0ek3f2tf3mxeha047hr8g8ea90z56zkna29fvv77jufea0qgx5wpuxex79l', 'num': 3},
{'seed': 'bcf836d2ed889f0cb18c159e8ac015548954f9d0898a212b741be21ae8b05fa2', 'pk': 'secret-extended-key-main1qd26sx2vqsqqpq8a4re2344dqhjzqqjx83jvwt0yv5prpfg4fa4fvae88z623m0vuzuz4hllv3nurjt3geyf4yswpdy326lfacaqr88ke6rumk2ydagqqwnjkhumkjna2ht63zl0szve2wk2jv7hph7euqxa879uw0z7kns80am03dkfmhpsulrzdp8x2neg58ha2p9akzza5y2u6cxfndk3k7nk4fcjwxky0gceggpvux66c4ld5nhnf4cunrx7d4kjzqw8j5lk00szx2shr', 'addr': 'zs14vw497a5qvcvj3qj38vrnsmxr4xjtwh0rzjavtj5n68md067y2futs0wjgl0kmrzve0tglmx5ae', 'num': 4},
{'seed': 'e3ce2fadd2d1e22d964442aa118057462b93fd0e000f085e3bfb58916842d8e5', 'pk': 'secret-extended-key-main1qwwehs3zqqqqpq85akjkzq86ua7dt0t8dde83226n35ew9r0vn6khzvydnxtjq6wgqwcr0krxfsrw3zrrcnhpf0sddtnqukygcm8l2jh4ccyqxp0rxssmng79h0u8dq69vj25tsk8dsnceemkhwq74sd2a4fuj24gjzc4aqx7f5j7edclxvkw309g6k9vmuyqlqklz5cpx2krxazjvpjmyvx0pvm8xvuxjl3s7wj7pjav37hvxpucsduf72h0ryl2qkrnn2ezjj5cgqmczpa9', 'addr': 'zs1khqep6xepy0zm7mtnmdkl42nakguqwhwpe8g9368c56anvgww0ue23u0lqtr8zvwxqd6qm6q43x', 'num': 0},
{'seed': 'e3ce2fadd2d1e22d964442aa118057462b93fd0e000f085e3bfb58916842d8e5', 'pk': 'secret-extended-key-main1qwwehs3zqyqqpqxpedawxudc6u8qsapnj005652v4erh65n435asrlupzvyfj9ljumtavepvrpvlrwa22hqawgpccl373jwd7fnwk4ur3658lvsgltyscj0fr4l7lkgww6aaz4mq4y48yva8z098wkrxagle2evvn4cstfsdaxgxq05a4zueee8eqdtmyg8nkptmlmeh43526nyqp445qgpt2zqzawx890m3ufgk4pazrrtpzxzaghg4x9dpvh2u2g5cgukm5ps6rwg9x6v25', 'addr': 'zs1l6p5mnn4wac55mlv2u72gsay8glv7zl7486hnvy9wf8jfm6tydpyljvyfzwkmf6wsqydjhhl0pe', 'num': 1},
{'seed': 'e3ce2fadd2d1e22d964442aa118057462b93fd0e000f085e3bfb58916842d8e5', 'pk': 'secret-extended-key-main1qwwehs3zqgqqpqxzshv8wc00adcsfdk5gc38uq62nqcjc0zgw4vz097s6h9t5j53fctt8p7k8j4e08wq3f8tds2l390fru224surdz4xunktwh0f8hls4s8ca8f8jg0ujqfvy7jzheyl60m5f9rc4l9ur6tzylhqhuk9nks9l8el20arl0mdlyss0yufk6nh2c2yrpj3rep70u2d33dc5zcgw2nnsqf9qlvns44nxhrg8uln0eth9rspzqgpswm5y7hkmtxt3xkz7kgtlgwds', 'addr': 'zs1nqpx3vhgvnc0hzezuty82hlqjd4vsxzl4fdny3l8eqn3r3gje8j0wck90nsy2gypr4zlqhwc5rs', 'num': 2},
{'seed': 'e3ce2fadd2d1e22d964442aa118057462b93fd0e000f085e3bfb58916842d8e5', 'pk': 'secret-extended-key-main1qwwehs3zqvqqpq9w7p2uhvgd4tkdc0qp85wqvmne68dev4feqrjerpsqexlt2uy96mgmh8mu7ad7fdxgfzf4plj694xdzaq9kuta0huw8z7dw00hcueqaq3pkrzfy2v4w5yhl98upj0q4pfsyw7vwwlfhwa5747f0nh7fccqkdw3zjsem502s3ce2kx8gq0u0zmv7772mze6mgqc9rf49d70h5dtdv0l275srmx6rf05q0n7snedpfcfgn9vl8f3kfs7l3ex7htwc6ggdl30j', 'addr': 'zs19g0pckku2lecr0sl9v3jjx2mzh9kka6snsukrx72ea7nnyyrux6k7nqctt7rgkd2p245y9h6yhv', 'num': 3},
{'seed': 'e3ce2fadd2d1e22d964442aa118057462b93fd0e000f085e3bfb58916842d8e5', 'pk': 'secret-extended-key-main1qwwehs3zqsqqpq89fwyv3nsdmj6p5q7fysw8f74ms4n37wpkknf54tn64r3cux4pce6a0twjqpkyatgll0ukkkxdphznglkjpncr4ezm6xfpe8hkzers5gmmu4yyjjyp4frgaxx6n6wtaq36h972yustvgze8aday0mh0mqdfdh0flqrqzjvnqv59aytzteemahdh6wgg6w2wjxas0v9av3ann9swpv298w4n25x3camuhvavwjm6dxhjhrvq539xrm4ucvv5lkm3cg4l4v50', 'addr': 'zs1yhtcgexlx0vsy4csfpf6jela5dajgw5kf32v2pae2nq8d8scue9zvg8lxtu2wgdsxwe55ek25yw', 'num': 4},
{'seed': 'cdb9e5b2c0a8b4a9328643da2d1f7e98e85e91df123381b9d9f6995824e995f6', 'pk': 'secret-extended-key-main1qdhux892qqqqpq9dsn2x9erc7srttvq6ns7vxscg0dwxnu83jatdhwt83p8kje8zlvtswhxlvtu6hkrdya5p524y4ta9vuekg8vmkzl4ch79eqpx50rqh54gxnjcwfwx9mjnsafc857la0j8qdjk8scphhlrezp3345ej6gtz8ttk3ypjxl9zsttrav3vp5svdlanm6rux76gqmthdle0nyxq5kzrm2jr2uvlhc0jsd3e9hrg90mhm5f86lf0k9furmd33kv8m9f3qgrc66kw', 'addr': 'zs1dfs2m8ggkrspzjlu8pgjra4djw0kqk2cwzr8r22ux4764v0twgcnhqga3ufjpnc7nvnkj3e4p2j', 'num': 0},
{'seed': 'cdb9e5b2c0a8b4a9328643da2d1f7e98e85e91df123381b9d9f6995824e995f6', 'pk': 'secret-extended-key-main1qdhux892qyqqpqqk298rqq5p2ftahmap5ctfaw83nla4adct895mg3g5a5kd5reuxk6v8kuqghmg4h7ry2rpkqpzzgj4z50335kcz4euufwz9z9vag8s9fv4fahyfdxhr39xkak0g8nqgtf7zgx8h8khqam0dy364jwx7ys9h3c3p6t2dy85jvv7dd28q8gwx0vgz648867240e80z4g6tznnd8d9ced3yjctcmz44xlljts6t3hg36u3vw5at0xh9tqx3g6zqf222suwea7c', 'addr': 'zs1x3zv2x9a6sh5563pnp9qjwqnpt6dg3cx6ajhag3uxha403de0xf9h8p0sq534zgan88a6l08e7w', 'num': 1},
{'seed': 'cdb9e5b2c0a8b4a9328643da2d1f7e98e85e91df123381b9d9f6995824e995f6', 'pk': 'secret-extended-key-main1qdhux892qgqqpq9gg0kk7j30vw2caxazcdz4sqh4fr546e3kylded7d657tn0g9eumkg4t0xhek3zrt3pexq08vf394fdq67f93u7qhhhwy3m37zjy0sc0umju3pep99py0au27yul9dt04cged650mgm22gk5rlrj9aa8gxu9taqwt3hggu7ezy8tc0z4lva7w70c4vd7929d9l38tzhpngcscp6nm0v8sjdjsm4vrrxcv6lzrnary7j4sy43l6d0j78k72sxw638sfclzjg', 'addr': 'zs1c7ex6jtcx5c3n2qq56vtmmj3kvrwta74ltsyrged6f5w80vk902k0d072a5jq85tk24sw4t5l4j', 'num': 2},
{'seed': 'cdb9e5b2c0a8b4a9328643da2d1f7e98e85e91df123381b9d9f6995824e995f6', 'pk': 'secret-extended-key-main1qdhux892qvqqpq9kxxa2t0fl3tgvgjwjky03z0k5x6nm5qfz4vp06sa7z6046e7txgcecwm4hazg002w5w8l48c4f0vlff24r33lm8lcrdhkmxh7yssq4gtxrmtrgy3m4wcj6euhgnym2cu2sf8k329cxdcjte3jlu3m72qryuul578fw3r2yjrquhne6uycwnjw82pckaktd0lk8c38lsq9pycsdx9u2flz7vrdyat2neu82r5q6zw5kkgys5sqdly2gvfe9tpeyngf9y7nl', 'addr': 'zs1elj3cdc63me6j3yvq9gf2gpnf0lvujc5485xgdpj4t6sequg6ap5jn8fdsc7a9k44zhmwcuefve', 'num': 3},
{'seed': 'cdb9e5b2c0a8b4a9328643da2d1f7e98e85e91df123381b9d9f6995824e995f6', 'pk': 'secret-extended-key-main1qdhux892qsqqpqy33eu26jp034dzr6zqqjdd5tuwxg2nnd90e3tl3dv49medx8d9qcxyxlj9l7qca4hzr92fel6ey9g4jn3pp45qmdqa6vav59emntrshc8d3rmdulvw8l7ghwn3wsfvkpaxstshkqeekeqzvg7883tccqszazt7ud2v8dhchp8xgt2qafm0cumdp35esmam6g98a2pesjxu5kce9804kcy4tm39rfym20s3np4jus52m590g43y8qkyyzk3256m4pcz4jyqs', 'addr': 'zs1hz6c6yphshzregyzsjpj34mr9j3w8e83uxxdpd0l6r6875lqjmqqa6a0sdl7amffnln9xpc9qs4', 'num': 4},
{'seed': '7c3b8bae579cead2910c824bb04c6df8933af611a19ee2f710c77f28e2963700', 'pk': 'secret-extended-key-main1qdgs4hwhqqqqpqqegrj88ahwzhp4q5ln4pel8xy8rplktkcpsrz9gw067vxtv32eht2fjfc9l7qg9e2qxy52g8erupkkt9n5zmctj8cekvzrdet7pggsyjd42mnuy43u708345ly3wl2dkuqp3kk8pfpsqu42yz3r78pyxcqtvea9cu7nzeae78ltevlq0hrhxm8lkuk8k8lh5v373gqrj6f0gvxypspvgfqjffud5cj8qwqludywyd44nyyh3jdz0ep8lyudd6ggqq78qawh', 'addr': 'zs1syt3tyygfnmsuc3uq3splkqhp2xraemlvmmlsqvymsscsued5qzr8t4mm2kjnsnrf9d66uf0ydd', 'num': 0},
{'seed': '7c3b8bae579cead2910c824bb04c6df8933af611a19ee2f710c77f28e2963700', 'pk': 'secret-extended-key-main1qdgs4hwhqyqqpqyqjpne3t73ju8scae9gjac89jjgdd7sv3y42x7ceesqc2e333asrg6sewg0cmzylsjykjj3yfg9vlf7vmqdlp3k26qtgtshcqc99dscmylrtygs73jvzlmpra9mw6es0lzck4g6p8kz9vsxm476alclmctzqhc5t2xhjul40tyedsa7za42jgj2qkzrssp9wk8egvwg9emywukk0ywc0jrunr2ge0za0ac0ua2h7lt5m2dpxah8uva9zvuxr7dmjgah77fs', 'addr': 'zs1mmkjcagjqjugtv2evtjsw465xp5myjsw92he9meepnkgultc5tcgdjxhlyn4p4gehq90q6rvz4t', 'num': 1},
{'seed': '7c3b8bae579cead2910c824bb04c6df8933af611a19ee2f710c77f28e2963700', 'pk': 'secret-extended-key-main1qdgs4hwhqgqqpqp7scuqy5ff9gme6x6el233nkne3n2f9mthuam960ghzscafaxxua0wfucxhcwxw42xs7npalklkttp0xrfsvrtezgf3q7qf43uj74qg3atscwlged4f3j46rgz7kn0aefp6narvaq88vh7vms3pd8epvq29dwl9u4kxgm0uwhzcqpfyajyr873x07zepwfwyvdm0kld08jnuxzhrk3g07zjunc7j5fxkxeg3ce07vlwa3g2fmqwjc9h9zx2qan42cu5p7n3', 'addr': 'zs16lealj562c93vfxrxm7vzksht6tm9mygtxc3dmm8epn9ss4yytx7kpcck7akj2wvm09x2uvx8kd', 'num': 2},
{'seed': '7c3b8bae579cead2910c824bb04c6df8933af611a19ee2f710c77f28e2963700', 'pk': 'secret-extended-key-main1qdgs4hwhqvqqpqzynghmn0cm4ucq5s4uy4dp66j66s8j5dtuwccvyczftccw9hx77xgldtqv7dweyt0r7m2anfzamec73rz6l08g5dq97n6ejlvx4p5qndpzs8ac2lwv60l9pq3s4ar4s3hg7a2c64qjjz5fuwccxnl72mqwd5a5hyfnv96rn4xy02k2j52cug8dnsuxxtk2r6hydsrqdr8w2cnxf4sf0z8e4f44xqr7p06k6ru47ygdau4kxdu9cqkk0qr4lr9z78sa4rjxx', 'addr': 'zs13l6pqgre37f906hrlgwk4nsu8y3r6r00m7kcxzv4lx9ym5atnvy6d20sjrfa8zzlsev9zpjv67j', 'num': 3},
{'seed': '7c3b8bae579cead2910c824bb04c6df8933af611a19ee2f710c77f28e2963700', 'pk': 'secret-extended-key-main1qdgs4hwhqsqqpqy43ehawjk98p8wnk4lnrm30efsgxa0x3ydue2fjuqglq5ye8ks3a0qp32xzatv2uus8zf7s052d3dpk06ltqg44gzu6the0663nraq6lhwnd4h95mc2mtjaxwdfcqg5fx76lwtn6mmsqrzv3ul6w46wwqd9c42zs3fx38a3ljgq8zjmpehpkz52khlf5x8y08zqm384cul50fvx6wns3ax35k2cf2dlusyq0ygm6fkkjnesh54eexu2gdulnlx6xg6dr86g', 'addr': 'zs13ypjnkhtvasl3m090vrmj7q4ppzj3u6mf2y7k8ec2n24zxs93j96azpuc8p9ta52986jj6h9rzs', 'num': 4},
{'seed': '1bee4759afdb6bbd70a714f0377c38bb2e1ff3e980602cb86035fae0cb11a9b1', 'pk': 'secret-extended-key-main1qwq3kpvvqqqqpqx33c2pjt2yaecqkex4qv0vpxrr0nkxm2tsql4kmfz4l2mfue65h0jvtx3ljh3jtaeuja76gx2p5szjnqh0ay7fvf7psg2s3qtufkvsr03mujwsdfer84uupkcak0s58ku0u0c0saxnvvfeqn29j4jfzgs8hxazs5hgk33l6xwwcfkhgzm7n8ffsgjdwr9uv23zzfsqvlksdhkdr8r08n6sr3fn67gm3zzqlgfgv2xa36w9re78ram3nq4zqgsl84qgh8uuk', 'addr': 'zs1h8pd53pavs5nuyr7jf4d32e33l5armzqymlkx5yjadtfyqvsjdf00sjx3mrj35aegjcgq65dc30', 'num': 0},
{'seed': '1bee4759afdb6bbd70a714f0377c38bb2e1ff3e980602cb86035fae0cb11a9b1', 'pk': 'secret-extended-key-main1qwq3kpvvqyqqpqp248mkuqf7qphvj5u2ysy454rhhcxthujvywdu2x5qp966q7s4fg270reuer248wjmk7pgm09djdr6468szvhehzfv7rntc55wjpusr2kvtfp39zrawfrjvd9a829l4upxcawnlejadsat9p9mcd9kq4qgreyku83vynzew468lmtfzxx5kyfzll6gv5x0mslqwsqh5vm86xm9r2e6nulwk6xmu8t6cu4wu4ktz8fjd23g0wlc3sjmuv76mdm3m2g887ymx', 'addr': 'zs18vrzmhqagxmmywpawc5zycl6wn2ns9ucemk0q9e50unp5cs0tg28mjvamjh32ytkdzmn255w2r8', 'num': 1},
{'seed': '1bee4759afdb6bbd70a714f0377c38bb2e1ff3e980602cb86035fae0cb11a9b1', 'pk': 'secret-extended-key-main1qwq3kpvvqgqqpq8ssy9hk7e09ydqjnda83kjt3u453mtwce4lunq09mhd3p8zfxkl2c3h5avws4qq86ytup47n05um84mr79vacq02grefuwchnj05wsh2a0vlp4szhd4u2rjs9uk8w35whcklpr0l66l4h3g6g3khekcegv4tldwvhm0fxjaecr2z8nzxzstgetppl9xw4d9xwnwn86wxdcle4ta397kvycmtaavrzurj5d9lfdg7hffsg0nqxay0nxs006dm300eg8q2s8z', 'addr': 'zs1j26t78cfn6tgn9v3m83nsavgndcwh4drtwqsxlfdse9can6va05yztjl4kf809egnla3c30vxjd', 'num': 2},
{'seed': '1bee4759afdb6bbd70a714f0377c38bb2e1ff3e980602cb86035fae0cb11a9b1', 'pk': 'secret-extended-key-main1qwq3kpvvqvqqpqxfc2r4gt5epjpz92m49judvu43033480n4upkfllkjjke0akfrw6kpe2cxgjs88rztqu87d0d2qzs4mqs8a2d7u0daad7ldujf9u2s4zgujcddy4l58k674d6hmekt0uamvn66n53753xdxjzwehadtwc8fmqsg3dfreedma4qe3q0cnld2zgjnznmlwrpaa8pcrp0rlc27tlx2ats9uhn42zwfdlz8099rg26w5z4eg8ezplpcw5ujkffa3tn39s035jhg', 'addr': 'zs1n05lpclu0apvu09vuwk47mjwdqjxk9k4fmw7xn5td3lw8fj4jtvylecdw8sx8rkwq9vxj43dwrs', 'num': 3},
{'seed': '1bee4759afdb6bbd70a714f0377c38bb2e1ff3e980602cb86035fae0cb11a9b1', 'pk': 'secret-extended-key-main1qwq3kpvvqsqqpq9ess7a9cqy37kftvhau4e5lhzlf2598ar4rqc64svj05q3x7ylcc3qu5suy0r6x70a7ezcyamg5dxldqhl8d7agc6tpfrygtpty26qjwjkf5kyyzjak08hgkyn08ej4yvjctuqzh47gsqt3argv5hswqg2pggux48qvflezft52t4rtljrm8yaugadfpda6xkquwl9jnznrafx2k5q57kcauz85jz23d29pu2rl9uhz530gzawwkp52up5x8jyruqqek0qm', 'addr': 'zs1g9k6sah06ggmdzwnjn63j5ugvjpztx2efkt38k8x60yaqqv4a2szlyx6nk6587tukjs6jlud0j6', 'num': 4},
{'seed': '23a28d3ce99495f9e7449a1d222d9daaba3a575fd1ad13b551cf1e07e120fa9b', 'pk': 'secret-extended-key-main1qv5d2fvjqqqqpqr63s8ny5pffjh6j9yfzr92sprtm2y7xka0n83lmcfrztkpdx3yyqzgrwp65s6xz2qzchpq7wjp6genypzmy32rkfq3g35v38fmkcsq9ple4xkmwu04y03d59mje2rh444e83yglxvuw5tpeh0wh2qkz8czxh96qcummhtd4fedcuy6kku6e9zaswchf7wunrs9p3esaea2l65g3tnpy83qp2p30ypzwqczwzldpl3cxw8z7ff78ualhtv2df56f3s6x9gr9', 'addr': 'zs1vzhexn5ts97qqwlalcyd2dgwrgvd0554fwgkp6wxecp5t7q4heldrkqwvxj0x3ethcnn76cg97s', 'num': 0},
{'seed': '23a28d3ce99495f9e7449a1d222d9daaba3a575fd1ad13b551cf1e07e120fa9b', 'pk': 'secret-extended-key-main1qv5d2fvjqyqqpqzl9vv0vq0n85mpwlkupjcpltpr7m3lttsn5tzmzlt8wgpmgf58kzruxrpt87xfhq90fsqc96dxnus9ex89kffhh94ptxnur643k2tq0986j954may8wngttavyft3mvlv6x4pkk75tm5hcv7f4l2zwnusqgdwcvwmch6kacnppkftjdtust6udn424m2aum3lc8u8sakfqg2eq4k0fcr4jgmt888wc6e27pld0dsn6kwm9xjevtvpf2zactpssucc35kk9g', 'addr': 'zs1rq3l8yn3t0t5k5qyfhq93qzcltgc2y47phr63la45kae6assfehlawd7g0hc2ek6dz5mc2vd9pz', 'num': 1},
{'seed': '23a28d3ce99495f9e7449a1d222d9daaba3a575fd1ad13b551cf1e07e120fa9b', 'pk': 'secret-extended-key-main1qv5d2fvjqgqqpqyddrj9zwzunfnxlzuap3cq7rl0exfxlqjjq5e0y0fxyzffttuzxfyp2ck89d4jlqrq7fuh444mpj43jsm500azvdw38reswxmgz34q2dfupcez67hqjhdshkk6hg0uhpcg2m5j5ls683rstzuz8tmq7gg8y4e64mdrpnzmvx0reraxvysaajv2ll8h72s66tuu3x68yqxdahw38fl74kfumr7hz9pp5p3q554c2ggykvzmstrvdxn8cd42zyht2dgkx3pzk', 'addr': 'zs1u4dlwn0neqjx9j8hyug6pewgs3xggwqtqkxlux8zpmhsg3r2dl6yyzna8tlvrcfw2hw95yh3thd', 'num': 2},
{'seed': '23a28d3ce99495f9e7449a1d222d9daaba3a575fd1ad13b551cf1e07e120fa9b', 'pk': 'secret-extended-key-main1qv5d2fvjqvqqpqyjks5nc2eywz2kuzdgu6ksz5tyn2xq5va45el7xpekh4njxkau69r2vknmgpe447h37tynl4wy4pp4w38cdlc96cl3chcrj34c94pq2u3wp98pvtjzwrcypc380jw5qjzycptmcsmj8fdmsmmr7gtw4dqgcnnzmh8ll56q90rmz5h9wy3x5kl8nehle5nqf49umdaj7xt6nvzc6hdhvq2ysxx2hmpxaactlwnth49tyh8pj3ddhgajvdr368xy6mctmyfrt', 'addr': 'zs1kghrl030ja0gfc09txu0lqt7zpex7wdztjvszgckmc7d7dhx0etsa2twt8rp6hzd72vr6rga042', 'num': 3},
{'seed': '23a28d3ce99495f9e7449a1d222d9daaba3a575fd1ad13b551cf1e07e120fa9b', 'pk': 'secret-extended-key-main1qv5d2fvjqsqqpqy2zte8rwadsnknwl5m4uwtq9t66fuah87hrr73q56cyvtn0xt8hkvu2utshgmf3e3gxvf0khvpl84qpuvz46lmhe3xjhkr7pgx5jwqwt8lj4y6l3vrzprew3ukd0zpa0uxh8phvpld759hh9320ussj0gvh53r2zlayedjzyclr2c7dvgptvse5e9d53kp0gt73vg7773w345zqcrskrd6w9htz9ejj9fchzu35ex6zpsxqge4fe4eekndaagx5lslyts2m', 'addr': 'zs1ksryksvndjmvtchkzg8q2j9ya4hh20ymrl9n3k4l55hggs34sxtc9a2xz8gzp57eg47vusln3gs', 'num': 4}
]";
test_address_derivation(&testdata, false);
}
}
}

61
lib/src/pdf.rs

@ -15,8 +15,8 @@ use printpdf::*;
/**
* Save the list of wallets (address + private keys) to the given PDF file name.
*/
pub fn save_to_pdf(is_testnet: bool, addresses: &str, filename: &str) -> Result<(), String> {
let (doc, page1, layer1) = PdfDocument::new("Zec Sapling Paper Wallet", Mm(210.0), Mm(297.0), "Layer 1");
pub fn save_to_pdf(addresses: &str, filename: &str) -> Result<(), String> {
let (doc, page1, layer1) = PdfDocument::new("Hush Paper Wallet", Mm(210.0), Mm(297.0), "Layer 1");
let font = doc.add_builtin_font(BuiltinFont::Courier).unwrap();
let font_bold = doc.add_builtin_font(BuiltinFont::CourierBold).unwrap();
@ -28,12 +28,12 @@ pub fn save_to_pdf(is_testnet: bool, addresses: &str, filename: &str) -> Result<
let mut current_layer = doc.get_page(page1).get_layer(layer1);
let total_pages = f64::ceil(keys.len() as f64 / 2.0); // 2 per page
let total_pages = f64::ceil(keys.len() as f64 / 1.0); // 1 per page
let mut current_page = 1;
for kv in keys.members() {
// Add next page when moving to the next position.
if pos >= 2 {
if pos >= 1 {
pos = 0;
current_page = current_page + 1;
@ -44,7 +44,7 @@ pub fn save_to_pdf(is_testnet: bool, addresses: &str, filename: &str) -> Result<
let address = kv["address"].as_str().unwrap();
let pk = kv["private_key"].as_str().unwrap();
let is_taddr = !address.starts_with(&params(is_testnet).zaddress_prefix);
let is_taddr = !address.starts_with(&params().zaddress_prefix);
let (seed, hdpath) = if kv["type"].as_str().unwrap() == "zaddr" && kv.contains("seed") {
(kv["seed"]["HDSeed"].as_str().unwrap(), kv["seed"]["path"].as_str().unwrap())
@ -57,7 +57,15 @@ pub fn save_to_pdf(is_testnet: bool, addresses: &str, filename: &str) -> Result<
add_pk_to_page(&current_layer, &font, &font_bold, pk, address, is_taddr, seed, hdpath, pos);
let line1 = Line {
points: vec![(Point::new(Mm(5.0), Mm(160.0)), false), (Point::new(Mm(205.0), Mm(160.0)), false)],
points: vec![(Point::new(Mm(5.0), Mm(98.0)), false), (Point::new(Mm(205.0), Mm(98.0)), false)],
is_closed: true,
has_fill: false,
has_stroke: true,
is_clipping_path: false,
};
let line2 = Line {
points: vec![(Point::new(Mm(5.0), Mm(198.0)), false), (Point::new(Mm(205.0), Mm(198.0)), false)],
is_closed: true,
has_fill: false,
has_stroke: true,
@ -69,8 +77,13 @@ pub fn save_to_pdf(is_testnet: bool, addresses: &str, filename: &str) -> Result<
current_layer.set_outline_color(outline_color);
current_layer.set_outline_thickness(2.0);
// Draw first line
// Set title
current_layer.use_text("Speak and Transact Freely", 32, Mm(19.0), Mm(277.0), &font_bold);
current_layer.use_text("Private Cryptocurrency and Messenger on Zero Knowledge Proof Encryption", 13, Mm(7.0), Mm(266.0), &font_bold);
// Draw lines
current_layer.add_shape(line1);
current_layer.add_shape(line2);
// Add footer of page, only once for each pair of addresses
if pos == 0 {
@ -142,19 +155,19 @@ fn add_address_to_page(current_layer: &PdfLayerReference, font: &IndirectFontRef
let (scaledimg, finalsize) = qrcode_scaled(address, if is_taddr {13} else {10});
// page_height top_margin vertical_padding position
let ypos = 297.0 - 5.0 - 35.0 - (140.0 * pos as f64);
let title = if is_taddr {"T Address"} else {"ZEC Address (Sapling)"};
let ypos = 297.0 - 5.0 - 77.0 - (140.0 * pos as f64);
let title = if is_taddr {"T Address"} else {"HUSH Address"};
add_address_at(current_layer, font, font_bold, title, address, &scaledimg, finalsize, ypos);
}
fn add_address_at(current_layer: &PdfLayerReference, font: &IndirectFontRef, font_bold: &IndirectFontRef, title: &str, address: &str, qrcode: &Vec<u8>, finalsize: usize, ypos: f64) {
add_qrcode_image_to_page(current_layer, qrcode, finalsize, Mm(10.0), Mm(ypos));
current_layer.use_text(title, 14, Mm(55.0), Mm(ypos+27.5), &font_bold);
current_layer.use_text(title, 14, Mm(55.0), Mm(ypos+22.5), &font_bold);
let strs = split_to_max(&address, 39, 39); // No spaces, so user can copy the address
for i in 0..strs.len() {
current_layer.use_text(strs[i].clone(), 12, Mm(55.0), Mm(ypos+20.0-((i*5) as f64)), &font);
current_layer.use_text(strs[i].clone(), 12, Mm(55.0), Mm(ypos+15.0-((i*5) as f64)), &font);
}
}
@ -163,30 +176,8 @@ fn add_address_at(current_layer: &PdfLayerReference, font: &IndirectFontRef, fon
*/
fn add_pk_to_page(current_layer: &PdfLayerReference, font: &IndirectFontRef, font_bold: &IndirectFontRef, pk: &str, address: &str, is_taddr: bool, seed: &str, path: &str, pos: u32) {
// page_height top_margin vertical_padding position
let ypos = 297.0 - 5.0 - 90.0 - (140.0 * pos as f64);
let ypos = 297.0 - 5.0 - 242.0 - (140.0 * pos as f64);
let line1 = Line {
points: vec![(Point::new(Mm(5.0), Mm(ypos + 50.0)), false), (Point::new(Mm(205.0), Mm(ypos + 50.0)), false)],
is_closed: true,
has_fill: false,
has_stroke: true,
is_clipping_path: false,
};
let outline_color = printpdf::Color::Rgb(Rgb::new(0.0, 0.0, 0.0, None));
current_layer.set_outline_color(outline_color);
let mut dash_pattern = LineDashPattern::default();
dash_pattern.dash_1 = Some(5);
current_layer.set_line_dash_pattern(dash_pattern);
current_layer.set_outline_thickness(1.0);
// Draw first line
current_layer.add_shape(line1);
// Reset the dashed line pattern
current_layer.set_line_dash_pattern(LineDashPattern::default());
let (scaledimg, finalsize) = qrcode_scaled(pk, if is_taddr {20} else {10});
add_qrcode_image_to_page(current_layer, &scaledimg, finalsize, Mm(145.0), Mm(ypos-17.5));
@ -198,7 +189,7 @@ fn add_pk_to_page(current_layer: &PdfLayerReference, font: &IndirectFontRef, fon
}
// Add the address a second time below the private key
let title = if is_taddr {"T Address"} else {"ZEC Address (Sapling)"};
let title = if is_taddr {"T Address"} else {"HUSH Address"};
current_layer.use_text(title, 12, Mm(10.0), Mm(ypos-10.0), &font_bold);
let strs = split_to_max(&address, 39, 39); // No spaces, so user can copy the address
for i in 0..strs.len() {

8
ui/.gitignore

@ -5,10 +5,10 @@ Makefile
Makefile.Debug
Makefile.Release
.qmake.stash
zecpaperwalletui
zecpaperwalletui.app/
zecpaperwalletui_plugin_import.cpp
zecpaperwalletui.pro.user
hushpaperwalletui
hushpaperwalletui.app/
hushpaperwalletui_plugin_import.cpp
hushpaperwalletui.pro.user
.vscode/
ui*.h
*.swp

6
ui/zecpaperwalletui_resource.rc → ui/hushpaperwalletui_resource.rc

@ -1,6 +1,6 @@
#include <windows.h>
IDI_ICON1 ICON DISCARDABLE "/opt/zecpaperwallet/ui/res/icon.ico"
IDI_ICON1 ICON DISCARDABLE "/opt/hushpaperwallet/ui/res/icon.ico"
VS_VERSION_INFO VERSIONINFO
FILEVERSION 0,0,0,0
@ -23,8 +23,8 @@ VS_VERSION_INFO VERSIONINFO
VALUE "FileDescription", "\0"
VALUE "FileVersion", "0.0.0.0\0"
VALUE "LegalCopyright", "\0"
VALUE "OriginalFilename", "zecpaperwalletui.exe\0"
VALUE "ProductName", "zecpaperwalletui\0"
VALUE "OriginalFilename", "hushpaperwalletui.exe\0"
VALUE "ProductName", "hushpaperwalletui\0"
VALUE "ProductVersion", "0.0.0.0\0"
END
END

18
ui/mkdockerwinlinux.sh

@ -29,30 +29,30 @@ if [ -z $APP_VERSION ]; then
exit 1;
fi
cd /opt/zecpaperwallet/ui
cd /opt/hushpaperwallet/ui
source ~/.cargo/env
# We need to run qmake before we run disclean
/opt/Qt/5.11.2/static/bin/qmake papersapling.pro CONFIG+=release
make distclean
rm -rf artifacts/linux-zecpaperwallet-v$APP_VERSION
mkdir -p artifacts/linux-zecpaperwallet-v$APP_VERSION
rm -rf artifacts/linux-hushpaperwallet-v$APP_VERSION
mkdir -p artifacts/linux-hushpaperwallet-v$APP_VERSION
/opt/Qt/5.11.2/static/bin/qmake papersapling.pro CONFIG+=release
make -j4
strip zecpaperwalletui
cp zecpaperwalletui artifacts/linux-zecpaperwallet-v$APP_VERSION
strip hushpaperwalletui
cp hushpaperwalletui artifacts/linux-hushpaperwallet-v$APP_VERSION
# Run qmake before distclean
/opt/mxe/usr/bin/x86_64-w64-mingw32.static-qmake-qt5 papersapling.pro CONFIG+=release
make distclean
rm -rf artifacts/Windows-zecpaperwallet-v$APP_VERSION
mkdir -p artifacts/Windows-zecpaperwallet-v$APP_VERSION
rm -rf artifacts/Windows-hushpaperwallet-v$APP_VERSION
mkdir -p artifacts/Windows-hushpaperwallet-v$APP_VERSION
/opt/mxe/usr/bin/x86_64-w64-mingw32.static-qmake-qt5 papersapling.pro CONFIG+=release
make -j4
strip release/zecpaperwalletui.exe
cp release/zecpaperwalletui.exe artifacts/Windows-zecpaperwallet-v$APP_VERSION
strip release/hushpaperwalletui.exe
cp release/hushpaperwalletui.exe artifacts/Windows-hushpaperwallet-v$APP_VERSION
# Cleanup before exiting
make distclean

76
ui/mkrelease.sh

@ -39,8 +39,8 @@ QT_STATIC=$QT_PATH/clang_64/bin
echo -n "Cleaning..............."
$QT_STATIC/qmake papersapling.pro CONFIG+=release >/dev/null
make distclean >/dev/null 2>&1
rm -rf artifacts/macOS-zecpaperwallet-v$APP_VERSION
mkdir -p artifacts/macOS-zecpaperwallet-v$APP_VERSION
rm -rf artifacts/macOS-hushpaperwallet-v$APP_VERSION
mkdir -p artifacts/macOS-hushpaperwallet-v$APP_VERSION
echo "[OK]"
echo -n "Testing................"
@ -67,12 +67,12 @@ echo "[OK]"
#Qt deploy
echo -n "Deploying.............."
$QT_STATIC/macdeployqt zecpaperwalletui.app
cp -r zecpaperwalletui.app artifacts/macOS-zecpaperwallet-v$APP_VERSION/
$QT_STATIC/macdeployqt hushpaperwalletui.app
cp -r hushpaperwalletui.app artifacts/macOS-hushpaperwallet-v$APP_VERSION/
echo "[OK]"
# Run inside docker container
docker run --rm -v ${PWD}/..:/opt/zecpaperwallet zecwallet/compileenv:v0.8 bash -c "cd /opt/zecpaperwallet/ui && ./mkdockerwinlinux.sh -v $APP_VERSION"
docker run --rm -v ${PWD}/..:/opt/hushpaperwallet hushwallet/compileenv:v0.8 bash -c "cd /opt/hushpaperwallet/ui && ./mkdockerwinlinux.sh -v $APP_VERSION"
# Move to build the cli
cd ../cli
@ -83,10 +83,10 @@ echo "pub fn version() -> &'static str { &\"$APP_VERSION\" }" > src/version.rs
# Compile for mac directly and copy it over
cargo build --release
cp target/release/zecpaperwallet ../ui/artifacts/macOS-zecpaperwallet-v$APP_VERSION/
cp target/release/hushpaperwallet ../ui/artifacts/macOS-hushpaperwallet-v$APP_VERSION/
# For Windows and Linux, build via docker
docker run --rm -v $(pwd)/..:/opt/zecpaperwallet rust/zecpaperwallet:v0.3 bash -c "cd /opt/zecpaperwallet/cli && cargo build --release && cargo build --release --target x86_64-pc-windows-gnu && cargo build --release --target aarch64-unknown-linux-gnu && cargo build --release --target armv7-unknown-linux-gnueabihf"
docker run --rm -v $(pwd)/..:/opt/hushpaperwallet rust/hushpaperwallet:v0.3 bash -c "cd /opt/hushpaperwallet/cli && cargo build --release && cargo build --release --target x86_64-pc-windows-gnu && cargo build --release --target aarch64-unknown-linux-gnu && cargo build --release --target armv7-unknown-linux-gnueabihf"
# Come back and package everything
cd ../ui
@ -94,62 +94,62 @@ cd ../ui
# Now sign and zip the binaries
#macOS
# binary is already copied above
gpg --batch --output artifacts/macOS-zecpaperwallet-v$APP_VERSION/zecpaperwallet.sig --detach-sig artifacts/macOS-zecpaperwallet-v$APP_VERSION/zecpaperwallet
#gpg --batch --output artifacts/macOS-zecpaperwallet-v$APP_VERSION/zecpaperwallet.app.sig --detach-sig artifacts/macOS-zecpaperwallet-v$APP_VERSION/zecpaperwallet.app
gpg --batch --output artifacts/macOS-hushpaperwallet-v$APP_VERSION/hushpaperwallet.sig --detach-sig artifacts/macOS-hushpaperwallet-v$APP_VERSION/hushpaperwallet
#gpg --batch --output artifacts/macOS-hushpaperwallet-v$APP_VERSION/hushpaperwallet.app.sig --detach-sig artifacts/macOS-hushpaperwallet-v$APP_VERSION/hushpaperwallet.app
cd artifacts
cd macOS-zecpaperwallet-v$APP_VERSION
gsha256sum zecpaperwallet > sha256sum.txt
cd macOS-hushpaperwallet-v$APP_VERSION
gsha256sum hushpaperwallet > sha256sum.txt
cd ..
zip -r macOS-zecpaperwallet-v$APP_VERSION.zip macOS-zecpaperwallet-v$APP_VERSION
zip -r macOS-hushpaperwallet-v$APP_VERSION.zip macOS-hushpaperwallet-v$APP_VERSION
cd ..
#Linux
cp ../cli/target/release/zecpaperwallet artifacts/linux-zecpaperwallet-v$APP_VERSION/
gpg --batch --output artifacts/linux-zecpaperwallet-v$APP_VERSION/zecpaperwallet.sig --detach-sig artifacts/linux-zecpaperwallet-v$APP_VERSION/zecpaperwallet
gpg --batch --output artifacts/linux-zecpaperwallet-v$APP_VERSION/zecpaperwalletui.sig --detach-sig artifacts/linux-zecpaperwallet-v$APP_VERSION/zecpaperwalletui
cp ../cli/target/release/hushpaperwallet artifacts/linux-hushpaperwallet-v$APP_VERSION/
gpg --batch --output artifacts/linux-hushpaperwallet-v$APP_VERSION/hushpaperwallet.sig --detach-sig artifacts/linux-hushpaperwallet-v$APP_VERSION/hushpaperwallet
gpg --batch --output artifacts/linux-hushpaperwallet-v$APP_VERSION/hushpaperwalletui.sig --detach-sig artifacts/linux-hushpaperwallet-v$APP_VERSION/hushpaperwalletui
cd artifacts
cd linux-zecpaperwallet-v$APP_VERSION
gsha256sum zecpaperwallet zecpaperwalletui > sha256sum.txt
cd linux-hushpaperwallet-v$APP_VERSION
gsha256sum hushpaperwallet hushpaperwalletui > sha256sum.txt
cd ..
zip -r linux-zecpaperwallet-v$APP_VERSION.zip linux-zecpaperwallet-v$APP_VERSION
zip -r linux-hushpaperwallet-v$APP_VERSION.zip linux-hushpaperwallet-v$APP_VERSION
cd ..
#Windows
cp ../cli/target/x86_64-pc-windows-gnu/release/zecpaperwallet.exe artifacts/Windows-zecpaperwallet-v$APP_VERSION/
gpg --batch --output artifacts/Windows-zecpaperwallet-v$APP_VERSION/zecpaperwallet.sig --detach-sig artifacts/Windows-zecpaperwallet-v$APP_VERSION/zecpaperwallet.exe
gpg --batch --output artifacts/Windows-zecpaperwallet-v$APP_VERSION/zecpaperwalletui.sig --detach-sig artifacts/Windows-zecpaperwallet-v$APP_VERSION/zecpaperwalletui.exe
cp ../cli/target/x86_64-pc-windows-gnu/release/hushpaperwallet.exe artifacts/Windows-hushpaperwallet-v$APP_VERSION/
gpg --batch --output artifacts/Windows-hushpaperwallet-v$APP_VERSION/hushpaperwallet.sig --detach-sig artifacts/Windows-hushpaperwallet-v$APP_VERSION/hushpaperwallet.exe
gpg --batch --output artifacts/Windows-hushpaperwallet-v$APP_VERSION/hushpaperwalletui.sig --detach-sig artifacts/Windows-hushpaperwallet-v$APP_VERSION/hushpaperwalletui.exe
cd artifacts
cd Windows-zecpaperwallet-v$APP_VERSION
gsha256sum zecpaperwallet.exe zecpaperwalletui.exe > sha256sum.txt
cd Windows-hushpaperwallet-v$APP_VERSION
gsha256sum hushpaperwallet.exe hushpaperwalletui.exe > sha256sum.txt
cd ..
zip -r Windows-zecpaperwallet-v$APP_VERSION.zip Windows-zecpaperwallet-v$APP_VERSION
zip -r Windows-hushpaperwallet-v$APP_VERSION.zip Windows-hushpaperwallet-v$APP_VERSION
cd ..
# aarch64 (armv8)
rm -rf artifacts/aarch64-zecpaperwallet-v$APP_VERSION
mkdir -p artifacts/aarch64-zecpaperwallet-v$APP_VERSION
cp ../cli/target/aarch64-unknown-linux-gnu/release/zecpaperwallet artifacts/aarch64-zecpaperwallet-v$APP_VERSION/
gpg --batch --output artifacts/aarch64-zecpaperwallet-v$APP_VERSION/zecpaperwallet.sig --detach-sig artifacts/aarch64-zecpaperwallet-v$APP_VERSION/zecpaperwallet
rm -rf artifacts/aarch64-hushpaperwallet-v$APP_VERSION
mkdir -p artifacts/aarch64-hushpaperwallet-v$APP_VERSION
cp ../cli/target/aarch64-unknown-linux-gnu/release/hushpaperwallet artifacts/aarch64-hushpaperwallet-v$APP_VERSION/
gpg --batch --output artifacts/aarch64-hushpaperwallet-v$APP_VERSION/hushpaperwallet.sig --detach-sig artifacts/aarch64-hushpaperwallet-v$APP_VERSION/hushpaperwallet
cd artifacts
cd aarch64-zecpaperwallet-v$APP_VERSION
gsha256sum zecpaperwallet > sha256sum.txt
cd aarch64-hushpaperwallet-v$APP_VERSION
gsha256sum hushpaperwallet > sha256sum.txt
cd ..
zip -r aarch64-zecpaperwallet-v$APP_VERSION.zip aarch64-zecpaperwallet-v$APP_VERSION
zip -r aarch64-hushpaperwallet-v$APP_VERSION.zip aarch64-hushpaperwallet-v$APP_VERSION
cd ..
# ARMv7
rm -rf artifacts/armv7-zecpaperwallet-v$APP_VERSION
mkdir -p artifacts/armv7-zecpaperwallet-v$APP_VERSION
cp ../cli/target/armv7-unknown-linux-gnueabihf/release/zecpaperwallet artifacts/armv7-zecpaperwallet-v$APP_VERSION/
gpg --batch --output artifacts/armv7-zecpaperwallet-v$APP_VERSION/zecpaperwallet.sig --detach-sig artifacts/armv7-zecpaperwallet-v$APP_VERSION/zecpaperwallet
rm -rf artifacts/armv7-hushpaperwallet-v$APP_VERSION
mkdir -p artifacts/armv7-hushpaperwallet-v$APP_VERSION
cp ../cli/target/armv7-unknown-linux-gnueabihf/release/hushpaperwallet artifacts/armv7-hushpaperwallet-v$APP_VERSION/
gpg --batch --output artifacts/armv7-hushpaperwallet-v$APP_VERSION/hushpaperwallet.sig --detach-sig artifacts/armv7-hushpaperwallet-v$APP_VERSION/hushpaperwallet
cd artifacts
cd armv7-zecpaperwallet-v$APP_VERSION
gsha256sum zecpaperwallet > sha256sum.txt
cd armv7-hushpaperwallet-v$APP_VERSION
gsha256sum hushpaperwallet > sha256sum.txt
cd ..
zip -r armv7-zecpaperwallet-v$APP_VERSION.zip armv7-zecpaperwallet-v$APP_VERSION
zip -r armv7-hushpaperwallet-v$APP_VERSION.zip armv7-hushpaperwallet-v$APP_VERSION
cd ..

20
ui/papersapling.pro

@ -8,7 +8,7 @@ QT += core gui
greaterThan(QT_MAJOR_VERSION, 4): QT += widgets
TARGET = zecpaperwalletui
TARGET = hushpaperwalletui
TEMPLATE = app
MOC_DIR = bin
@ -50,7 +50,7 @@ HEADERS += \
src/qrcode/QrCode.hpp \
src/qrcode/QrSegment.hpp \
src/version.h \
qtlib/src/zecpaperrust.h
qtlib/src/hushpaperrust.h
FORMS += \
@ -69,8 +69,8 @@ mac: LIBS+= -Wl,-bind_at_load
win32: RC_ICONS = res/icon.ico
ICON = res/logo.icns
unix: librust.target = $$PWD/qtlib/target/release/libzecpaperrust.a
else:win32: librust.target = $$PWD/qtlib/target/x86_64-pc-windows-gnu/release/zecpaperrust.lib
unix: librust.target = $$PWD/qtlib/target/release/libhushpaperrust.a
else:win32: librust.target = $$PWD/qtlib/target/x86_64-pc-windows-gnu/release/hushpaperrust.lib
unix: librust.commands = $(MAKE) -C $$PWD/qtlib
else:win32: librust.commands = $(MAKE) -C $$PWD/qtlib winrelease
@ -81,7 +81,7 @@ distclean.depends += librustclean
QMAKE_INFO_PLIST = res/Info.plist
QMAKE_EXTRA_TARGETS += librust librustclean distclean
QMAKE_CLEAN += $$PWD/qtlib/target/release/libzecpaperrust.a
QMAKE_CLEAN += $$PWD/qtlib/target/release/libhushpaperrust.a
# Default rules for deployment.
qnx: target.path = /tmp/$${TARGET}/bin
@ -89,9 +89,9 @@ else: unix:!android: target.path = /opt/$${TARGET}/bin
!isEmpty(target.path): INSTALLS += target
win32: LIBS += -L$$PWD/qtlib/target/x86_64-pc-windows-gnu/release -lzecpaperrust
else:macx: LIBS += -L$$PWD/qtlib/target/release -lzecpaperrust -framework Security -framework Foundation
else:unix: LIBS += -L$$PWD/qtlib/target/release -lzecpaperrust -ldl
win32: LIBS += -L$$PWD/qtlib/target/x86_64-pc-windows-gnu/release -lhushpaperrust
else:macx: LIBS += -L$$PWD/qtlib/target/release -lhushpaperrust -framework Security -framework Foundation
else:unix: LIBS += -L$$PWD/qtlib/target/release -lhushpaperrust -ldl
win32: PRE_TARGETDEPS += $$PWD/qtlib/target/x86_64-pc-windows-gnu/release/zecpaperrust.lib
else:unix::PRE_TARGETDEPS += $$PWD/qtlib/target/release/libzecpaperrust.a
win32: PRE_TARGETDEPS += $$PWD/qtlib/target/x86_64-pc-windows-gnu/release/hushpaperrust.lib
else:unix::PRE_TARGETDEPS += $$PWD/qtlib/target/release/libhushpaperrust.a

4
ui/qtlib/Cargo.toml

@ -5,9 +5,9 @@ authors = ["ZecWallet"]
edition = "2018"
[lib]
name = "zecpaperrust"
name = "hushpaperrust"
crate-type = ["staticlib"]
[dependencies]
libc = "0.2.58"
zecpaperlib = { path = "../../lib" }
hushpaperlib = { path = "../../lib" }

4
ui/qtlib/src/zecpaperrust.h → ui/qtlib/src/hushpaperrust.h

@ -1,5 +1,5 @@
#ifndef _ZEC_PAPER_RUST_H
#define _ZEC_PAPER_RUST_H
#ifndef _HUSH_PAPER_RUST_H
#define _HUSH_PAPER_RUST_H
#ifdef __cplusplus
extern "C"{

2
ui/qtlib/src/lib.rs

@ -1,6 +1,6 @@
use libc::{c_char};
use std::ffi::{CStr, CString};
use zecpaperlib::{pdf, paper};
use hushpaperlib::{pdf, paper};
/**
* Call into rust to generate a paper wallet. Returns the paper wallet in JSON form.

4
ui/res/Info.plist

@ -3,13 +3,13 @@
<plist version="1.0">
<dict>
<key>CFBundleExecutable</key>
<string>zecpaperwalletui</string>
<string>hushpaperwalletui</string>
<key>CFBundleGetInfoString</key>
<string>Created by Qt/QMake</string>
<key>CFBundleIconFile</key>
<string>logo.icns</string>
<key>CFBundleIdentifier</key>
<string>co.zecwallet.paper</string>
<string>co.hushwallet.paper</string>
<key>CFBundlePackageType</key>
<string>APPL</string>
<key>CFBundleSignature</key>

6
ui/src/about.ui

@ -11,7 +11,7 @@
</rect>
</property>
<property name="windowTitle">
<string>About zecpaperwallet</string>
<string>About hushpaperwallet</string>
</property>
<layout class="QGridLayout" name="gridLayout">
<item row="2" column="0">
@ -59,13 +59,13 @@
<item row="0" column="0">
<widget class="QGroupBox" name="groupBox">
<property name="title">
<string>zecpaperwallet</string>
<string>hushpaperwallet</string>
</property>
<layout class="QHBoxLayout" name="horizontalLayout">
<item>
<widget class="QLabel" name="lblVersion">
<property name="text">
<string>zecpaperwallet version 1.0(6 May 2009)</string>
<string>hushpaperwallet version 1.0(6 May 2009)</string>
</property>
</widget>
</item>

6
ui/src/main.cpp

@ -7,8 +7,8 @@ int main(int argc, char *argv[])
QCoreApplication::setAttribute(Qt::AA_UseHighDpiPixmaps);
QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling);
QCoreApplication::setOrganizationDomain("zecwallet.co");
QCoreApplication::setOrganizationName("zecpaperwallet");
QCoreApplication::setOrganizationDomain("hushwallet.co");
QCoreApplication::setOrganizationName("hushpaperwallet");
#ifdef Q_OS_LINUX
QFontDatabase::addApplicationFont(":/fonts/res/Ubuntu-R.ttf");
@ -18,7 +18,7 @@ int main(int argc, char *argv[])
QApplication a(argc, argv);
MainWindow w;
w.setWindowTitle(QString("zecpaperwallet ") + APP_VERSION);
w.setWindowTitle(QString("hushpaperwallet ") + APP_VERSION);
w.show();

6
ui/src/mainwindow.cpp

@ -8,7 +8,7 @@
#include "ui_wallet.h"
#include "ui_about.h"
#include "zecpaperrust.h"
#include "hushpaperrust.h"
void SaveRestore(QDialog* d) {
d->restoreGeometry(QSettings().value(d->objectName() % "geometry").toByteArray());
@ -172,7 +172,7 @@ MainWindow::MainWindow(QWidget *parent) :
// Help site
QObject::connect(ui->actionHelp_site, &QAction::triggered, [=]() {
QDesktopServices::openUrl(QUrl("https://docs.zecwallet.co/paper"));
QDesktopServices::openUrl(QUrl("https://docs.hushwallet.co/paper"));
});
// About button
@ -180,7 +180,7 @@ MainWindow::MainWindow(QWidget *parent) :
QDialog ad(this);
Ui_AboutDialog d;
d.setupUi(&ad);
d.lblVersion->setText(QString("zecpaperwallet ") + APP_VERSION + "(" + APP_BUILD_DATE + ")");
d.lblVersion->setText(QString("hushpaperwallet ") + APP_VERSION + "(" + APP_BUILD_DATE + ")");
SaveRestore(&ad);
ad.exec();

2
ui/src/mainwindow.ui

@ -11,7 +11,7 @@
</rect>
</property>
<property name="windowTitle">
<string>Zec Sapling Paper Wallet</string>
<string>Hush Paper Wallet</string>
</property>
<widget class="QWidget" name="centralWidget">
<layout class="QGridLayout" name="gridLayout">

2
web/.gitignore

@ -1,2 +0,0 @@
target/

36
web/Cargo.toml

@ -1,36 +0,0 @@
[package]
name = "zecpaperwallet"
version = "0.1.0"
authors = ["Aditya Kulkarni <adityapk@gmail.com>"]
edition = "2018"
[lib]
crate-type = ["cdylib", "rlib"]
[features]
default = ["console_error_panic_hook"]
[dependencies]
sha2 = "0.8.0"
wasm-bindgen = "0.2"
zecpaperlib = { path = "../lib", default-features = false }
# The `console_error_panic_hook` crate provides better debugging of panics by
# logging them with `console.error`. This is great for development, but requires
# all the `std::fmt` and `std::panicking` infrastructure, so isn't great for
# code size when deploying.
console_error_panic_hook = { version = "0.1.1", optional = true }
# `wee_alloc` is a tiny allocator for wasm that is only ~1K in code size
# compared to the default allocator's ~10K. It is slower than the default
# allocator, however.
#
# Unfortunately, `wee_alloc` requires nightly Rust when targeting wasm for now.
wee_alloc = { version = "0.4.2", optional = true }
[dev-dependencies]
wasm-bindgen-test = "0.2"
[profile.release]
# Tell `rustc` to optimize for small code size.
opt-level = "s"

176
web/LICENSE_APACHE

@ -1,176 +0,0 @@
Apache License
Version 2.0, January 2004
http://www.apache.org/licenses/
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
1. Definitions.
"License" shall mean the terms and conditions for use, reproduction,
and distribution as defined by Sections 1 through 9 of this document.
"Licensor" shall mean the copyright owner or entity authorized by
the copyright owner that is granting the License.
"Legal Entity" shall mean the union of the acting entity and all
other entities that control, are controlled by, or are under common
control with that entity. For the purposes of this definition,
"control" means (i) the power, direct or indirect, to cause the
direction or management of such entity, whether by contract or
otherwise, or (ii) ownership of fifty percent (50%) or more of the
outstanding shares, or (iii) beneficial ownership of such entity.
"You" (or "Your") shall mean an individual or Legal Entity
exercising permissions granted by this License.
"Source" form shall mean the preferred form for making modifications,
including but not limited to software source code, documentation
source, and configuration files.
"Object" form shall mean any form resulting from mechanical
transformation or translation of a Source form, including but
not limited to compiled object code, generated documentation,
and conversions to other media types.
"Work" shall mean the work of authorship, whether in Source or
Object form, made available under the License, as indicated by a
copyright notice that is included in or attached to the work
(an example is provided in the Appendix below).
"Derivative Works" shall mean any work, whether in Source or Object
form, that is based on (or derived from) the Work and for which the
editorial revisions, annotations, elaborations, or other modifications
represent, as a whole, an original work of authorship. For the purposes
of this License, Derivative Works shall not include works that remain
separable from, or merely link (or bind by name) to the interfaces of,
the Work and Derivative Works thereof.
"Contribution" shall mean any work of authorship, including
the original version of the Work and any modifications or additions
to that Work or Derivative Works thereof, that is intentionally
submitted to Licensor for inclusion in the Work by the copyright owner
or by an individual or Legal Entity authorized to submit on behalf of
the copyright owner. For the purposes of this definition, "submitted"
means any form of electronic, verbal, or written communication sent
to the Licensor or its representatives, including but not limited to
communication on electronic mailing lists, source code control systems,
and issue tracking systems that are managed by, or on behalf of, the
Licensor for the purpose of discussing and improving the Work, but
excluding communication that is conspicuously marked or otherwise
designated in writing by the copyright owner as "Not a Contribution."
"Contributor" shall mean Licensor and any individual or Legal Entity
on behalf of whom a Contribution has been received by Licensor and
subsequently incorporated within the Work.
2. Grant of Copyright License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
copyright license to reproduce, prepare Derivative Works of,
publicly display, publicly perform, sublicense, and distribute the
Work and such Derivative Works in Source or Object form.
3. Grant of Patent License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
(except as stated in this section) patent license to make, have made,
use, offer to sell, sell, import, and otherwise transfer the Work,
where such license applies only to those patent claims licensable
by such Contributor that are necessarily infringed by their
Contribution(s) alone or by combination of their Contribution(s)
with the Work to which such Contribution(s) was submitted. If You
institute patent litigation against any entity (including a
cross-claim or counterclaim in a lawsuit) alleging that the Work
or a Contribution incorporated within the Work constitutes direct
or contributory patent infringement, then any patent licenses
granted to You under this License for that Work shall terminate
as of the date such litigation is filed.
4. Redistribution. You may reproduce and distribute copies of the
Work or Derivative Works thereof in any medium, with or without
modifications, and in Source or Object form, provided that You
meet the following conditions:
(a) You must give any other recipients of the Work or
Derivative Works a copy of this License; and
(b) You must cause any modified files to carry prominent notices
stating that You changed the files; and
(c) You must retain, in the Source form of any Derivative Works
that You distribute, all copyright, patent, trademark, and
attribution notices from the Source form of the Work,
excluding those notices that do not pertain to any part of
the Derivative Works; and
(d) If the Work includes a "NOTICE" text file as part of its
distribution, then any Derivative Works that You distribute must
include a readable copy of the attribution notices contained
within such NOTICE file, excluding those notices that do not
pertain to any part of the Derivative Works, in at least one
of the following places: within a NOTICE text file distributed
as part of the Derivative Works; within the Source form or
documentation, if provided along with the Derivative Works; or,
within a display generated by the Derivative Works, if and
wherever such third-party notices normally appear. The contents
of the NOTICE file are for informational purposes only and
do not modify the License. You may add Your own attribution
notices within Derivative Works that You distribute, alongside
or as an addendum to the NOTICE text from the Work, provided
that such additional attribution notices cannot be construed
as modifying the License.
You may add Your own copyright statement to Your modifications and
may provide additional or different license terms and conditions
for use, reproduction, or distribution of Your modifications, or
for any such Derivative Works as a whole, provided Your use,
reproduction, and distribution of the Work otherwise complies with
the conditions stated in this License.
5. Submission of Contributions. Unless You explicitly state otherwise,
any Contribution intentionally submitted for inclusion in the Work
by You to the Licensor shall be under the terms and conditions of
this License, without any additional terms or conditions.
Notwithstanding the above, nothing herein shall supersede or modify
the terms of any separate license agreement you may have executed
with Licensor regarding such Contributions.
6. Trademarks. This License does not grant permission to use the trade
names, trademarks, service marks, or product names of the Licensor,
except as required for reasonable and customary use in describing the
origin of the Work and reproducing the content of the NOTICE file.
7. Disclaimer of Warranty. Unless required by applicable law or
agreed to in writing, Licensor provides the Work (and each
Contributor provides its Contributions) on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
implied, including, without limitation, any warranties or conditions
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
PARTICULAR PURPOSE. You are solely responsible for determining the
appropriateness of using or redistributing the Work and assume any
risks associated with Your exercise of permissions under this License.
8. Limitation of Liability. In no event and under no legal theory,
whether in tort (including negligence), contract, or otherwise,
unless required by applicable law (such as deliberate and grossly
negligent acts) or agreed to in writing, shall any Contributor be
liable to You for damages, including any direct, indirect, special,
incidental, or consequential damages of any character arising as a
result of this License or out of the use or inability to use the
Work (including but not limited to damages for loss of goodwill,
work stoppage, computer failure or malfunction, or any and all
other commercial damages or losses), even if such Contributor
has been advised of the possibility of such damages.
9. Accepting Warranty or Additional Liability. While redistributing
the Work or Derivative Works thereof, You may choose to offer,
and charge a fee for, acceptance of support, warranty, indemnity,
or other liability obligations and/or rights consistent with this
License. However, in accepting such obligations, You may act only
on Your own behalf and on Your sole responsibility, not on behalf
of any other Contributor, and only if You agree to indemnify,
defend, and hold each Contributor harmless for any liability
incurred by, or claims asserted against, such Contributor by reason
of your accepting any such warranty or additional liability.
END OF TERMS AND CONDITIONS

25
web/LICENSE_MIT

@ -1,25 +0,0 @@
Copyright (c) 2018 Aditya Kulkarni <adityapk@gmail.com>
Permission is hereby granted, free of charge, to any
person obtaining a copy of this software and associated
documentation files (the "Software"), to deal in the
Software without restriction, including without
limitation the rights to use, copy, modify, merge,
publish, distribute, sublicense, and/or sell copies of
the Software, and to permit persons to whom the Software
is furnished to do so, subject to the following
conditions:
The above copyright notice and this permission notice
shall be included in all copies or substantial portions
of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF
ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED
TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT
SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR
IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
DEALINGS IN THE SOFTWARE.

26
web/README.md

@ -1,26 +0,0 @@
## ZecPaperWallet Web
The paper wallet generator [is hosted at paper.zecwallet.co](https://paper.zecwallet.co).
This is a web version of the Zec Sapling Paper Wallet generator. It's mainly for illustrative purposes. If you want to generate a serious offline paper wallet, you should run [zecpaperwallet](https://github.com/adityapk00/zecpaperwallet) offline.
## Installing wasm-pack
You can run the web wallet locally. You need to install the following first:
1. [Rust 1.32+](https://www.rust-lang.org/tools/install)
2. [nodejs / npm](https://www.npmjs.com/get-npm)
3. wasm-pack
```
cargo install wasm-pack
```
### Running locally
You can run the web wallet locally.
```
cd zecpaperwallet/web
wasm-pack build
cd www
npm install
npm run start
```
This will start a local web server at `localhost:8080` where you can access the paper wallet

3
web/package-lock.json

@ -1,3 +0,0 @@
{
"lockfileVersion": 1
}

17
web/src/lib.rs

@ -1,17 +0,0 @@
mod utils;
use zecpaperlib::paper::{generate_wallet, double_sha256};
use wasm_bindgen::prelude::*;
// When the `wee_alloc` feature is enabled, use `wee_alloc` as the global
// allocator.
#[cfg(feature = "wee_alloc")]
#[global_allocator]
static ALLOC: wee_alloc::WeeAlloc = wee_alloc::WeeAlloc::INIT;
#[wasm_bindgen]
pub fn get_wallet(zaddrs: u32, taddrs: u32, entropy: String) -> String {
let w = generate_wallet(false, false, zaddrs, taddrs, &double_sha256(entropy.as_bytes()));
return w;
}

10
web/src/utils.rs

@ -1,10 +0,0 @@
pub fn set_panic_hook() {
// When the `console_error_panic_hook` feature is enabled, we can call the
// `set_panic_hook` function at least once during initialization, and then
// we will get better error messages if our code ever panics.
//
// For more details see
// https://github.com/rustwasm/console_error_panic_hook#readme
#[cfg(feature = "console_error_panic_hook")]
console_error_panic_hook::set_once();
}

13
web/tests/web.rs

@ -1,13 +0,0 @@
//! Test suite for the Web and headless browsers.
#![cfg(target_arch = "wasm32")]
extern crate wasm_bindgen_test;
use wasm_bindgen_test::*;
wasm_bindgen_test_configure!(run_in_browser);
#[wasm_bindgen_test]
fn pass() {
assert_eq!(1 + 1, 2);
}

3
web/www/.gitignore

@ -1,3 +0,0 @@
node_modules
dist
package-lock.json

5
web/www/.travis.yml

@ -1,5 +0,0 @@
language: node_js
node_js: "10"
script:
- ./node_modules/.bin/webpack

201
web/www/LICENSE-APACHE

@ -1,201 +0,0 @@
Apache License
Version 2.0, January 2004
http://www.apache.org/licenses/
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
1. Definitions.
"License" shall mean the terms and conditions for use, reproduction,
and distribution as defined by Sections 1 through 9 of this document.
"Licensor" shall mean the copyright owner or entity authorized by
the copyright owner that is granting the License.
"Legal Entity" shall mean the union of the acting entity and all
other entities that control, are controlled by, or are under common
control with that entity. For the purposes of this definition,
"control" means (i) the power, direct or indirect, to cause the
direction or management of such entity, whether by contract or
otherwise, or (ii) ownership of fifty percent (50%) or more of the
outstanding shares, or (iii) beneficial ownership of such entity.
"You" (or "Your") shall mean an individual or Legal Entity
exercising permissions granted by this License.
"Source" form shall mean the preferred form for making modifications,
including but not limited to software source code, documentation
source, and configuration files.
"Object" form shall mean any form resulting from mechanical
transformation or translation of a Source form, including but
not limited to compiled object code, generated documentation,
and conversions to other media types.
"Work" shall mean the work of authorship, whether in Source or
Object form, made available under the License, as indicated by a
copyright notice that is included in or attached to the work
(an example is provided in the Appendix below).
"Derivative Works" shall mean any work, whether in Source or Object
form, that is based on (or derived from) the Work and for which the
editorial revisions, annotations, elaborations, or other modifications
represent, as a whole, an original work of authorship. For the purposes
of this License, Derivative Works shall not include works that remain
separable from, or merely link (or bind by name) to the interfaces of,
the Work and Derivative Works thereof.
"Contribution" shall mean any work of authorship, including
the original version of the Work and any modifications or additions
to that Work or Derivative Works thereof, that is intentionally
submitted to Licensor for inclusion in the Work by the copyright owner
or by an individual or Legal Entity authorized to submit on behalf of
the copyright owner. For the purposes of this definition, "submitted"
means any form of electronic, verbal, or written communication sent
to the Licensor or its representatives, including but not limited to
communication on electronic mailing lists, source code control systems,
and issue tracking systems that are managed by, or on behalf of, the
Licensor for the purpose of discussing and improving the Work, but
excluding communication that is conspicuously marked or otherwise
designated in writing by the copyright owner as "Not a Contribution."
"Contributor" shall mean Licensor and any individual or Legal Entity
on behalf of whom a Contribution has been received by Licensor and
subsequently incorporated within the Work.
2. Grant of Copyright License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
copyright license to reproduce, prepare Derivative Works of,
publicly display, publicly perform, sublicense, and distribute the
Work and such Derivative Works in Source or Object form.
3. Grant of Patent License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
(except as stated in this section) patent license to make, have made,
use, offer to sell, sell, import, and otherwise transfer the Work,
where such license applies only to those patent claims licensable
by such Contributor that are necessarily infringed by their
Contribution(s) alone or by combination of their Contribution(s)
with the Work to which such Contribution(s) was submitted. If You
institute patent litigation against any entity (including a
cross-claim or counterclaim in a lawsuit) alleging that the Work
or a Contribution incorporated within the Work constitutes direct
or contributory patent infringement, then any patent licenses
granted to You under this License for that Work shall terminate
as of the date such litigation is filed.
4. Redistribution. You may reproduce and distribute copies of the
Work or Derivative Works thereof in any medium, with or without
modifications, and in Source or Object form, provided that You
meet the following conditions:
(a) You must give any other recipients of the Work or
Derivative Works a copy of this License; and
(b) You must cause any modified files to carry prominent notices
stating that You changed the files; and
(c) You must retain, in the Source form of any Derivative Works
that You distribute, all copyright, patent, trademark, and
attribution notices from the Source form of the Work,
excluding those notices that do not pertain to any part of
the Derivative Works; and
(d) If the Work includes a "NOTICE" text file as part of its
distribution, then any Derivative Works that You distribute must
include a readable copy of the attribution notices contained
within such NOTICE file, excluding those notices that do not
pertain to any part of the Derivative Works, in at least one
of the following places: within a NOTICE text file distributed
as part of the Derivative Works; within the Source form or
documentation, if provided along with the Derivative Works; or,
within a display generated by the Derivative Works, if and
wherever such third-party notices normally appear. The contents
of the NOTICE file are for informational purposes only and
do not modify the License. You may add Your own attribution
notices within Derivative Works that You distribute, alongside
or as an addendum to the NOTICE text from the Work, provided
that such additional attribution notices cannot be construed
as modifying the License.
You may add Your own copyright statement to Your modifications and
may provide additional or different license terms and conditions
for use, reproduction, or distribution of Your modifications, or
for any such Derivative Works as a whole, provided Your use,
reproduction, and distribution of the Work otherwise complies with
the conditions stated in this License.
5. Submission of Contributions. Unless You explicitly state otherwise,
any Contribution intentionally submitted for inclusion in the Work
by You to the Licensor shall be under the terms and conditions of
this License, without any additional terms or conditions.
Notwithstanding the above, nothing herein shall supersede or modify
the terms of any separate license agreement you may have executed
with Licensor regarding such Contributions.
6. Trademarks. This License does not grant permission to use the trade
names, trademarks, service marks, or product names of the Licensor,
except as required for reasonable and customary use in describing the
origin of the Work and reproducing the content of the NOTICE file.
7. Disclaimer of Warranty. Unless required by applicable law or
agreed to in writing, Licensor provides the Work (and each
Contributor provides its Contributions) on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
implied, including, without limitation, any warranties or conditions
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
PARTICULAR PURPOSE. You are solely responsible for determining the
appropriateness of using or redistributing the Work and assume any
risks associated with Your exercise of permissions under this License.
8. Limitation of Liability. In no event and under no legal theory,
whether in tort (including negligence), contract, or otherwise,
unless required by applicable law (such as deliberate and grossly
negligent acts) or agreed to in writing, shall any Contributor be
liable to You for damages, including any direct, indirect, special,
incidental, or consequential damages of any character arising as a
result of this License or out of the use or inability to use the
Work (including but not limited to damages for loss of goodwill,
work stoppage, computer failure or malfunction, or any and all
other commercial damages or losses), even if such Contributor
has been advised of the possibility of such damages.
9. Accepting Warranty or Additional Liability. While redistributing
the Work or Derivative Works thereof, You may choose to offer,
and charge a fee for, acceptance of support, warranty, indemnity,
or other liability obligations and/or rights consistent with this
License. However, in accepting such obligations, You may act only
on Your own behalf and on Your sole responsibility, not on behalf
of any other Contributor, and only if You agree to indemnify,
defend, and hold each Contributor harmless for any liability
incurred by, or claims asserted against, such Contributor by reason
of your accepting any such warranty or additional liability.
END OF TERMS AND CONDITIONS
APPENDIX: How to apply the Apache License to your work.
To apply the Apache License to your work, attach the following
boilerplate notice, with the fields enclosed by brackets "[]"
replaced with your own identifying information. (Don't include
the brackets!) The text should be enclosed in the appropriate
comment syntax for the file format. We also recommend that a
file or class name and description of purpose be included on the
same "printed page" as the copyright notice for easier
identification within third-party archives.
Copyright [yyyy] [name of copyright owner]
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.

25
web/www/LICENSE-MIT

@ -1,25 +0,0 @@
Copyright (c) [year] [name]
Permission is hereby granted, free of charge, to any
person obtaining a copy of this software and associated
documentation files (the "Software"), to deal in the
Software without restriction, including without
limitation the rights to use, copy, modify, merge,
publish, distribute, sublicense, and/or sell copies of
the Software, and to permit persons to whom the Software
is furnished to do so, subject to the following
conditions:
The above copyright notice and this permission notice
shall be included in all copies or substantial portions
of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF
ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED
TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT
SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR
IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
DEALINGS IN THE SOFTWARE.

5
web/www/bootstrap.js

@ -1,5 +0,0 @@
// A dependency graph that contains any wasm must all be imported
// asynchronously. This `bootstrap.js` file does the single async import, so
// that no one else needs to worry about it again.
import("./index.js")
.catch(e => console.error("Error importing `index.js`:", e));

159
web/www/index.html

@ -1,159 +0,0 @@
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1">
<!-- Latest compiled and minified CSS -->
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css" integrity="sha384-BVYiiSIFeK1dGmJRAkycuHAHRg32OmUcww7on3RYdg4Va+PmSTsz/K68vbdEjh4u" crossorigin="anonymous">
<!-- Optional theme -->
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap-theme.min.css" integrity="sha384-rHyoN1iRsVXV4nD0JutlnGaslCJuC7uwjduW9SVrLvRYooPp2bWYgmgJQIXwl/Sp" crossorigin="anonymous">
<style type="text/css">
@media print {
@page {
size: 330mm 427mm;
margin: 14mm;
}
.page-break {page-break-after: always;}
.container {
width: 1200px;
}
}
.h-divider{
margin-top:5px;
margin-bottom:15px;
height:1px;
width:100%;
border-top:1px solid black;
}
.h-dashed {
height:1px;
width:100%;
border-top:1px dashed gray;
}
.fixed-width {
font-family: monospace;
font-size: 1.2em;
}
.pk-section canvas {
margin-top: 30px;
}
.address-section h1 {
padding-top: 30px;
padding-left: 20px
}
.address-section p {
padding-left: 20px;
}
</style>
<title>zecpaperwallet Web!</title>
</head>
<body>
<script src="./bootstrap.js"></script>
<nav class="navbar navbar-default">
<div class="container">
<div class="navbar-header">
<h1>ZecPaperWallet - Zcash Sapling Paper Wallet Generator</h1>
</div>
</div>
</nav>
<div class="container">
<div class="row>">
<div class="alert alert-warning" role="alert">
<span class="glyphicon glyphicon-exclamation-sign" aria-hidden="true"></span>
<span class="sr-only">Error:</span>
For informational purposes only. For serious wallets, please run <a target="_blank" href="https://github.com/adityapk00/zecpaperwallet"><code>zecpaperwallet</code></a> offline on an air-gapped computer.
</div>
</div>
<div id="result-panel">
<div class="panel panel-primary">
<div class="panel-heading">
<h1 class="panel-title">Zcash Sapling Paper Wallet</h1>
</div>
<div class="panel-body" id="wallet">
</div>
</div>
</div>
<div class="row">
<div class="col-sm-1 col-sm-offset-5">
<button type="button" id="reset_button" class="btn btn-warning">Reset</button>
</div>
<div class="col-sm-1">
<button type="button" id="print_button" class="btn btn-success">Print</button>
</div>
</div>
<div class="row" style="padding-top: 10px;">
<div class="col-sm-12">
<div class="well">
Copyright &copy; 2019, ZecWallet.
</div>
</div>
</div>
</div>
<div class="modal" id="configdialog" tabindex="-1" role="dialog">
<div class="modal-dialog" role="document">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title">ZecPaperWallet - Configure Entropy</h4>
</div>
<div class="modal-body">
<div class="form-group">
<label for="numAddresses">Number of z Addresses</label>
<input type="text" class="form-control" id="numzAddresses" value="2" onkeypress="if ( isNaN( String.fromCharCode(event.keyCode) )) return false;">
<label for="numAddresses">Number of t Addresses</label>
<input type="text" class="form-control" id="numtAddresses" value="2" onkeypress="if ( isNaN( String.fromCharCode(event.keyCode) )) return false;">
</div>
<p>Move around your mouse or type random characters
into the box below until the bar is full.
</p>
<input type="text" id="keyboard_entropy" placeholder="entropy" style="width: 100%"/>
<hr/>
<p>Collected Entropy:</p>
<div class="progress">
<div class="progress-bar" id="entropy_bar" role="progressbar" aria-valuenow="0" aria-valuemin="0" aria-valuemax="100" style="width: 0%;"></div>
</div>
</div>
<div class="modal-footer">
<button type="button" id="generate_button" class="btn btn-warning">Generate >></button>
</div>
</div><!-- /.modal-content -->
</div><!-- /.modal-dialog -->
</div><!-- /.modal -->
<div class="modal" id="pleasewait" tabindex="-1" role="dialog">
<div class="modal-dialog" role="document">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title">Generating Wallet</h4>
</div>
<div class="modal-body">
<p>Generating wallet. Please wait&hellip;</p>
</div>
</div><!-- /.modal-content -->
</div><!-- /.modal-dialog -->
</div><!-- /.modal -->
</body>
</html>

153
web/www/index.js

@ -1,153 +0,0 @@
global.jQuery = require('jquery');
require('bootstrap');
var QRCode = require('qrcode')
import * as wasm from "zecpaperwallet";
var address_number = 0;
function add_section(wallet_item) {
let htmls = `
<div class="row address-section">
<div class="col-sm-9" style="word-break: break-word;">
<h1> Address
${(() => {
if (wallet_item["address"].startsWith("z")) { return "(Sapling)"; }
else { return "(Transparent)"; }
}) ()
}
</h1>
<p class="fixed-width"> ${wallet_item["address"]} </p>
</div>
<div class="col-sm-3">
<canvas id="qrcode_addr_${address_number}"></canvas>
</div>
</div>
`;
jQuery("#wallet").append(htmls);
QRCode.toCanvas(document.getElementById("qrcode_addr_"+address_number),
wallet_item["address"], {
scale : 5.5
});
let pk_section = `
<div class="row pk-section">
<div class="h-dashed"></div>
<div class="col-sm-3">
<canvas id="qrcode_pk_${address_number}"></canvas>
</div>
<div class="col-sm-9" style="word-break: break-word;">
<h1> Private Key </h1>
<p class="fixed-width"> ${wallet_item["private_key"]} </p>
<br/>
<h2> Address </h2>
<p class="fixed-width"> ${wallet_item["address"]} </p>
${(() => {
if (wallet_item.seed) {
return `<code> HD Key: ${wallet_item["seed"]["HDSeed"]}, path: ${wallet_item["seed"]["path"]} </code>`;
} else { return ""; }
}) ()
}
</div>
</div>
<div class='h-divider'></div>
`;
jQuery("#wallet").append(pk_section);
QRCode.toCanvas(document.getElementById("qrcode_pk_"+address_number),
wallet_item["private_key"], {
scale: wallet_item["private_key"].length < 60 ? 6.5 : 3.5
});
address_number++;
if (address_number % 2 == 0) {
jQuery("#wallet").append("<div class='page-break'></div>");
}
}
var user_entropy = "";
function update_user_entropy() {
let valeur = (user_entropy.length / 2) / 32 * 100; // hex is 2 chars per byte
if (valeur > 100) {
valeur = 100;
if (jQuery("#generate_button").hasClass("btn-warning")) {
jQuery("#generate_button").removeClass("btn-warning");
jQuery("#generate_button").addClass("btn-success");
}
if (!jQuery("#entropy_bar").hasClass("progress-bar-success")) {
jQuery("#entropy_bar").addClass("progress-bar-success");
}
}
jQuery('#entropy_bar').css('width', valeur+'%').attr('aria-valuenow', valeur);
}
// Mouse move for entropy collection
var mouse_count = 0;
jQuery("body").mousemove(function(e) {
if (mouse_count++ % 5 > 0) return;
user_entropy += ((e.originalEvent.clientX + e.originalEvent.clientY) % 16).toString(16);
update_user_entropy();
});
jQuery("#keyboard_entropy").keypress(function (e) {
user_entropy += (e.originalEvent.charCode % 32).toString(16);
update_user_entropy();
});
jQuery("#generate_button").click(function (e) {
jQuery("#configdialog").modal('hide');
});
jQuery("#reset_button").click(function (e) {
user_entropy = "";
update_user_entropy();
address_number = 0;
jQuery("#generate_button").removeClass("btn-success");
jQuery("#generate_button").addClass("btn-warning");
jQuery("#entropy_bar").removeClass("progress-bar-success");
jQuery("#wallet").empty();
jQuery("#configdialog").modal('show');
});
jQuery("#print_button").click(function (e) {
window.print();
});
// First trigger the modal
jQuery("#configdialog").modal({
keyboard: false
});
const toHexString = bytes =>
bytes.reduce((str, byte) => str + byte.toString(16).padStart(2, '0'), '');
jQuery("#configdialog").on("hidden.bs.modal", function (e) {
// Get system entropy
var buf = new Uint8Array(32);
window.crypto.getRandomValues(buf);
let system_entropy = toHexString(buf);
let numzAddresses = jQuery("#numzAddresses").val();
let numtAddresses = jQuery("#numtAddresses").val();
jQuery("#pleasewait").modal('show');
// Run this async so that the please wait dialog can show
setTimeout(() => {
let w = JSON.parse(wasm.get_wallet(numzAddresses, numtAddresses, user_entropy + system_entropy));
w.forEach(wallet_item => {
add_section(wallet_item);
});
jQuery("#pleasewait").modal("hide");
}, 1);
});

42
web/www/package.json

@ -1,42 +0,0 @@
{
"name": "create-wasm-app",
"version": "0.1.0",
"description": "create an app to consume rust-generated wasm packages",
"main": "index.js",
"bin": {
"create-wasm-app": ".bin/create-wasm-app.js"
},
"scripts": {
"build": "webpack --config webpack.config.js",
"start": "webpack-dev-server"
},
"repository": {
"type": "git",
"url": "git+https://github.com/rustwasm/create-wasm-app.git"
},
"keywords": [
"webassembly",
"wasm",
"rust",
"webpack"
],
"author": "Aditya Kulkarni <zcash@adityapk.com>",
"license": "(MIT OR Apache-2.0)",
"bugs": {
"url": "https://github.com/rustwasm/create-wasm-app/issues"
},
"homepage": "https://github.com/rustwasm/create-wasm-app#readme",
"dependencies": {
"bootstrap": "^3.4.1",
"jquery": "^3.4.1",
"qrcode": "^1.3.4",
"zecpaperwallet": "file:../pkg"
},
"devDependencies": {
"copy-webpack-plugin": "^5.0.0",
"hello-wasm-pack": "^0.1.0",
"webpack": "^4.35.2",
"webpack-cli": "^3.3.5",
"webpack-dev-server": "^3.1.5"
}
}

14
web/www/webpack.config.js

@ -1,14 +0,0 @@
const CopyWebpackPlugin = require("copy-webpack-plugin");
const path = require('path');
module.exports = {
entry: "./bootstrap.js",
output: {
path: path.resolve(__dirname, "dist"),
filename: "bootstrap.js",
},
mode: "production",
plugins: [
new CopyWebpackPlugin(['index.html'])
],
};
Loading…
Cancel
Save