11package cash.p.terminal.core.adapters
22
3+ import cash.p.terminal.core.ISendBitcoinAdapter
34import cash.p.terminal.core.ITransactionsAdapter
45import cash.p.terminal.core.UnsupportedFilterException
56import cash.p.terminal.entities.LastBlockInfo
@@ -35,6 +36,7 @@ import io.horizontalsystems.bitcoincore.rbf.ReplacementTransactionInfo
3536import io.horizontalsystems.bitcoincore.storage.FullTransaction
3637import io.horizontalsystems.bitcoincore.storage.UnspentOutput
3738import io.horizontalsystems.bitcoincore.storage.UnspentOutputInfo
39+ import io.horizontalsystems.bitcoincore.storage.UtxoFilters
3840import io.horizontalsystems.core.BackgroundManager
3941import io.horizontalsystems.core.BackgroundManagerState
4042import io.horizontalsystems.core.entities.BlockchainType
@@ -50,7 +52,6 @@ import kotlinx.coroutines.Dispatchers
5052import kotlinx.coroutines.cancel
5153import kotlinx.coroutines.flow.Flow
5254import kotlinx.coroutines.flow.StateFlow
53- import kotlinx.coroutines.flow.asStateFlow
5455import kotlinx.coroutines.flow.emptyFlow
5556import kotlinx.coroutines.launch
5657import kotlinx.coroutines.reactive.asFlow
@@ -68,7 +69,7 @@ abstract class BitcoinBaseAdapter(
6869 val wallet : Wallet ,
6970 private val confirmationsThreshold : Int ,
7071 protected val decimal : Int = 8
71- ) : IAdapter, ITransactionsAdapter, IBalanceAdapter, IReceiveAdapter {
72+ ) : IAdapter, ITransactionsAdapter, IBalanceAdapter, IReceiveAdapter, ISendBitcoinAdapter {
7273
7374 private val scope = CoroutineScope (Dispatchers .Default )
7475
@@ -108,6 +109,9 @@ abstract class BitcoinBaseAdapter(
108109 protected val transactionRecordsSubject: PublishSubject <List <TransactionRecord >> =
109110 PublishSubject .create()
110111
112+ final override val unspentOutputs: List <UnspentOutputInfo >
113+ get() = kit.getUnspentOutputs(UtxoFilters ())
114+
111115 override val balanceUpdatedFlow: Flow <Unit >
112116 get() = balanceUpdatedSubject.toFlowable(BackpressureStrategy .BUFFER ).asFlow()
113117
@@ -309,7 +313,7 @@ abstract class BitcoinBaseAdapter(
309313 }
310314 }
311315
312- suspend fun send (
316+ override suspend fun send (
313317 amount : BigDecimal ,
314318 address : String ,
315319 memo : String? ,
@@ -318,6 +322,9 @@ abstract class BitcoinBaseAdapter(
318322 pluginData : Map <Byte , IPluginData >? ,
319323 transactionSorting : TransactionDataSortMode ? ,
320324 rbfEnabled : Boolean ,
325+ dustThreshold : Int? ,
326+ changeToFirstInput : Boolean ,
327+ utxoFilters : UtxoFilters ,
321328 logger : AppLogger
322329 ): String {
323330 logger.info(" call btc-kit.send" )
@@ -331,44 +338,59 @@ abstract class BitcoinBaseAdapter(
331338 sortType = sortingType,
332339 unspentOutputs = unspentOutputs,
333340 pluginData = pluginData ? : mapOf (),
341+ dustThreshold = dustThreshold,
342+ changeToFirstInput = changeToFirstInput,
343+ filters = utxoFilters,
334344 rbfEnabled = rbfEnabled
335345 )
336346 return sendData.header.uid
337347 }
338348
339- fun availableBalance (
349+ override fun availableBalance (
340350 feeRate : Int ,
341351 address : String? ,
342352 memo : String? ,
343353 unspentOutputs : List <UnspentOutputInfo >? ,
344- pluginData : Map <Byte , IPluginData >?
354+ pluginData : Map <Byte , IPluginData >? ,
355+ dustThreshold : Int? ,
356+ changeToFirstInput : Boolean ,
357+ utxoFilters : UtxoFilters
345358 ): BigDecimal {
346359 return try {
347360 val maximumSpendableValue = kit.maximumSpendableValue(
348- address, memo, feeRate, unspentOutputs, pluginData
349- ? : mapOf ()
361+ address = address,
362+ memo = memo,
363+ feeRate = feeRate,
364+ unspentOutputInfos = unspentOutputs,
365+ pluginData = pluginData ? : mapOf (),
366+ dustThreshold = dustThreshold,
367+ changeToFirstInput = changeToFirstInput,
368+ filters = utxoFilters,
350369 )
351370 satoshiToBTC(maximumSpendableValue, RoundingMode .CEILING )
352371 } catch (e: Exception ) {
353372 BigDecimal .ZERO
354373 }
355374 }
356375
357- fun minimumSendAmount (address : String? ): BigDecimal ? {
376+ override fun minimumSendAmount (address : String? , dustThreshold : Int ? ): BigDecimal ? {
358377 return try {
359- satoshiToBTC(kit.minimumSpendableValue(address).toLong(), RoundingMode .CEILING )
378+ satoshiToBTC(kit.minimumSpendableValue(address, dustThreshold ).toLong(), RoundingMode .CEILING )
360379 } catch (e: Exception ) {
361380 null
362381 }
363382 }
364383
365- fun bitcoinFeeInfo (
384+ override fun bitcoinFeeInfo (
366385 amount : BigDecimal ,
367386 feeRate : Int ,
368387 address : String? ,
369388 memo : String? ,
370389 unspentOutputs : List <UnspentOutputInfo >? ,
371- pluginData : Map <Byte , IPluginData >?
390+ pluginData : Map <Byte , IPluginData >? ,
391+ dustThreshold : Int? ,
392+ changeToFirstInput : Boolean ,
393+ filters : UtxoFilters
372394 ): BitcoinFeeInfo ? {
373395 return try {
374396 val satoshiAmount = (amount * satoshisInBitcoin).toLong()
@@ -379,7 +401,10 @@ abstract class BitcoinBaseAdapter(
379401 senderPay = true ,
380402 feeRate = feeRate,
381403 unspentOutputs = unspentOutputs,
382- pluginData = pluginData ? : mapOf ()
404+ pluginData = pluginData ? : mapOf (),
405+ dustThreshold = dustThreshold,
406+ changeToFirstInput = changeToFirstInput,
407+ filters = filters
383408 ).let {
384409 BitcoinFeeInfo (
385410 unspentOutputs = it.unspentOutputs,
@@ -393,7 +418,7 @@ abstract class BitcoinBaseAdapter(
393418 }
394419 }
395420
396- fun validate (address : String , pluginData : Map <Byte , IPluginData >? ) {
421+ override fun validate (address : String , pluginData : Map <Byte , IPluginData >? ) {
397422 kit.validateAddress(address, pluginData ? : mapOf ())
398423 }
399424
0 commit comments