2023-06-20 02:26:38 -07:00
@file : Suppress ( " MaxLineLength " )
2021-04-22 15:52:32 -07:00
package cash.z.ecc.android.sdk.sample
2021-08-30 05:53:12 -07:00
import androidx.test.filters.LargeTest
2021-04-22 15:52:32 -07:00
import cash.z.ecc.android.sdk.ext.ZcashSdk
2022-07-12 05:40:09 -07:00
import cash.z.ecc.android.sdk.model.BlockHeight
2022-06-21 16:34:42 -07:00
import cash.z.ecc.android.sdk.model.Zatoshi
2022-08-02 06:29:09 -07:00
import cash.z.ecc.android.sdk.model.ZcashNetwork
2021-04-22 15:52:32 -07:00
import cash.z.ecc.android.sdk.util.TestWallet
import kotlinx.coroutines.delay
import kotlinx.coroutines.runBlocking
import org.junit.Assert
2021-08-30 05:53:12 -07:00
import org.junit.Ignore
2021-04-22 15:52:32 -07:00
import org.junit.Test
/ * *
* Sample tests are used to demonstrate functionality . This one attempts to setup a scenario where
* one wallet shields funds and the other restores from the blockchain . Ultimately , they should have
* the same data .
* /
class TransparentRestoreSample {
2022-06-21 16:34:42 -07:00
val TX _VALUE = Zatoshi ( ZcashSdk . MINERS_FEE . value / 2 )
2021-04-22 15:52:32 -07:00
// val walletA = SimpleWallet(SEED_PHRASE, "WalletA")
// the wallet that only restores what everyone else did
// val walletB = SimpleWallet(SEED_PHRASE, "WalletB")
// // the wallet that sends Z2T transactions
//
// // sandbox wallet
// val walletSandbox = SimpleWallet(SEED_PHRASE, "WalletC")
// val walletZ2T = SimpleWallet(SEED_PHRASE, "WalletZ2T")
// val externalTransparentAddress =
// DerivationTool.deriveTransparentAddress(Mnemonics.MnemonicCode(RANDOM_PHRASE).toSeed(), Testnet)
// @Test
fun sendZ2Texternal ( ) = runBlocking {
val extWallet = TestWallet ( TestWallet . Backups . ALICE , alias = " WalletE " )
extWallet . sync ( )
// extWallet.send(542, walletSandbox.transparentAddress, "External funds memo is lost, though")
delay ( 1000 )
}
// @Test
fun sendZ2T ( ) = runBlocking {
// walletSandbox.sync()
// walletZ2T.send(543, externalTransparentAddress, "External funds memo is lost, though")
delay ( 1000 )
}
// @Test
fun autoShield ( ) = runBlocking < Unit > {
val wallet = TestWallet ( TestWallet . Backups . SAMPLE _WALLET , alias = " WalletC " )
wallet . sync ( )
val tbalance = wallet . transparentBalance ( )
val address = wallet . transparentAddress
2023-06-20 02:26:38 -07:00
Assert . assertTrue (
" Not enough funds to run sample. Expected some Zatoshi but found ${tbalance.available} . " +
" Try adding funds to $address " ,
tbalance . available . value > 0
)
2021-04-22 15:52:32 -07:00
// wallet.shieldFunds()
}
// @Test
fun cli ( ) = runBlocking < Unit > {
// val wallet = SimpleWallet(SEED_PHRASE, "WalletCli")
// wallet.sync()
// wallet.rewindToHeight(1343500).join(45_000)
val wallet = TestWallet ( TestWallet . Backups . SAMPLE _WALLET , alias = " WalletC " )
// wallet.sync().rewindToHeight(1339178).join(10000)
2022-07-12 05:40:09 -07:00
wallet . sync ( ) . rewindToHeight ( BlockHeight . new ( ZcashNetwork . Testnet , 1339178 ) ) . send (
2021-04-22 15:52:32 -07:00
" ztestsapling17zazsl8rryl8kjaqxnr2r29rw9d9a2mud37ugapm0s8gmyv0ue43h9lqwmhdsp3nu9dazeqfs6l " ,
" is send broken? "
) . join ( 5 )
}
2021-08-30 05:53:12 -07:00
// This test is extremely slow and doesn't assert anything, so the benefit of this test is unclear
// It is disabled to allow moving forward with configuring CI.
2021-04-22 15:52:32 -07:00
@Test
2021-08-30 05:53:12 -07:00
@LargeTest
@Ignore ( " This test is extremely slow " )
2021-04-22 15:52:32 -07:00
fun kris ( ) = runBlocking < Unit > {
2022-07-12 05:40:09 -07:00
val wallet0 = TestWallet (
TestWallet . Backups . SAMPLE_WALLET . seedPhrase ,
" tmpabc " ,
2022-08-02 06:29:09 -07:00
ZcashNetwork . Testnet ,
2022-07-12 05:40:09 -07:00
startHeight = BlockHeight . new (
ZcashNetwork . Testnet ,
1330190
)
)
2021-04-22 15:52:32 -07:00
// val wallet1 = SimpleWallet(WALLET0_PHRASE, "Wallet1")
wallet0 . sync ( ) // .shieldFunds()
// .send(amount = 1543L, memo = "")
. join ( )
// wallet1.sync().join(5_000L)
}
/ *
* /
/ * *
* Sanity check that the wallet has enough funds for the test
* /
// @Test
fun hasFunds ( ) = runBlocking < Unit > {
2022-08-02 06:29:09 -07:00
val walletSandbox = TestWallet (
TestWallet . Backups . SAMPLE_WALLET . seedPhrase ,
" WalletC " ,
ZcashNetwork . Testnet ,
startHeight = BlockHeight . new (
ZcashNetwork . Testnet ,
1330190
)
)
2021-04-22 15:52:32 -07:00
// val job = walletA.walletScope.launch {
// walletA.sync()
// }
walletSandbox . sync ( )
// job.join()
delay ( 500 )
// val value = walletA.available
// val address = walletA.shieldedAddress
// Assert.assertTrue("Not enough funds to run sample. Expected at least $TX_VALUE Zatoshi but found $value. Try adding funds to $address", value >= TX_VALUE)
// send z->t
// walletA.send(TX_VALUE, walletA.transparentAddress, "${TransparentRestoreSample::class.java.simpleName} z->t")
2022-07-12 05:40:09 -07:00
walletSandbox . rewindToHeight ( BlockHeight . new ( ZcashNetwork . Testnet , 1339178 ) )
2021-04-22 15:52:32 -07:00
delay ( 500 )
// walletB.sync()
// rewind database B to height then rescan
}
// // when startHeight is null, it will use the latest checkpoint
// class SimpleWallet(
// seedPhrase: String,
// alias: String = ZcashSdk.DEFAULT_ALIAS,
// startHeight: Int? = null
// ) {
// val walletScope = CoroutineScope(
// SupervisorJob() + newFixedThreadPoolContext(3, this.javaClass.simpleName)
// )
// private val context = InstrumentationRegistry.getInstrumentation().context
// private val seed: ByteArray = Mnemonics.MnemonicCode(seedPhrase).toSeed()
// private val shieldedSpendingKey = DerivationTool.deriveSpendingKeys(seed, Testnet)[0]
2022-05-18 18:04:30 -07:00
// private val transparentAccountPrivateKey = DerivationTool.deriveTransparentAccountPrivateKey(seed, Testnet)
2021-04-22 15:52:32 -07:00
// private val host = "lightwalletd.testnet.electriccoin.co"
// private val initializer = Initializer(context) { config ->
// config.importWallet(seed, startHeight)
// config.setNetwork(Testnet, host)
// config.alias = alias
// }
//
// val synchronizer = Synchronizer(initializer)
// val available get() = synchronizer.latestBalance.availableZatoshi
// val shieldedAddress = DerivationTool.deriveShieldedAddress(seed, Testnet)
// val transparentAddress = DerivationTool.deriveTransparentAddress(seed, Testnet)
// val birthdayHeight get() = synchronizer.latestBirthdayHeight
//
// suspend fun transparentBalance(): WalletBalance {
// synchronizer.refreshUtxos(transparentAddress, synchronizer.latestBirthdayHeight)
// return synchronizer.getTransparentBalance(transparentAddress)
// }
//
// suspend fun sync(): SimpleWallet {
// if (!synchronizer.isStarted) {
// twig("Starting sync")
// synchronizer.start(walletScope)
// } else {
// twig("Awaiting next SYNCED status")
// }
//
// // block until synced
// synchronizer.status.first { it == SYNCED }
// twig("Synced!")
// return this
// }
//
// suspend fun send(address: String = transparentAddress, memo: String = "", amount: Long = 500L): SimpleWallet {
// synchronizer.sendToAddress(shieldedSpendingKey, amount, address, memo)
// .takeWhile { it.isPending() }
// .collect {
// twig("Updated transaction: $it")
// }
// return this
// }
//
// suspend fun rewindToHeight(height: Int): SimpleWallet {
// synchronizer.rewindToHeight(height, false)
// return this
// }
//
// suspend fun shieldFunds(): SimpleWallet {
// twig("checking $transparentAddress for transactions!")
// synchronizer.refreshUtxos(transparentAddress, 935000).let { count ->
// twig("FOUND $count new UTXOs")
// }
//
// synchronizer.getTransparentBalance(transparentAddress).let { walletBalance ->
// twig("FOUND utxo balance of total: ${walletBalance.totalZatoshi} available: ${walletBalance.availableZatoshi}")
//
// if (walletBalance.availableZatoshi > 0L) {
2022-05-18 18:04:30 -07:00
// synchronizer.shieldFunds(shieldedSpendingKey, transparentAccountPrivateKey)
2021-04-22 15:52:32 -07:00
// .onCompletion { twig("done shielding funds") }
// .catch { twig("Failed with $it") }
// .collect()
// }
// }
//
// return this
// }
//
// suspend fun join(timeout: Long? = null): SimpleWallet {
// // block until stopped
// twig("Staying alive until synchronizer is stopped!")
// if (timeout != null) {
// twig("Scheduling a stop in ${timeout}ms")
// walletScope.launch {
// delay(timeout)
// synchronizer.stop()
// }
// }
// synchronizer.status.first { it == Synchronizer.Status.STOPPED }
// twig("Stopped!")
// return this
// }
//
// companion object {
// init {
// Twig.plant(TroubleshootingTwig())
// }
// }
// }
}