mirror of
https://github.com/cypherstack/stack_wallet.git
synced 2024-12-23 11:59:30 +00:00
commit
352680ecc9
76 changed files with 6268 additions and 4032 deletions
|
@ -1,3 +1,4 @@
|
|||
import 'package:flutter/foundation.dart';
|
||||
import 'package:isar/isar.dart';
|
||||
import 'package:stackwallet/models/isar/models/isar_models.dart';
|
||||
import 'package:stackwallet/utilities/stack_file_system.dart';
|
||||
|
@ -28,7 +29,7 @@ class MainDB {
|
|||
AddressSchema,
|
||||
],
|
||||
directory: (await StackFileSystem.applicationIsarDirectory()).path,
|
||||
inspector: false,
|
||||
inspector: kDebugMode,
|
||||
name: "wallet_data",
|
||||
);
|
||||
return true;
|
||||
|
@ -47,6 +48,31 @@ class MainDB {
|
|||
await isar.addresses.putAll(addresses);
|
||||
});
|
||||
|
||||
Future<void> updateOrPutAddresses(List<Address> addresses) async {
|
||||
await isar.writeTxn(() async {
|
||||
for (final address in addresses) {
|
||||
final storedAddress = await isar.addresses
|
||||
.getByValueWalletId(address.value, address.walletId);
|
||||
|
||||
if (storedAddress == null) {
|
||||
await isar.addresses.put(address);
|
||||
} else {
|
||||
address.id = storedAddress.id;
|
||||
await storedAddress.transactions.load();
|
||||
final txns = storedAddress.transactions.toList();
|
||||
await isar.addresses.delete(storedAddress.id);
|
||||
await isar.addresses.put(address);
|
||||
address.transactions.addAll(txns);
|
||||
await address.transactions.save();
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
Future<Address?> getAddress(String walletId, String address) async {
|
||||
return isar.addresses.getByValueWalletId(address, walletId);
|
||||
}
|
||||
|
||||
Future<void> updateAddress(Address oldAddress, Address newAddress) =>
|
||||
isar.writeTxn(() async {
|
||||
newAddress.id = oldAddress.id;
|
||||
|
@ -73,6 +99,10 @@ class MainDB {
|
|||
await isar.transactions.putAll(transactions);
|
||||
});
|
||||
|
||||
Future<Transaction?> getTransaction(String walletId, String txid) async {
|
||||
return isar.transactions.getByTxidWalletId(txid, walletId);
|
||||
}
|
||||
|
||||
// utxos
|
||||
QueryBuilder<UTXO, UTXO, QAfterWhereClause> getUTXOs(String walletId) =>
|
||||
isar.utxos.where().walletIdEqualTo(walletId);
|
||||
|
|
|
@ -4,6 +4,7 @@ import 'dart:io';
|
|||
import 'package:connectivity_plus/connectivity_plus.dart';
|
||||
import 'package:decimal/decimal.dart';
|
||||
import 'package:stackwallet/electrumx_rpc/rpc.dart';
|
||||
import 'package:stackwallet/exceptions/electrumx/no_such_transaction.dart';
|
||||
import 'package:stackwallet/utilities/logger.dart';
|
||||
import 'package:stackwallet/utilities/prefs.dart';
|
||||
import 'package:uuid/uuid.dart';
|
||||
|
@ -132,7 +133,17 @@ class ElectrumX {
|
|||
final response = await _rpcClient!.request(jsonRequestString);
|
||||
|
||||
if (response["error"] != null) {
|
||||
throw Exception("JSONRPC response error: $response");
|
||||
if (response["error"]
|
||||
.toString()
|
||||
.contains("No such mempool or blockchain transaction")) {
|
||||
throw NoSuchTransactionException(
|
||||
"No such mempool or blockchain transaction",
|
||||
args.first.toString(),
|
||||
);
|
||||
}
|
||||
|
||||
throw Exception(
|
||||
"JSONRPC response \ncommand: $command \nargs: $args \nerror: $response");
|
||||
}
|
||||
|
||||
currentFailoverIndex = -1;
|
||||
|
@ -544,6 +555,10 @@ class ElectrumX {
|
|||
verbose,
|
||||
],
|
||||
);
|
||||
if (!verbose) {
|
||||
return {"rawtx": response["result"] as String};
|
||||
}
|
||||
|
||||
return Map<String, dynamic>.from(response["result"] as Map);
|
||||
} catch (e) {
|
||||
rethrow;
|
||||
|
|
5
lib/exceptions/address/address_exception.dart
Normal file
5
lib/exceptions/address/address_exception.dart
Normal file
|
@ -0,0 +1,5 @@
|
|||
import 'package:stackwallet/exceptions/sw_exception.dart';
|
||||
|
||||
class AddressException extends SWException {
|
||||
AddressException(super.message);
|
||||
}
|
7
lib/exceptions/electrumx/no_such_transaction.dart
Normal file
7
lib/exceptions/electrumx/no_such_transaction.dart
Normal file
|
@ -0,0 +1,7 @@
|
|||
import 'package:stackwallet/exceptions/sw_exception.dart';
|
||||
|
||||
class NoSuchTransactionException extends SWException {
|
||||
final String txid;
|
||||
|
||||
NoSuchTransactionException(super.message, this.txid);
|
||||
}
|
11
lib/exceptions/sw_exception.dart
Normal file
11
lib/exceptions/sw_exception.dart
Normal file
|
@ -0,0 +1,11 @@
|
|||
// generic stack wallet exception which all other custom exceptions should
|
||||
// extend from
|
||||
|
||||
class SWException with Exception {
|
||||
SWException(this.message);
|
||||
|
||||
final String message;
|
||||
|
||||
@override
|
||||
toString() => message;
|
||||
}
|
|
@ -0,0 +1,5 @@
|
|||
import 'package:stackwallet/exceptions/sw_exception.dart';
|
||||
|
||||
class InsufficientBalanceException extends SWException {
|
||||
InsufficientBalanceException(super.message);
|
||||
}
|
5
lib/exceptions/wallet/paynym_send_exception.dart
Normal file
5
lib/exceptions/wallet/paynym_send_exception.dart
Normal file
|
@ -0,0 +1,5 @@
|
|||
import 'package:stackwallet/exceptions/sw_exception.dart';
|
||||
|
||||
class PaynymSendException extends SWException {
|
||||
PaynymSendException(super.message);
|
||||
}
|
|
@ -254,6 +254,7 @@ class _MaterialAppWithThemeState extends ConsumerState<MaterialAppWithTheme>
|
|||
_desktopHasPassword =
|
||||
await ref.read(storageCryptoHandlerProvider).hasPassword();
|
||||
}
|
||||
await MainDB.instance.initMainDB();
|
||||
}
|
||||
|
||||
Future<void> load() async {
|
||||
|
@ -267,8 +268,6 @@ class _MaterialAppWithThemeState extends ConsumerState<MaterialAppWithTheme>
|
|||
await loadShared();
|
||||
}
|
||||
|
||||
await MainDB.instance.initMainDB();
|
||||
|
||||
_notificationsService = ref.read(notificationsProvider);
|
||||
_nodeService = ref.read(nodeServiceChangeNotifierProvider);
|
||||
_tradesService = ref.read(tradesServiceProvider);
|
||||
|
|
|
@ -1,14 +1,10 @@
|
|||
import 'package:isar/isar.dart';
|
||||
import 'package:stackwallet/exceptions/address/address_exception.dart';
|
||||
import 'package:stackwallet/models/isar/models/address/crypto_currency_address.dart';
|
||||
import 'package:stackwallet/models/isar/models/blockchain_data/transaction.dart';
|
||||
import 'package:stackwallet/services/coins/coin_paynym_extension.dart';
|
||||
|
||||
part 'address.g.dart';
|
||||
|
||||
class AddressException extends SWException {
|
||||
AddressException(super.message);
|
||||
}
|
||||
|
||||
@Collection(accessor: "addresses")
|
||||
class Address extends CryptoCurrencyAddress {
|
||||
Address({
|
||||
|
|
|
@ -5,16 +5,17 @@ import 'package:flutter/services.dart';
|
|||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:qr_flutter/qr_flutter.dart';
|
||||
import 'package:stackwallet/exceptions/wallet/insufficient_balance_exception.dart';
|
||||
import 'package:stackwallet/models/paynym/paynym_account_lite.dart';
|
||||
import 'package:stackwallet/notifications/show_flush_bar.dart';
|
||||
import 'package:stackwallet/pages/paynym/dialogs/confirm_paynym_connect_dialog.dart';
|
||||
import 'package:stackwallet/pages/paynym/paynym_home_view.dart';
|
||||
import 'package:stackwallet/pages/paynym/subwidgets/paynym_bot.dart';
|
||||
import 'package:stackwallet/pages/send_view/confirm_transaction_view.dart';
|
||||
import 'package:stackwallet/pages/send_view/send_view.dart';
|
||||
import 'package:stackwallet/providers/global/wallets_provider.dart';
|
||||
import 'package:stackwallet/route_generator.dart';
|
||||
import 'package:stackwallet/services/coins/coin_paynym_extension.dart';
|
||||
import 'package:stackwallet/services/coins/dogecoin/dogecoin_wallet.dart';
|
||||
import 'package:stackwallet/services/mixins/paynym_wallet_interface.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
|
@ -25,6 +26,7 @@ import 'package:stackwallet/widgets/desktop/primary_button.dart';
|
|||
import 'package:stackwallet/widgets/desktop/secondary_button.dart';
|
||||
import 'package:stackwallet/widgets/loading_indicator.dart';
|
||||
import 'package:stackwallet/widgets/rounded_container.dart';
|
||||
import 'package:tuple/tuple.dart';
|
||||
|
||||
class PaynymDetailsPopup extends ConsumerStatefulWidget {
|
||||
const PaynymDetailsPopup({
|
||||
|
@ -43,6 +45,19 @@ class PaynymDetailsPopup extends ConsumerStatefulWidget {
|
|||
class _PaynymDetailsPopupState extends ConsumerState<PaynymDetailsPopup> {
|
||||
bool _showInsufficientFundsInfo = false;
|
||||
|
||||
Future<void> _onSend() async {
|
||||
final manager =
|
||||
ref.read(walletsChangeNotifierProvider).getManager(widget.walletId);
|
||||
await Navigator.of(context).pushNamed(
|
||||
SendView.routeName,
|
||||
arguments: Tuple3(
|
||||
manager.walletId,
|
||||
manager.coin,
|
||||
widget.accountLite,
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
Future<void> _onConnectPressed() async {
|
||||
bool canPop = false;
|
||||
unawaited(
|
||||
|
@ -57,30 +72,24 @@ class _PaynymDetailsPopupState extends ConsumerState<PaynymDetailsPopup> {
|
|||
),
|
||||
);
|
||||
|
||||
final wallet = ref
|
||||
.read(walletsChangeNotifierProvider)
|
||||
.getManager(widget.walletId)
|
||||
.wallet as DogecoinWallet;
|
||||
final manager =
|
||||
ref.read(walletsChangeNotifierProvider).getManager(widget.walletId);
|
||||
|
||||
// sanity check to prevent second notifcation tx
|
||||
if (wallet.hasConnectedConfirmed(widget.accountLite.code)) {
|
||||
canPop = true;
|
||||
Navigator.of(context).pop();
|
||||
// TODO show info popup
|
||||
return;
|
||||
} else if (wallet.hasConnected(widget.accountLite.code)) {
|
||||
final wallet = manager.wallet as PaynymWalletInterface;
|
||||
|
||||
if (await wallet.hasConnected(widget.accountLite.code)) {
|
||||
canPop = true;
|
||||
Navigator.of(context).pop();
|
||||
// TODO show info popup
|
||||
return;
|
||||
}
|
||||
|
||||
final rates = await wallet.fees;
|
||||
final rates = await manager.fees;
|
||||
|
||||
Map<String, dynamic> preparedTx;
|
||||
|
||||
try {
|
||||
preparedTx = await wallet.buildNotificationTx(
|
||||
preparedTx = await wallet.prepareNotificationTx(
|
||||
selectedTxFeeRate: rates.medium,
|
||||
targetPaymentCodeString: widget.accountLite.code,
|
||||
);
|
||||
|
@ -117,7 +126,7 @@ class _PaynymDetailsPopupState extends ConsumerState<PaynymDetailsPopup> {
|
|||
Navigator.of(context).push(
|
||||
RouteGenerator.getRoute(
|
||||
builder: (_) => ConfirmTransactionView(
|
||||
walletId: wallet.walletId,
|
||||
walletId: manager.walletId,
|
||||
routeOnSuccessName: PaynymHomeView.routeName,
|
||||
isPaynymNotificationTransaction: true,
|
||||
transactionInfo: {
|
||||
|
@ -133,7 +142,7 @@ class _PaynymDetailsPopupState extends ConsumerState<PaynymDetailsPopup> {
|
|||
);
|
||||
},
|
||||
amount: (preparedTx["amount"] as int) + (preparedTx["fee"] as int),
|
||||
coin: wallet.coin,
|
||||
coin: manager.coin,
|
||||
),
|
||||
);
|
||||
}
|
||||
|
@ -141,6 +150,11 @@ class _PaynymDetailsPopupState extends ConsumerState<PaynymDetailsPopup> {
|
|||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
final manager = ref.watch(walletsChangeNotifierProvider
|
||||
.select((value) => value.getManager(widget.walletId)));
|
||||
|
||||
final wallet = manager.wallet as PaynymWalletInterface;
|
||||
|
||||
return DesktopDialog(
|
||||
maxWidth: MediaQuery.of(context).size.width - 32,
|
||||
maxHeight: double.infinity,
|
||||
|
@ -173,20 +187,51 @@ class _PaynymDetailsPopupState extends ConsumerState<PaynymDetailsPopup> {
|
|||
),
|
||||
],
|
||||
),
|
||||
PrimaryButton(
|
||||
label: "Connect",
|
||||
buttonHeight: ButtonHeight.l,
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.circlePlusFilled,
|
||||
width: 10,
|
||||
height: 10,
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.buttonTextPrimary,
|
||||
),
|
||||
iconSpacing: 4,
|
||||
width: 86,
|
||||
onPressed: _onConnectPressed,
|
||||
FutureBuilder(
|
||||
future: wallet.hasConnected(widget.accountLite.code),
|
||||
builder: (context, AsyncSnapshot<bool> snapshot) {
|
||||
if (snapshot.connectionState == ConnectionState.done &&
|
||||
snapshot.hasData) {
|
||||
if (snapshot.data!) {
|
||||
return PrimaryButton(
|
||||
label: "Send",
|
||||
buttonHeight: ButtonHeight.l,
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.circleArrowUpRight,
|
||||
width: 10,
|
||||
height: 10,
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.buttonTextPrimary,
|
||||
),
|
||||
iconSpacing: 4,
|
||||
width: 86,
|
||||
onPressed: _onSend,
|
||||
);
|
||||
} else {
|
||||
return PrimaryButton(
|
||||
label: "Connect",
|
||||
buttonHeight: ButtonHeight.l,
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.circlePlusFilled,
|
||||
width: 10,
|
||||
height: 10,
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.buttonTextPrimary,
|
||||
),
|
||||
iconSpacing: 4,
|
||||
width: 86,
|
||||
onPressed: _onConnectPressed,
|
||||
);
|
||||
}
|
||||
} else {
|
||||
return const SizedBox(
|
||||
height: 32,
|
||||
child: LoadingIndicator(),
|
||||
);
|
||||
}
|
||||
},
|
||||
),
|
||||
],
|
||||
),
|
||||
|
|
|
@ -9,9 +9,9 @@ import 'package:stackwallet/pages/wallet_view/wallet_view.dart';
|
|||
import 'package:stackwallet/providers/global/paynym_api_provider.dart';
|
||||
import 'package:stackwallet/providers/global/wallets_provider.dart';
|
||||
import 'package:stackwallet/providers/wallet/my_paynym_account_state_provider.dart';
|
||||
import 'package:stackwallet/services/coins/coin_paynym_extension.dart';
|
||||
import 'package:stackwallet/services/coins/dogecoin/dogecoin_wallet.dart';
|
||||
import 'package:stackwallet/services/mixins/paynym_wallet_interface.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/enums/derive_path_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
import 'package:stackwallet/utilities/util.dart';
|
||||
|
@ -159,16 +159,18 @@ class _PaynymClaimViewState extends ConsumerState<PaynymClaimView> {
|
|||
).then((value) => shouldCancel = value == true),
|
||||
);
|
||||
|
||||
// get wallet to access paynym calls
|
||||
final wallet = ref
|
||||
final manager = ref
|
||||
.read(walletsChangeNotifierProvider)
|
||||
.getManager(widget.walletId)
|
||||
.wallet as DogecoinWallet;
|
||||
.getManager(widget.walletId);
|
||||
|
||||
// get wallet to access paynym calls
|
||||
final wallet = manager.wallet as PaynymWalletInterface;
|
||||
|
||||
if (shouldCancel) return;
|
||||
|
||||
// get payment code
|
||||
final pCode = await wallet.getPaymentCode();
|
||||
final pCode = await wallet.getPaymentCode(
|
||||
DerivePathTypeExt.primaryFor(manager.coin));
|
||||
|
||||
if (shouldCancel) return;
|
||||
|
||||
|
|
|
@ -5,14 +5,14 @@ import 'package:flutter/services.dart';
|
|||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:qr_flutter/qr_flutter.dart';
|
||||
import 'package:stackwallet/exceptions/wallet/insufficient_balance_exception.dart';
|
||||
import 'package:stackwallet/models/paynym/paynym_account_lite.dart';
|
||||
import 'package:stackwallet/notifications/show_flush_bar.dart';
|
||||
import 'package:stackwallet/pages/paynym/dialogs/confirm_paynym_connect_dialog.dart';
|
||||
import 'package:stackwallet/pages/paynym/subwidgets/paynym_bot.dart';
|
||||
import 'package:stackwallet/pages/send_view/confirm_transaction_view.dart';
|
||||
import 'package:stackwallet/providers/global/wallets_provider.dart';
|
||||
import 'package:stackwallet/services/coins/coin_paynym_extension.dart';
|
||||
import 'package:stackwallet/services/coins/dogecoin/dogecoin_wallet.dart';
|
||||
import 'package:stackwallet/services/mixins/paynym_wallet_interface.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
|
@ -57,30 +57,24 @@ class _PaynymDetailsPopupState extends ConsumerState<DesktopPaynymDetails> {
|
|||
),
|
||||
);
|
||||
|
||||
final wallet = ref
|
||||
.read(walletsChangeNotifierProvider)
|
||||
.getManager(widget.walletId)
|
||||
.wallet as DogecoinWallet;
|
||||
final manager =
|
||||
ref.read(walletsChangeNotifierProvider).getManager(widget.walletId);
|
||||
|
||||
// sanity check to prevent second notification tx
|
||||
if (wallet.hasConnectedConfirmed(widget.accountLite.code)) {
|
||||
canPop = true;
|
||||
Navigator.of(context, rootNavigator: true).pop();
|
||||
// TODO show info popup
|
||||
return;
|
||||
} else if (wallet.hasConnected(widget.accountLite.code)) {
|
||||
final wallet = manager.wallet as PaynymWalletInterface;
|
||||
|
||||
if (await wallet.hasConnected(widget.accountLite.code)) {
|
||||
canPop = true;
|
||||
Navigator.of(context, rootNavigator: true).pop();
|
||||
// TODO show info popup
|
||||
return;
|
||||
}
|
||||
|
||||
final rates = await wallet.fees;
|
||||
final rates = await manager.fees;
|
||||
|
||||
Map<String, dynamic> preparedTx;
|
||||
|
||||
try {
|
||||
preparedTx = await wallet.buildNotificationTx(
|
||||
preparedTx = await wallet.prepareNotificationTx(
|
||||
selectedTxFeeRate: rates.medium,
|
||||
targetPaymentCodeString: widget.accountLite.code,
|
||||
);
|
||||
|
@ -118,7 +112,7 @@ class _PaynymDetailsPopupState extends ConsumerState<DesktopPaynymDetails> {
|
|||
maxHeight: double.infinity,
|
||||
maxWidth: 580,
|
||||
child: ConfirmTransactionView(
|
||||
walletId: wallet.walletId,
|
||||
walletId: manager.walletId,
|
||||
isPaynymNotificationTransaction: true,
|
||||
transactionInfo: {
|
||||
"hex": preparedTx["hex"],
|
||||
|
@ -147,7 +141,7 @@ class _PaynymDetailsPopupState extends ConsumerState<DesktopPaynymDetails> {
|
|||
);
|
||||
},
|
||||
amount: (preparedTx["amount"] as int) + (preparedTx["fee"] as int),
|
||||
coin: wallet.coin,
|
||||
coin: manager.coin,
|
||||
),
|
||||
);
|
||||
}
|
||||
|
@ -159,10 +153,11 @@ class _PaynymDetailsPopupState extends ConsumerState<DesktopPaynymDetails> {
|
|||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
final wallet = ref
|
||||
.watch(walletsChangeNotifierProvider)
|
||||
.getManager(widget.walletId)
|
||||
.wallet as DogecoinWallet;
|
||||
final manager = ref.watch(walletsChangeNotifierProvider
|
||||
.select((value) => value.getManager(widget.walletId)));
|
||||
|
||||
final wallet = manager.wallet as PaynymWalletInterface;
|
||||
|
||||
return RoundedWhiteContainer(
|
||||
padding: const EdgeInsets.all(0),
|
||||
child: Column(
|
||||
|
@ -192,40 +187,53 @@ class _PaynymDetailsPopupState extends ConsumerState<DesktopPaynymDetails> {
|
|||
),
|
||||
Row(
|
||||
children: [
|
||||
if (!wallet.hasConnected(widget.accountLite.code))
|
||||
Expanded(
|
||||
child: PrimaryButton(
|
||||
label: "Connect",
|
||||
buttonHeight: ButtonHeight.s,
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.circlePlusFilled,
|
||||
width: 16,
|
||||
height: 16,
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.buttonTextPrimary,
|
||||
),
|
||||
iconSpacing: 6,
|
||||
onPressed: _onConnectPressed,
|
||||
),
|
||||
),
|
||||
if (wallet.hasConnected(widget.accountLite.code))
|
||||
Expanded(
|
||||
child: PrimaryButton(
|
||||
label: "Send",
|
||||
buttonHeight: ButtonHeight.s,
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.circleArrowUpRight,
|
||||
width: 16,
|
||||
height: 16,
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.buttonTextPrimary,
|
||||
),
|
||||
iconSpacing: 6,
|
||||
onPressed: _onSend,
|
||||
),
|
||||
Expanded(
|
||||
child: FutureBuilder(
|
||||
future: wallet.hasConnected(widget.accountLite.code),
|
||||
builder: (context, AsyncSnapshot<bool> snapshot) {
|
||||
if (snapshot.connectionState ==
|
||||
ConnectionState.done &&
|
||||
snapshot.hasData) {
|
||||
if (snapshot.data!) {
|
||||
return PrimaryButton(
|
||||
label: "Send",
|
||||
buttonHeight: ButtonHeight.s,
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.circleArrowUpRight,
|
||||
width: 16,
|
||||
height: 16,
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.buttonTextPrimary,
|
||||
),
|
||||
iconSpacing: 6,
|
||||
onPressed: _onSend,
|
||||
);
|
||||
} else {
|
||||
return PrimaryButton(
|
||||
label: "Connect",
|
||||
buttonHeight: ButtonHeight.s,
|
||||
icon: SvgPicture.asset(
|
||||
Assets.svg.circlePlusFilled,
|
||||
width: 16,
|
||||
height: 16,
|
||||
color: Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.buttonTextPrimary,
|
||||
),
|
||||
iconSpacing: 6,
|
||||
onPressed: _onConnectPressed,
|
||||
);
|
||||
}
|
||||
} else {
|
||||
return const SizedBox(
|
||||
height: 100,
|
||||
child: LoadingIndicator(),
|
||||
);
|
||||
}
|
||||
},
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
width: 20,
|
||||
),
|
||||
|
|
|
@ -4,6 +4,7 @@ import 'package:decimal/decimal.dart';
|
|||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:stackwallet/models/paynym/paynym_account_lite.dart';
|
||||
import 'package:stackwallet/notifications/show_flush_bar.dart';
|
||||
import 'package:stackwallet/pages/pinpad_views/lock_screen_view.dart';
|
||||
import 'package:stackwallet/pages/send_view/sub_widgets/sending_transaction_dialog.dart';
|
||||
|
@ -12,10 +13,9 @@ import 'package:stackwallet/pages_desktop_specific/my_stack_view/wallet_view/sub
|
|||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/providers/wallet/public_private_balance_state_provider.dart';
|
||||
import 'package:stackwallet/route_generator.dart';
|
||||
import 'package:stackwallet/services/coins/coin_paynym_extension.dart';
|
||||
import 'package:stackwallet/services/coins/dogecoin/dogecoin_wallet.dart';
|
||||
import 'package:stackwallet/services/coins/epiccash/epiccash_wallet.dart';
|
||||
import 'package:stackwallet/services/coins/firo/firo_wallet.dart';
|
||||
import 'package:stackwallet/services/mixins/paynym_wallet_interface.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/constants.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
|
@ -92,11 +92,10 @@ class _ConfirmTransactionViewState
|
|||
try {
|
||||
String txid;
|
||||
if (widget.isPaynymNotificationTransaction) {
|
||||
txid = await (manager.wallet as DogecoinWallet)
|
||||
.confirmNotificationTx(preparedTx: transactionInfo);
|
||||
txid = await (manager.wallet as PaynymWalletInterface)
|
||||
.broadcastNotificationTx(preparedTx: transactionInfo);
|
||||
} else if (widget.isPaynymTransaction) {
|
||||
//
|
||||
throw UnimplementedError("paynym send not implemented yet");
|
||||
txid = await manager.confirmSend(txData: transactionInfo);
|
||||
} else {
|
||||
final coin = manager.coin;
|
||||
if ((coin == Coin.firo || coin == Coin.firoTestNet) &&
|
||||
|
@ -334,14 +333,20 @@ class _ConfirmTransactionViewState
|
|||
crossAxisAlignment: CrossAxisAlignment.stretch,
|
||||
children: [
|
||||
Text(
|
||||
"Recipient",
|
||||
widget.isPaynymTransaction
|
||||
? "PayNym recipient"
|
||||
: "Recipient",
|
||||
style: STextStyles.smallMed12(context),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 4,
|
||||
),
|
||||
Text(
|
||||
"${transactionInfo["address"] ?? "ERROR"}",
|
||||
widget.isPaynymTransaction
|
||||
? (transactionInfo["paynymAccountLite"]
|
||||
as PaynymAccountLite)
|
||||
.nymName
|
||||
: "${transactionInfo["address"] ?? "ERROR"}",
|
||||
style: STextStyles.itemSubtitle12(context),
|
||||
),
|
||||
],
|
||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -2,6 +2,9 @@ import 'package:flutter/material.dart';
|
|||
import 'package:flutter_svg/svg.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
import 'package:stackwallet/utilities/util.dart';
|
||||
import 'package:stackwallet/widgets/conditional_parent.dart';
|
||||
import 'package:stackwallet/widgets/desktop/desktop_dialog.dart';
|
||||
import 'package:stackwallet/widgets/stack_dialog.dart';
|
||||
|
||||
class RescanningDialog extends StatefulWidget {
|
||||
|
@ -21,9 +24,12 @@ class _RescanningDialogState extends State<RescanningDialog>
|
|||
late AnimationController? _spinController;
|
||||
late Animation<double> _spinAnimation;
|
||||
|
||||
late final bool isDesktop;
|
||||
|
||||
// late final VoidCallback onCancel;
|
||||
@override
|
||||
void initState() {
|
||||
isDesktop = Util.isDesktop;
|
||||
// onCancel = widget.onCancel;
|
||||
|
||||
_spinController = AnimationController(
|
||||
|
@ -53,33 +59,42 @@ class _RescanningDialogState extends State<RescanningDialog>
|
|||
onWillPop: () async {
|
||||
return false;
|
||||
},
|
||||
child: StackDialog(
|
||||
title: "Rescanning blockchain",
|
||||
message: "This may take a while. Please do not exit this screen.",
|
||||
icon: RotationTransition(
|
||||
turns: _spinAnimation,
|
||||
child: SvgPicture.asset(
|
||||
Assets.svg.arrowRotate3,
|
||||
width: 24,
|
||||
height: 24,
|
||||
color: Theme.of(context).extension<StackColors>()!.accentColorDark,
|
||||
),
|
||||
child: ConditionalParent(
|
||||
condition: isDesktop,
|
||||
builder: (child) => DesktopDialog(
|
||||
maxHeight: 200,
|
||||
maxWidth: 500,
|
||||
child: child,
|
||||
),
|
||||
child: StackDialog(
|
||||
title: "Rescanning blockchain",
|
||||
message: "This may take a while. Please do not exit this screen.",
|
||||
icon: RotationTransition(
|
||||
turns: _spinAnimation,
|
||||
child: SvgPicture.asset(
|
||||
Assets.svg.arrowRotate3,
|
||||
width: 24,
|
||||
height: 24,
|
||||
color:
|
||||
Theme.of(context).extension<StackColors>()!.accentColorDark,
|
||||
),
|
||||
),
|
||||
// rightButton: TextButton(
|
||||
// style: Theme.of(context).textButtonTheme.style?.copyWith(
|
||||
// backgroundColor: MaterialStateProperty.all<Color>(
|
||||
// CFColors.buttonGray,
|
||||
// ),
|
||||
// ),
|
||||
// child: Text(
|
||||
// "Cancel",
|
||||
// style: STextStyles.itemSubtitle12(context),
|
||||
// ),
|
||||
// onPressed: () {
|
||||
// Navigator.of(context).pop();
|
||||
// onCancel.call();
|
||||
// },
|
||||
// ),
|
||||
),
|
||||
// rightButton: TextButton(
|
||||
// style: Theme.of(context).textButtonTheme.style?.copyWith(
|
||||
// backgroundColor: MaterialStateProperty.all<Color>(
|
||||
// CFColors.buttonGray,
|
||||
// ),
|
||||
// ),
|
||||
// child: Text(
|
||||
// "Cancel",
|
||||
// style: STextStyles.itemSubtitle12(context),
|
||||
// ),
|
||||
// onPressed: () {
|
||||
// Navigator.of(context).pop();
|
||||
// onCancel.call();
|
||||
// },
|
||||
// ),
|
||||
),
|
||||
);
|
||||
}
|
||||
|
|
|
@ -76,6 +76,8 @@ class _WalletNetworkSettingsViewState
|
|||
StreamSubscription<dynamic>? _blocksRemainingSubscription;
|
||||
// late StreamSubscription _nodeStatusSubscription;
|
||||
|
||||
late final bool isDesktop;
|
||||
|
||||
late double _percent;
|
||||
late int _blocksRemaining;
|
||||
bool _advancedIsExpanded = false;
|
||||
|
@ -114,7 +116,7 @@ class _WalletNetworkSettingsViewState
|
|||
|
||||
if (mounted) {
|
||||
// pop rescanning dialog
|
||||
Navigator.pop(context);
|
||||
Navigator.of(context, rootNavigator: isDesktop).pop();
|
||||
|
||||
// show success
|
||||
await showDialog<dynamic>(
|
||||
|
@ -132,7 +134,7 @@ class _WalletNetworkSettingsViewState
|
|||
style: STextStyles.itemSubtitle12(context),
|
||||
),
|
||||
onPressed: () {
|
||||
Navigator.of(context).pop();
|
||||
Navigator.of(context, rootNavigator: isDesktop).pop();
|
||||
},
|
||||
),
|
||||
),
|
||||
|
@ -143,7 +145,7 @@ class _WalletNetworkSettingsViewState
|
|||
|
||||
if (mounted) {
|
||||
// pop rescanning dialog
|
||||
Navigator.pop(context);
|
||||
Navigator.of(context, rootNavigator: isDesktop).pop();
|
||||
|
||||
// show error
|
||||
await showDialog<dynamic>(
|
||||
|
@ -162,7 +164,7 @@ class _WalletNetworkSettingsViewState
|
|||
style: STextStyles.itemSubtitle12(context),
|
||||
),
|
||||
onPressed: () {
|
||||
Navigator.of(context).pop();
|
||||
Navigator.of(context, rootNavigator: isDesktop).pop();
|
||||
},
|
||||
),
|
||||
),
|
||||
|
@ -183,6 +185,7 @@ class _WalletNetworkSettingsViewState
|
|||
|
||||
@override
|
||||
void initState() {
|
||||
isDesktop = Util.isDesktop;
|
||||
_currentSyncStatus = widget.initialSyncStatus;
|
||||
// _currentNodeStatus = widget.initialNodeStatus;
|
||||
if (_currentSyncStatus == WalletSyncStatus.synced) {
|
||||
|
@ -270,7 +273,6 @@ class _WalletNetworkSettingsViewState
|
|||
@override
|
||||
Widget build(BuildContext context) {
|
||||
final screenWidth = MediaQuery.of(context).size.width;
|
||||
final bool isDesktop = Util.isDesktop;
|
||||
|
||||
final progressLength = isDesktop
|
||||
? 430.0
|
||||
|
|
|
@ -8,16 +8,16 @@ import 'package:stackwallet/pages/paynym/paynym_home_view.dart';
|
|||
import 'package:stackwallet/providers/global/paynym_api_provider.dart';
|
||||
import 'package:stackwallet/providers/global/wallets_provider.dart';
|
||||
import 'package:stackwallet/providers/wallet/my_paynym_account_state_provider.dart';
|
||||
import 'package:stackwallet/services/coins/coin_paynym_extension.dart';
|
||||
import 'package:stackwallet/services/coins/dogecoin/dogecoin_wallet.dart';
|
||||
import 'package:stackwallet/services/mixins/paynym_wallet_interface.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/derive_path_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/logger.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
import 'package:stackwallet/widgets/loading_indicator.dart';
|
||||
|
||||
class WalletNavigationBar extends StatefulWidget {
|
||||
class WalletNavigationBar extends ConsumerStatefulWidget {
|
||||
const WalletNavigationBar({
|
||||
Key? key,
|
||||
required this.onReceivePressed,
|
||||
|
@ -40,10 +40,11 @@ class WalletNavigationBar extends StatefulWidget {
|
|||
final String walletId;
|
||||
|
||||
@override
|
||||
State<WalletNavigationBar> createState() => _WalletNavigationBarState();
|
||||
ConsumerState<WalletNavigationBar> createState() =>
|
||||
_WalletNavigationBarState();
|
||||
}
|
||||
|
||||
class _WalletNavigationBarState extends State<WalletNavigationBar> {
|
||||
class _WalletNavigationBarState extends ConsumerState<WalletNavigationBar> {
|
||||
double scale = 0;
|
||||
final duration = const Duration(milliseconds: 200);
|
||||
|
||||
|
@ -61,41 +62,41 @@ class _WalletNavigationBarState extends State<WalletNavigationBar> {
|
|||
child: Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
AnimatedOpacity(
|
||||
opacity: scale,
|
||||
duration: duration,
|
||||
child: GestureDetector(
|
||||
onTap: () {},
|
||||
child: Container(
|
||||
padding: const EdgeInsets.all(16),
|
||||
width: 146,
|
||||
decoration: BoxDecoration(
|
||||
color:
|
||||
Theme.of(context).extension<StackColors>()!.popupBG,
|
||||
boxShadow: [
|
||||
Theme.of(context)
|
||||
.extension<StackColors>()!
|
||||
.standardBoxShadow
|
||||
],
|
||||
borderRadius: BorderRadius.circular(
|
||||
widget.height / 2.0,
|
||||
),
|
||||
),
|
||||
child: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.center,
|
||||
children: [
|
||||
Text(
|
||||
"Whirlpool",
|
||||
style: STextStyles.w600_12(context),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
const SizedBox(
|
||||
height: 8,
|
||||
),
|
||||
// AnimatedOpacity(
|
||||
// opacity: scale,
|
||||
// duration: duration,
|
||||
// child: GestureDetector(
|
||||
// onTap: () {},
|
||||
// child: Container(
|
||||
// padding: const EdgeInsets.all(16),
|
||||
// width: 146,
|
||||
// decoration: BoxDecoration(
|
||||
// color:
|
||||
// Theme.of(context).extension<StackColors>()!.popupBG,
|
||||
// boxShadow: [
|
||||
// Theme.of(context)
|
||||
// .extension<StackColors>()!
|
||||
// .standardBoxShadow
|
||||
// ],
|
||||
// borderRadius: BorderRadius.circular(
|
||||
// widget.height / 2.0,
|
||||
// ),
|
||||
// ),
|
||||
// child: Row(
|
||||
// mainAxisAlignment: MainAxisAlignment.center,
|
||||
// children: [
|
||||
// Text(
|
||||
// "Whirlpool",
|
||||
// style: STextStyles.w600_12(context),
|
||||
// ),
|
||||
// ],
|
||||
// ),
|
||||
// ),
|
||||
// ),
|
||||
// ),
|
||||
// const SizedBox(
|
||||
// height: 8,
|
||||
// ),
|
||||
AnimatedOpacity(
|
||||
opacity: scale,
|
||||
duration: duration,
|
||||
|
@ -114,13 +115,15 @@ class _WalletNavigationBarState extends State<WalletNavigationBar> {
|
|||
),
|
||||
);
|
||||
|
||||
// todo make generic and not doge specific
|
||||
final wallet = (ref
|
||||
final manager = ref
|
||||
.read(walletsChangeNotifierProvider)
|
||||
.getManager(widget.walletId)
|
||||
.wallet as DogecoinWallet);
|
||||
.getManager(widget.walletId);
|
||||
|
||||
final code = await wallet.getPaymentCode();
|
||||
final paynymInterface =
|
||||
manager.wallet as PaynymWalletInterface;
|
||||
|
||||
final code = await paynymInterface.getPaymentCode(
|
||||
DerivePathTypeExt.primaryFor(manager.coin));
|
||||
|
||||
final account = await ref
|
||||
.read(paynymAPIProvider)
|
||||
|
@ -357,7 +360,8 @@ class _WalletNavigationBarState extends State<WalletNavigationBar> {
|
|||
),
|
||||
),
|
||||
),
|
||||
if (widget.coin.hasPaynymSupport)
|
||||
if (ref.watch(walletsChangeNotifierProvider.select((value) =>
|
||||
value.getManager(widget.walletId).hasPaynymSupport)))
|
||||
RawMaterialButton(
|
||||
constraints: const BoxConstraints(
|
||||
minWidth: 66,
|
||||
|
|
|
@ -19,14 +19,14 @@ import 'package:stackwallet/providers/global/paynym_api_provider.dart';
|
|||
import 'package:stackwallet/providers/providers.dart';
|
||||
import 'package:stackwallet/providers/ui/transaction_filter_provider.dart';
|
||||
import 'package:stackwallet/providers/wallet/my_paynym_account_state_provider.dart';
|
||||
import 'package:stackwallet/services/coins/coin_paynym_extension.dart';
|
||||
import 'package:stackwallet/services/coins/dogecoin/dogecoin_wallet.dart';
|
||||
import 'package:stackwallet/services/coins/firo/firo_wallet.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/wallet_sync_status_changed_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/global_event_bus.dart';
|
||||
import 'package:stackwallet/services/mixins/paynym_wallet_interface.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/enums/backup_frequency_type.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/derive_path_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/logger.dart';
|
||||
import 'package:stackwallet/utilities/text_styles.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
|
@ -209,13 +209,13 @@ class _DesktopWalletViewState extends ConsumerState<DesktopWalletView> {
|
|||
),
|
||||
);
|
||||
|
||||
// todo make generic and not doge specific
|
||||
final wallet = (ref
|
||||
.read(walletsChangeNotifierProvider)
|
||||
.getManager(widget.walletId)
|
||||
.wallet as DogecoinWallet);
|
||||
final manager =
|
||||
ref.read(walletsChangeNotifierProvider).getManager(widget.walletId);
|
||||
|
||||
final code = await wallet.getPaymentCode();
|
||||
final wallet = manager.wallet as PaynymWalletInterface;
|
||||
|
||||
final code =
|
||||
await wallet.getPaymentCode(DerivePathTypeExt.primaryFor(manager.coin));
|
||||
|
||||
final account = await ref.read(paynymAPIProvider).nym(code.toString());
|
||||
|
||||
|
@ -445,7 +445,8 @@ class _DesktopWalletViewState extends ConsumerState<DesktopWalletView> {
|
|||
);
|
||||
},
|
||||
),
|
||||
if (coin.hasPaynymSupport)
|
||||
if (ref.watch(walletsChangeNotifierProvider.select((value) =>
|
||||
value.getManager(widget.walletId).hasPaynymSupport)))
|
||||
SecondaryButton(
|
||||
label: "PayNym",
|
||||
width: 160,
|
||||
|
|
|
@ -6,6 +6,7 @@ import 'package:stackwallet/models/buy/response_objects/quote.dart';
|
|||
import 'package:stackwallet/models/contact_address_entry.dart';
|
||||
import 'package:stackwallet/models/exchange/incomplete_exchange.dart';
|
||||
import 'package:stackwallet/models/exchange/response_objects/trade.dart';
|
||||
import 'package:stackwallet/models/paynym/paynym_account_lite.dart';
|
||||
import 'package:stackwallet/models/send_view_auto_fill_data.dart';
|
||||
import 'package:stackwallet/pages/add_wallet_views/add_wallet_view/add_wallet_view.dart';
|
||||
import 'package:stackwallet/pages/add_wallet_views/create_or_restore_wallet_view/create_or_restore_wallet_view.dart';
|
||||
|
@ -843,6 +844,18 @@ class RouteGenerator {
|
|||
name: settings.name,
|
||||
),
|
||||
);
|
||||
} else if (args is Tuple3<String, Coin, PaynymAccountLite>) {
|
||||
return getRoute(
|
||||
shouldUseMaterialRoute: useMaterialPageRoute,
|
||||
builder: (_) => SendView(
|
||||
walletId: args.item1,
|
||||
coin: args.item2,
|
||||
accountLite: args.item3,
|
||||
),
|
||||
settings: RouteSettings(
|
||||
name: settings.name,
|
||||
),
|
||||
);
|
||||
}
|
||||
return _routeError("${settings.name} invalid args: ${args.toString()}");
|
||||
|
||||
|
|
|
@ -13,16 +13,18 @@ import 'package:isar/isar.dart';
|
|||
import 'package:stackwallet/db/main_db.dart';
|
||||
import 'package:stackwallet/electrumx_rpc/cached_electrumx.dart';
|
||||
import 'package:stackwallet/electrumx_rpc/electrumx.dart';
|
||||
import 'package:stackwallet/exceptions/electrumx/no_such_transaction.dart';
|
||||
import 'package:stackwallet/models/balance.dart';
|
||||
import 'package:stackwallet/models/isar/models/isar_models.dart' as isar_models;
|
||||
import 'package:stackwallet/models/paymint/fee_object_model.dart';
|
||||
import 'package:stackwallet/services/coins/coin_paynym_extension.dart';
|
||||
import 'package:stackwallet/services/coins/coin_service.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/node_connection_status_changed_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/refresh_percent_changed_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/updated_in_background_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/wallet_sync_status_changed_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/global_event_bus.dart';
|
||||
import 'package:stackwallet/services/mixins/electrum_x_parsing.dart';
|
||||
import 'package:stackwallet/services/mixins/paynym_wallet_interface.dart';
|
||||
import 'package:stackwallet/services/mixins/wallet_cache.dart';
|
||||
import 'package:stackwallet/services/mixins/wallet_db.dart';
|
||||
import 'package:stackwallet/services/node_service.dart';
|
||||
|
@ -33,6 +35,7 @@ import 'package:stackwallet/utilities/assets.dart';
|
|||
import 'package:stackwallet/utilities/constants.dart';
|
||||
import 'package:stackwallet/utilities/default_nodes.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/derive_path_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/fee_rate_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/flutter_secure_storage_interface.dart';
|
||||
import 'package:stackwallet/utilities/format.dart';
|
||||
|
@ -50,8 +53,6 @@ const String GENESIS_HASH_MAINNET =
|
|||
const String GENESIS_HASH_TESTNET =
|
||||
"000000000933ea01ad0ee984209779baaec3ced90fa3f408719526f8d77f4943";
|
||||
|
||||
enum DerivePathType { bip44, bip49, bip84 }
|
||||
|
||||
bip32.BIP32 getBip32Node(
|
||||
int chain,
|
||||
int index,
|
||||
|
@ -138,7 +139,8 @@ bip32.BIP32 getBip32RootWrapper(Tuple2<String, NetworkType> args) {
|
|||
return getBip32Root(args.item1, args.item2);
|
||||
}
|
||||
|
||||
class BitcoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
||||
class BitcoinWallet extends CoinServiceAPI
|
||||
with WalletCache, WalletDB, ElectrumXParsing, PaynymWalletInterface {
|
||||
static const integrationTestFlag =
|
||||
bool.fromEnvironment("IS_INTEGRATION_TEST");
|
||||
|
||||
|
@ -178,8 +180,16 @@ class BitcoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
Future<List<isar_models.UTXO>> get utxos => db.getUTXOs(walletId).findAll();
|
||||
|
||||
@override
|
||||
Future<List<isar_models.Transaction>> get transactions =>
|
||||
db.getTransactions(walletId).sortByTimestampDesc().findAll();
|
||||
Future<List<isar_models.Transaction>> get transactions => db
|
||||
.getTransactions(walletId)
|
||||
.filter()
|
||||
.not()
|
||||
.group((q) => q
|
||||
.subTypeEqualTo(isar_models.TransactionSubType.bip47Notification)
|
||||
.and()
|
||||
.typeEqualTo(isar_models.TransactionType.incoming))
|
||||
.sortByTimestampDesc()
|
||||
.findAll();
|
||||
|
||||
@override
|
||||
Future<String> get currentReceivingAddress async =>
|
||||
|
@ -193,7 +203,7 @@ class BitcoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
.subTypeEqualTo(isar_models.AddressSubType.receiving)
|
||||
.sortByDerivationIndexDesc()
|
||||
.findFirst()) ??
|
||||
await _generateAddressForChain(0, 0, DerivePathType.bip84);
|
||||
await _generateAddressForChain(0, 0, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
Future<String> get currentChangeAddress async =>
|
||||
(await _currentChangeAddress).value;
|
||||
|
@ -206,7 +216,7 @@ class BitcoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
.subTypeEqualTo(isar_models.AddressSubType.change)
|
||||
.sortByDerivationIndexDesc()
|
||||
.findFirst()) ??
|
||||
await _generateAddressForChain(1, 0, DerivePathType.bip84);
|
||||
await _generateAddressForChain(1, 0, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
@override
|
||||
Future<void> exit() async {
|
||||
|
@ -673,6 +683,18 @@ class BitcoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
...p2shChangeAddressArray,
|
||||
]);
|
||||
|
||||
// generate to ensure notification address is in db before refreshing transactions
|
||||
await getMyNotificationAddress(DerivePathType.bip44);
|
||||
|
||||
// refresh transactions to pick up any received notification transactions
|
||||
await _refreshTransactions();
|
||||
|
||||
// restore paynym transactions
|
||||
await restoreAllHistory(
|
||||
maxUnusedAddressGap: maxUnusedAddressGap,
|
||||
maxNumberOfIndexesToCheck: maxNumberOfIndexesToCheck,
|
||||
);
|
||||
|
||||
await _updateUTXOs();
|
||||
|
||||
await Future.wait([
|
||||
|
@ -737,6 +759,13 @@ class BitcoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
}
|
||||
}
|
||||
return needsRefresh;
|
||||
} on NoSuchTransactionException catch (e) {
|
||||
// TODO: move direct transactions elsewhere
|
||||
await db.isar.writeTxn(() async {
|
||||
await db.isar.transactions.deleteByTxidWalletId(e.txid, walletId);
|
||||
});
|
||||
await txTracker.deleteTransaction(e.txid);
|
||||
return true;
|
||||
} catch (e, s) {
|
||||
Logging.instance.log(
|
||||
"Exception caught in refreshIfThereIsNewData: $e\n$s",
|
||||
|
@ -906,6 +935,8 @@ class BitcoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
GlobalEventBus.instance.fire(RefreshPercentChangedEvent(0.3, walletId));
|
||||
await _checkCurrentReceivingAddressesForTransactions();
|
||||
|
||||
await checkAllCurrentReceivingPaynymAddressesForTransactions();
|
||||
|
||||
final fetchFuture = _refreshTransactions();
|
||||
final utxosRefreshFuture = _updateUTXOs();
|
||||
GlobalEventBus.instance
|
||||
|
@ -1264,6 +1295,26 @@ class BitcoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
_secureStore = secureStore;
|
||||
initCache(walletId, coin);
|
||||
initWalletDB(mockableOverride: mockableOverride);
|
||||
initPaynymWalletInterface(
|
||||
walletId: walletId,
|
||||
walletName: walletName,
|
||||
network: _network,
|
||||
coin: coin,
|
||||
db: db,
|
||||
electrumXClient: electrumXClient,
|
||||
secureStorage: secureStore,
|
||||
getMnemonic: () => mnemonic,
|
||||
getChainHeight: () => chainHeight,
|
||||
getCurrentChangeAddress: () => currentChangeAddress,
|
||||
estimateTxFee: estimateTxFee,
|
||||
prepareSend: prepareSend,
|
||||
getTxCount: getTxCount,
|
||||
fetchBuildTxData: fetchBuildTxData,
|
||||
refresh: refresh,
|
||||
checkChangeAddressForTransactions: _checkChangeAddressForTransactions,
|
||||
addDerivation: addDerivation,
|
||||
addDerivations: addDerivations,
|
||||
);
|
||||
}
|
||||
|
||||
@override
|
||||
|
@ -1324,62 +1375,11 @@ class BitcoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
.getAddresses(walletId)
|
||||
.filter()
|
||||
.not()
|
||||
.typeEqualTo(isar_models.AddressType.unknown)
|
||||
.and()
|
||||
.not()
|
||||
.typeEqualTo(isar_models.AddressType.nonWallet)
|
||||
.and()
|
||||
.group((q) => q
|
||||
.subTypeEqualTo(isar_models.AddressSubType.receiving)
|
||||
.or()
|
||||
.subTypeEqualTo(isar_models.AddressSubType.change))
|
||||
.not()
|
||||
.subTypeEqualTo(isar_models.AddressSubType.nonWallet)
|
||||
.findAll();
|
||||
// final List<String> allAddresses = [];
|
||||
// final receivingAddresses = DB.instance.get<dynamic>(
|
||||
// boxName: walletId, key: 'receivingAddressesP2WPKH') as List<dynamic>;
|
||||
// final changeAddresses = DB.instance.get<dynamic>(
|
||||
// boxName: walletId, key: 'changeAddressesP2WPKH') as List<dynamic>;
|
||||
// final receivingAddressesP2PKH = DB.instance.get<dynamic>(
|
||||
// boxName: walletId, key: 'receivingAddressesP2PKH') as List<dynamic>;
|
||||
// final changeAddressesP2PKH =
|
||||
// DB.instance.get<dynamic>(boxName: walletId, key: 'changeAddressesP2PKH')
|
||||
// as List<dynamic>;
|
||||
// final receivingAddressesP2SH = DB.instance.get<dynamic>(
|
||||
// boxName: walletId, key: 'receivingAddressesP2SH') as List<dynamic>;
|
||||
// final changeAddressesP2SH =
|
||||
// DB.instance.get<dynamic>(boxName: walletId, key: 'changeAddressesP2SH')
|
||||
// as List<dynamic>;
|
||||
//
|
||||
// for (var i = 0; i < receivingAddresses.length; i++) {
|
||||
// if (!allAddresses.contains(receivingAddresses[i])) {
|
||||
// allAddresses.add(receivingAddresses[i] as String);
|
||||
// }
|
||||
// }
|
||||
// for (var i = 0; i < changeAddresses.length; i++) {
|
||||
// if (!allAddresses.contains(changeAddresses[i])) {
|
||||
// allAddresses.add(changeAddresses[i] as String);
|
||||
// }
|
||||
// }
|
||||
// for (var i = 0; i < receivingAddressesP2PKH.length; i++) {
|
||||
// if (!allAddresses.contains(receivingAddressesP2PKH[i])) {
|
||||
// allAddresses.add(receivingAddressesP2PKH[i] as String);
|
||||
// }
|
||||
// }
|
||||
// for (var i = 0; i < changeAddressesP2PKH.length; i++) {
|
||||
// if (!allAddresses.contains(changeAddressesP2PKH[i])) {
|
||||
// allAddresses.add(changeAddressesP2PKH[i] as String);
|
||||
// }
|
||||
// }
|
||||
// for (var i = 0; i < receivingAddressesP2SH.length; i++) {
|
||||
// if (!allAddresses.contains(receivingAddressesP2SH[i])) {
|
||||
// allAddresses.add(receivingAddressesP2SH[i] as String);
|
||||
// }
|
||||
// }
|
||||
// for (var i = 0; i < changeAddressesP2SH.length; i++) {
|
||||
// if (!allAddresses.contains(changeAddressesP2SH[i])) {
|
||||
// allAddresses.add(changeAddressesP2SH[i] as String);
|
||||
// }
|
||||
// }
|
||||
return allAddresses;
|
||||
}
|
||||
|
||||
|
@ -1754,15 +1754,34 @@ class BitcoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
coin: coin,
|
||||
);
|
||||
|
||||
// todo check here if we should mark as blocked
|
||||
// fetch stored tx to see if paynym notification tx and block utxo
|
||||
final storedTx = await db.getTransaction(
|
||||
walletId,
|
||||
fetchedUtxoList[i][j]["tx_hash"] as String,
|
||||
);
|
||||
|
||||
bool shouldBlock = false;
|
||||
String? blockReason;
|
||||
|
||||
if (storedTx?.subType ==
|
||||
isar_models.TransactionSubType.bip47Notification &&
|
||||
storedTx?.type == isar_models.TransactionType.incoming) {
|
||||
// probably safe to assume this is an incoming tx as it is a utxo
|
||||
// belonging to this wallet. The extra check may be redundant but
|
||||
// just in case...
|
||||
|
||||
shouldBlock = true;
|
||||
blockReason = "Incoming paynym notification transaction.";
|
||||
}
|
||||
|
||||
final utxo = isar_models.UTXO(
|
||||
walletId: walletId,
|
||||
txid: txn["txid"] as String,
|
||||
vout: fetchedUtxoList[i][j]["tx_pos"] as int,
|
||||
value: fetchedUtxoList[i][j]["value"] as int,
|
||||
name: "",
|
||||
isBlocked: false,
|
||||
blockedReason: null,
|
||||
isBlocked: shouldBlock,
|
||||
blockedReason: blockReason,
|
||||
isCoinbase: txn["is_coinbase"] as bool? ?? false,
|
||||
blockHash: txn["blockhash"] as String?,
|
||||
blockHeight: fetchedUtxoList[i][j]["height"] as int?,
|
||||
|
@ -1868,7 +1887,7 @@ class BitcoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
|
||||
// Use new index to derive a new receiving address
|
||||
final newReceivingAddress = await _generateAddressForChain(
|
||||
0, newReceivingIndex, DerivePathType.bip84);
|
||||
0, newReceivingIndex, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
final existing = await db
|
||||
.getAddresses(walletId)
|
||||
|
@ -1887,7 +1906,7 @@ class BitcoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
}
|
||||
} catch (e, s) {
|
||||
Logging.instance.log(
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathType.bip84}): $e\n$s",
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathTypeExt.primaryFor(coin)}): $e\n$s",
|
||||
level: LogLevel.Error);
|
||||
rethrow;
|
||||
}
|
||||
|
@ -1907,7 +1926,7 @@ class BitcoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
|
||||
// Use new index to derive a new change address
|
||||
final newChangeAddress = await _generateAddressForChain(
|
||||
1, newChangeIndex, DerivePathType.bip84);
|
||||
1, newChangeIndex, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
final existing = await db
|
||||
.getAddresses(walletId)
|
||||
|
@ -1926,12 +1945,12 @@ class BitcoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
}
|
||||
} on SocketException catch (se, s) {
|
||||
Logging.instance.log(
|
||||
"SocketException caught in _checkReceivingAddressForTransactions(${DerivePathType.bip84}): $se\n$s",
|
||||
"SocketException caught in _checkReceivingAddressForTransactions(${DerivePathTypeExt.primaryFor(coin)}): $se\n$s",
|
||||
level: LogLevel.Error);
|
||||
return;
|
||||
} catch (e, s) {
|
||||
Logging.instance.log(
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathType.bip84}): $e\n$s",
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathTypeExt.primaryFor(coin)}): $e\n$s",
|
||||
level: LogLevel.Error);
|
||||
rethrow;
|
||||
}
|
||||
|
@ -2269,7 +2288,7 @@ class BitcoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
utxoSigningData: utxoSigningData,
|
||||
recipients: [
|
||||
_recipientAddress,
|
||||
await _getCurrentAddressForChain(1, DerivePathType.bip84),
|
||||
await _getCurrentAddressForChain(1, DerivePathTypeExt.primaryFor(coin)),
|
||||
],
|
||||
satoshiAmounts: [
|
||||
satoshiAmountToSend,
|
||||
|
@ -2308,8 +2327,8 @@ class BitcoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
feeForTwoOutputs) {
|
||||
// generate new change address if current change address has been used
|
||||
await _checkChangeAddressForTransactions();
|
||||
final String newChangeAddress =
|
||||
await _getCurrentAddressForChain(1, DerivePathType.bip84);
|
||||
final String newChangeAddress = await _getCurrentAddressForChain(
|
||||
1, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
int feeBeingPaid =
|
||||
satoshisBeingUsed - satoshiAmountToSend - changeOutputSize;
|
||||
|
@ -3035,7 +3054,7 @@ class BitcoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
|
||||
// Use new index to derive a new receiving address
|
||||
final newReceivingAddress = await _generateAddressForChain(
|
||||
0, newReceivingIndex, DerivePathType.bip84);
|
||||
0, newReceivingIndex, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
// Add that new receiving address
|
||||
await db.putAddress(newReceivingAddress);
|
||||
|
|
|
@ -34,6 +34,7 @@ import 'package:stackwallet/utilities/assets.dart';
|
|||
import 'package:stackwallet/utilities/constants.dart';
|
||||
import 'package:stackwallet/utilities/default_nodes.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/derive_path_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/fee_rate_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/flutter_secure_storage_interface.dart';
|
||||
import 'package:stackwallet/utilities/format.dart';
|
||||
|
@ -50,8 +51,6 @@ const String GENESIS_HASH_MAINNET =
|
|||
const String GENESIS_HASH_TESTNET =
|
||||
"000000000933ea01ad0ee984209779baaec3ced90fa3f408719526f8d77f4943";
|
||||
|
||||
enum DerivePathType { bip44, bip49 }
|
||||
|
||||
bip32.BIP32 getBip32Node(int chain, int index, String mnemonic,
|
||||
NetworkType network, DerivePathType derivePathType) {
|
||||
final root = getBip32Root(mnemonic, network);
|
||||
|
@ -170,7 +169,7 @@ class BitcoinCashWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
.subTypeEqualTo(isar_models.AddressSubType.receiving)
|
||||
.sortByDerivationIndexDesc()
|
||||
.findFirst()) ??
|
||||
await _generateAddressForChain(0, 0, DerivePathType.bip44);
|
||||
await _generateAddressForChain(0, 0, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
Future<String> get currentChangeAddress async =>
|
||||
(await _currentChangeAddress).value;
|
||||
|
@ -183,7 +182,7 @@ class BitcoinCashWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
.subTypeEqualTo(isar_models.AddressSubType.change)
|
||||
.sortByDerivationIndexDesc()
|
||||
.findFirst()) ??
|
||||
await _generateAddressForChain(1, 0, DerivePathType.bip44);
|
||||
await _generateAddressForChain(1, 0, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
@override
|
||||
Future<void> exit() async {
|
||||
|
@ -1421,9 +1420,8 @@ class BitcoinCashWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
.address!;
|
||||
addrType = isar_models.AddressType.p2sh;
|
||||
break;
|
||||
// default:
|
||||
// // should never hit this due to all enum cases handled
|
||||
// return null;
|
||||
case DerivePathType.bip84:
|
||||
throw UnsupportedError("bip84 not supported by BCH");
|
||||
}
|
||||
|
||||
// add generated address & info to derivations
|
||||
|
@ -1466,6 +1464,8 @@ class BitcoinCashWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
case DerivePathType.bip49:
|
||||
type = isar_models.AddressType.p2sh;
|
||||
break;
|
||||
case DerivePathType.bip84:
|
||||
throw UnsupportedError("bip84 not supported by BCH");
|
||||
}
|
||||
|
||||
final address = await db
|
||||
|
@ -1491,6 +1491,8 @@ class BitcoinCashWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
case DerivePathType.bip49:
|
||||
key = "${walletId}_${chainId}DerivationsP2SH";
|
||||
break;
|
||||
case DerivePathType.bip84:
|
||||
throw UnsupportedError("bip84 not supported by BCH");
|
||||
}
|
||||
return key;
|
||||
}
|
||||
|
@ -1752,7 +1754,7 @@ class BitcoinCashWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
|
||||
// Use new index to derive a new receiving address
|
||||
final newReceivingAddress = await _generateAddressForChain(
|
||||
0, newReceivingIndex, DerivePathType.bip44);
|
||||
0, newReceivingIndex, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
final existing = await db
|
||||
.getAddresses(walletId)
|
||||
|
@ -1771,12 +1773,12 @@ class BitcoinCashWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
}
|
||||
} on SocketException catch (se, s) {
|
||||
Logging.instance.log(
|
||||
"SocketException caught in _checkReceivingAddressForTransactions(${DerivePathType.bip44}): $se\n$s",
|
||||
"SocketException caught in _checkReceivingAddressForTransactions(${DerivePathTypeExt.primaryFor(coin)}): $se\n$s",
|
||||
level: LogLevel.Error);
|
||||
return;
|
||||
} catch (e, s) {
|
||||
Logging.instance.log(
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathType.bip44}): $e\n$s",
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathTypeExt.primaryFor(coin)}): $e\n$s",
|
||||
level: LogLevel.Error);
|
||||
rethrow;
|
||||
}
|
||||
|
@ -1796,7 +1798,7 @@ class BitcoinCashWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
|
||||
// Use new index to derive a new change address
|
||||
final newChangeAddress = await _generateAddressForChain(
|
||||
1, newChangeIndex, DerivePathType.bip44);
|
||||
1, newChangeIndex, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
final existing = await db
|
||||
.getAddresses(walletId)
|
||||
|
@ -1815,12 +1817,12 @@ class BitcoinCashWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
}
|
||||
} on SocketException catch (se, s) {
|
||||
Logging.instance.log(
|
||||
"SocketException caught in _checkReceivingAddressForTransactions(${DerivePathType.bip44}): $se\n$s",
|
||||
"SocketException caught in _checkReceivingAddressForTransactions(${DerivePathTypeExt.primaryFor(coin)}): $se\n$s",
|
||||
level: LogLevel.Error);
|
||||
return;
|
||||
} catch (e, s) {
|
||||
Logging.instance.log(
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathType.bip44}): $e\n$s",
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathTypeExt.primaryFor(coin)}): $e\n$s",
|
||||
level: LogLevel.Error);
|
||||
rethrow;
|
||||
}
|
||||
|
@ -2346,7 +2348,7 @@ class BitcoinCashWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
utxoSigningData: utxoSigningData,
|
||||
recipients: [
|
||||
_recipientAddress,
|
||||
await _getCurrentAddressForChain(1, DerivePathType.bip44),
|
||||
await _getCurrentAddressForChain(1, DerivePathTypeExt.primaryFor(coin)),
|
||||
],
|
||||
satoshiAmounts: [
|
||||
satoshiAmountToSend,
|
||||
|
@ -2399,8 +2401,8 @@ class BitcoinCashWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
feeForTwoOutputs) {
|
||||
// generate new change address if current change address has been used
|
||||
await _checkChangeAddressForTransactions();
|
||||
final String newChangeAddress =
|
||||
await _getCurrentAddressForChain(1, DerivePathType.bip44);
|
||||
final String newChangeAddress = await _getCurrentAddressForChain(
|
||||
1, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
int feeBeingPaid =
|
||||
satoshisBeingUsed - satoshiAmountToSend - changeOutputSize;
|
||||
|
@ -2611,6 +2613,8 @@ class BitcoinCashWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
case DerivePathType.bip49:
|
||||
addressesP2SH.add(address);
|
||||
break;
|
||||
case DerivePathType.bip84:
|
||||
throw UnsupportedError("bip84 not supported by BCH");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -2997,7 +3001,7 @@ class BitcoinCashWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
|
||||
// Use new index to derive a new receiving address
|
||||
final newReceivingAddress = await _generateAddressForChain(
|
||||
0, newReceivingIndex, DerivePathType.bip44);
|
||||
0, newReceivingIndex, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
// Add that new receiving address
|
||||
await db.putAddress(newReceivingAddress);
|
||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -14,16 +14,17 @@ import 'package:isar/isar.dart';
|
|||
import 'package:stackwallet/db/main_db.dart';
|
||||
import 'package:stackwallet/electrumx_rpc/cached_electrumx.dart';
|
||||
import 'package:stackwallet/electrumx_rpc/electrumx.dart';
|
||||
import 'package:stackwallet/exceptions/electrumx/no_such_transaction.dart';
|
||||
import 'package:stackwallet/models/balance.dart';
|
||||
import 'package:stackwallet/models/isar/models/isar_models.dart' as isar_models;
|
||||
import 'package:stackwallet/models/paymint/fee_object_model.dart';
|
||||
import 'package:stackwallet/services/coins/coin_paynym_extension.dart';
|
||||
import 'package:stackwallet/services/coins/coin_service.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/node_connection_status_changed_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/refresh_percent_changed_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/updated_in_background_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/wallet_sync_status_changed_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/global_event_bus.dart';
|
||||
import 'package:stackwallet/services/mixins/electrum_x_parsing.dart';
|
||||
import 'package:stackwallet/services/mixins/wallet_cache.dart';
|
||||
import 'package:stackwallet/services/mixins/wallet_db.dart';
|
||||
import 'package:stackwallet/services/node_service.dart';
|
||||
|
@ -34,6 +35,7 @@ import 'package:stackwallet/utilities/assets.dart';
|
|||
import 'package:stackwallet/utilities/constants.dart';
|
||||
import 'package:stackwallet/utilities/default_nodes.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/derive_path_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/fee_rate_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/flutter_secure_storage_interface.dart';
|
||||
import 'package:stackwallet/utilities/format.dart';
|
||||
|
@ -50,8 +52,6 @@ const String GENESIS_HASH_MAINNET =
|
|||
const String GENESIS_HASH_TESTNET =
|
||||
"bb0a78264637406b6360aad926284d544d7049f45189db5664f3c4d07350559e";
|
||||
|
||||
enum DerivePathType { bip44 }
|
||||
|
||||
bip32.BIP32 getBip32Node(int chain, int index, String mnemonic,
|
||||
NetworkType network, DerivePathType derivePathType) {
|
||||
final root = getBip32Root(mnemonic, network);
|
||||
|
@ -90,7 +90,7 @@ bip32.BIP32 getBip32NodeFromRoot(
|
|||
case DerivePathType.bip44:
|
||||
return root.derivePath("m/44'/$coinType'/0'/$chain/$index");
|
||||
default:
|
||||
throw Exception("DerivePathType must not be null.");
|
||||
throw Exception("Unsupported DerivePathType");
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -125,7 +125,8 @@ bip32.BIP32 getBip32RootWrapper(Tuple2<String, NetworkType> args) {
|
|||
return getBip32Root(args.item1, args.item2);
|
||||
}
|
||||
|
||||
class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
||||
class DogecoinWallet extends CoinServiceAPI
|
||||
with WalletCache, WalletDB, ElectrumXParsing {
|
||||
static const integrationTestFlag =
|
||||
bool.fromEnvironment("IS_INTEGRATION_TEST");
|
||||
final _prefs = Prefs.instance;
|
||||
|
@ -150,8 +151,16 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
Future<List<isar_models.UTXO>> get utxos => db.getUTXOs(walletId).findAll();
|
||||
|
||||
@override
|
||||
Future<List<isar_models.Transaction>> get transactions =>
|
||||
db.getTransactions(walletId).sortByTimestampDesc().findAll();
|
||||
Future<List<isar_models.Transaction>> get transactions => db
|
||||
.getTransactions(walletId)
|
||||
.filter()
|
||||
.not()
|
||||
.group((q) => q
|
||||
.subTypeEqualTo(isar_models.TransactionSubType.bip47Notification)
|
||||
.and()
|
||||
.typeEqualTo(isar_models.TransactionType.incoming))
|
||||
.sortByTimestampDesc()
|
||||
.findAll();
|
||||
|
||||
@override
|
||||
Coin get coin => _coin;
|
||||
|
@ -168,7 +177,7 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
.subTypeEqualTo(isar_models.AddressSubType.receiving)
|
||||
.sortByDerivationIndexDesc()
|
||||
.findFirst()) ??
|
||||
await _generateAddressForChain(0, 0, DerivePathType.bip44);
|
||||
await _generateAddressForChain(0, 0, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
// @override
|
||||
Future<String> get currentChangeAddress async =>
|
||||
|
@ -182,7 +191,7 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
.subTypeEqualTo(isar_models.AddressSubType.change)
|
||||
.sortByDerivationIndexDesc()
|
||||
.findFirst()) ??
|
||||
await _generateAddressForChain(1, 0, DerivePathType.bip44);
|
||||
await _generateAddressForChain(1, 0, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
@override
|
||||
Future<void> exit() async {
|
||||
|
@ -529,6 +538,19 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
...p2pkhChangeAddressArray,
|
||||
]);
|
||||
|
||||
// paynym stuff
|
||||
// // generate to ensure notification address is in db before refreshing transactions
|
||||
// await getMyNotificationAddress(DerivePathType.bip44);
|
||||
//
|
||||
// // refresh transactions to pick up any received notification transactions
|
||||
// await _refreshTransactions();
|
||||
//
|
||||
// // restore paynym transactions
|
||||
// await restoreAllHistory(
|
||||
// maxUnusedAddressGap: maxUnusedAddressGap,
|
||||
// maxNumberOfIndexesToCheck: maxNumberOfIndexesToCheck,
|
||||
// );
|
||||
|
||||
await _updateUTXOs();
|
||||
|
||||
await Future.wait([
|
||||
|
@ -596,6 +618,13 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
}
|
||||
}
|
||||
return needsRefresh;
|
||||
} on NoSuchTransactionException catch (e) {
|
||||
// TODO: move direct transactions elsewhere
|
||||
await db.isar.writeTxn(() async {
|
||||
await db.isar.transactions.deleteByTxidWalletId(e.txid, walletId);
|
||||
});
|
||||
await txTracker.deleteTransaction(e.txid);
|
||||
return true;
|
||||
} catch (e, s) {
|
||||
Logging.instance.log(
|
||||
"Exception caught in refreshIfThereIsNewData: $e\n$s",
|
||||
|
@ -761,6 +790,9 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
GlobalEventBus.instance.fire(RefreshPercentChangedEvent(0.3, walletId));
|
||||
await _checkCurrentReceivingAddressesForTransactions();
|
||||
|
||||
// paynym stuff
|
||||
// await checkAllCurrentReceivingPaynymAddressesForTransactions();
|
||||
|
||||
final fetchFuture = _refreshTransactions();
|
||||
final utxosRefreshFuture = _updateUTXOs();
|
||||
GlobalEventBus.instance
|
||||
|
@ -1099,6 +1131,27 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
_secureStore = secureStore;
|
||||
initCache(walletId, coin);
|
||||
initWalletDB(mockableOverride: mockableOverride);
|
||||
|
||||
// paynym stuff
|
||||
// initPaynymWalletInterface(
|
||||
// walletId: walletId,
|
||||
// walletName: walletName,
|
||||
// network: network,
|
||||
// coin: coin,
|
||||
// db: db,
|
||||
// electrumXClient: electrumXClient,
|
||||
// getMnemonic: () => mnemonic,
|
||||
// getChainHeight: () => chainHeight,
|
||||
// getCurrentChangeAddress: () => currentChangeAddress,
|
||||
// estimateTxFee: estimateTxFee,
|
||||
// prepareSend: prepareSend,
|
||||
// getTxCount: getTxCount,
|
||||
// fetchBuildTxData: fetchBuildTxData,
|
||||
// refresh: refresh,
|
||||
// checkChangeAddressForTransactions: checkChangeAddressForTransactions,
|
||||
// addDerivation: addDerivation,
|
||||
// addDerivations: addDerivations,
|
||||
// );
|
||||
}
|
||||
|
||||
@override
|
||||
|
@ -1161,10 +1214,8 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
.not()
|
||||
.typeEqualTo(isar_models.AddressType.nonWallet)
|
||||
.and()
|
||||
.group((q) => q
|
||||
.subTypeEqualTo(isar_models.AddressSubType.receiving)
|
||||
.or()
|
||||
.subTypeEqualTo(isar_models.AddressSubType.change))
|
||||
.not()
|
||||
.subTypeEqualTo(isar_models.AddressSubType.nonWallet)
|
||||
.findAll();
|
||||
return allAddresses;
|
||||
}
|
||||
|
@ -1274,9 +1325,8 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
case DerivePathType.bip44:
|
||||
address = P2PKH(data: data, network: network).data.address!;
|
||||
break;
|
||||
// default:
|
||||
// // should never hit this due to all enum cases handled
|
||||
// return null;
|
||||
default:
|
||||
throw Exception("Unsupported DerivePathType");
|
||||
}
|
||||
|
||||
// add generated address & info to derivations
|
||||
|
@ -1321,6 +1371,8 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
.sortByDerivationIndexDesc()
|
||||
.findFirst();
|
||||
break;
|
||||
default:
|
||||
throw Exception("Unsupported DerivePathType");
|
||||
}
|
||||
return address!.value;
|
||||
}
|
||||
|
@ -1333,6 +1385,8 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
case DerivePathType.bip44:
|
||||
key = "${walletId}_${chainId}DerivationsP2PKH";
|
||||
break;
|
||||
default:
|
||||
throw Exception("Unsupported DerivePathType");
|
||||
}
|
||||
return key;
|
||||
}
|
||||
|
@ -1503,15 +1557,34 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
coin: coin,
|
||||
);
|
||||
|
||||
// todo check here if we should mark as blocked
|
||||
// fetch stored tx to see if paynym notification tx and block utxo
|
||||
final storedTx = await db.getTransaction(
|
||||
walletId,
|
||||
fetchedUtxoList[i][j]["tx_hash"] as String,
|
||||
);
|
||||
|
||||
bool shouldBlock = false;
|
||||
String? blockReason;
|
||||
|
||||
if (storedTx?.subType ==
|
||||
isar_models.TransactionSubType.bip47Notification &&
|
||||
storedTx?.type == isar_models.TransactionType.incoming) {
|
||||
// probably safe to assume this is an incoming tx as it is a utxo
|
||||
// belonging to this wallet. The extra check may be redundant but
|
||||
// just in case...
|
||||
|
||||
shouldBlock = true;
|
||||
blockReason = "Incoming paynym notification transaction.";
|
||||
}
|
||||
|
||||
final utxo = isar_models.UTXO(
|
||||
walletId: walletId,
|
||||
txid: txn["txid"] as String,
|
||||
vout: fetchedUtxoList[i][j]["tx_pos"] as int,
|
||||
value: fetchedUtxoList[i][j]["value"] as int,
|
||||
name: "",
|
||||
isBlocked: false,
|
||||
blockedReason: null,
|
||||
isBlocked: shouldBlock,
|
||||
blockedReason: blockReason,
|
||||
isCoinbase: txn["is_coinbase"] as bool? ?? false,
|
||||
blockHash: txn["blockhash"] as String?,
|
||||
blockHeight: fetchedUtxoList[i][j]["height"] as int?,
|
||||
|
@ -1656,7 +1729,7 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
|
||||
// Use new index to derive a new receiving address
|
||||
final newReceivingAddress = await _generateAddressForChain(
|
||||
0, newReceivingIndex, DerivePathType.bip44);
|
||||
0, newReceivingIndex, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
final existing = await db
|
||||
.getAddresses(walletId)
|
||||
|
@ -1675,12 +1748,12 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
}
|
||||
} on SocketException catch (se, s) {
|
||||
Logging.instance.log(
|
||||
"SocketException caught in _checkReceivingAddressForTransactions($DerivePathType.bip44): $se\n$s",
|
||||
"SocketException caught in _checkReceivingAddressForTransactions(${DerivePathTypeExt.primaryFor(coin)}): $se\n$s",
|
||||
level: LogLevel.Error);
|
||||
return;
|
||||
} catch (e, s) {
|
||||
Logging.instance.log(
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions($DerivePathType.bip44): $e\n$s",
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathTypeExt.primaryFor(coin)}): $e\n$s",
|
||||
level: LogLevel.Error);
|
||||
rethrow;
|
||||
}
|
||||
|
@ -1700,7 +1773,7 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
|
||||
// Use new index to derive a new change address
|
||||
final newChangeAddress = await _generateAddressForChain(
|
||||
1, newChangeIndex, DerivePathType.bip44);
|
||||
1, newChangeIndex, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
final existing = await db
|
||||
.getAddresses(walletId)
|
||||
|
@ -1719,7 +1792,7 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
}
|
||||
} catch (e, s) {
|
||||
Logging.instance.log(
|
||||
"Exception rethrown from _checkChangeAddressForTransactions(${DerivePathType.bip44}): $e\n$s",
|
||||
"Exception rethrown from _checkChangeAddressForTransactions(${DerivePathTypeExt.primaryFor(coin)}): $e\n$s",
|
||||
level: LogLevel.Error);
|
||||
rethrow;
|
||||
}
|
||||
|
@ -2088,7 +2161,7 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
utxoSigningData: utxoSigningData,
|
||||
recipients: [
|
||||
_recipientAddress,
|
||||
await _getCurrentAddressForChain(1, DerivePathType.bip44),
|
||||
await _getCurrentAddressForChain(1, DerivePathTypeExt.primaryFor(coin)),
|
||||
],
|
||||
satoshiAmounts: [
|
||||
satoshiAmountToSend,
|
||||
|
@ -2141,8 +2214,8 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
feeForTwoOutputs) {
|
||||
// generate new change address if current change address has been used
|
||||
await checkChangeAddressForTransactions();
|
||||
final String newChangeAddress =
|
||||
await _getCurrentAddressForChain(1, DerivePathType.bip44);
|
||||
final String newChangeAddress = await _getCurrentAddressForChain(
|
||||
1, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
int feeBeingPaid =
|
||||
satoshisBeingUsed - satoshiAmountToSend - changeOutputSize;
|
||||
|
@ -2340,6 +2413,8 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
case DerivePathType.bip44:
|
||||
addressesP2PKH.add(address);
|
||||
break;
|
||||
default:
|
||||
throw Exception("Unsupported DerivePathType");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -2757,7 +2832,7 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
|
||||
// Use new index to derive a new receiving address
|
||||
final newReceivingAddress = await _generateAddressForChain(
|
||||
0, newReceivingIndex, DerivePathType.bip44);
|
||||
0, newReceivingIndex, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
// Add that new receiving address
|
||||
await db.putAddress(newReceivingAddress);
|
||||
|
@ -2775,7 +2850,7 @@ class DogecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
// Dogecoin Network
|
||||
final dogecoin = NetworkType(
|
||||
messagePrefix: '\x18Dogecoin Signed Message:\n',
|
||||
bech32: 'bc',
|
||||
// bech32: 'bc',
|
||||
bip32: Bip32Type(public: 0x02facafd, private: 0x02fac398),
|
||||
pubKeyHash: 0x1e,
|
||||
scriptHash: 0x16,
|
||||
|
@ -2783,7 +2858,7 @@ final dogecoin = NetworkType(
|
|||
|
||||
final dogecointestnet = NetworkType(
|
||||
messagePrefix: '\x18Dogecoin Signed Message:\n',
|
||||
bech32: 'tb',
|
||||
// bech32: 'tb',
|
||||
bip32: Bip32Type(public: 0x043587cf, private: 0x04358394),
|
||||
pubKeyHash: 0x71,
|
||||
scriptHash: 0xc4,
|
||||
|
|
|
@ -17,13 +17,13 @@ import 'package:stackwallet/electrumx_rpc/electrumx.dart';
|
|||
import 'package:stackwallet/models/balance.dart';
|
||||
import 'package:stackwallet/models/isar/models/isar_models.dart' as isar_models;
|
||||
import 'package:stackwallet/models/paymint/fee_object_model.dart';
|
||||
import 'package:stackwallet/services/coins/coin_paynym_extension.dart';
|
||||
import 'package:stackwallet/services/coins/coin_service.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/node_connection_status_changed_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/refresh_percent_changed_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/updated_in_background_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/wallet_sync_status_changed_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/global_event_bus.dart';
|
||||
import 'package:stackwallet/services/mixins/electrum_x_parsing.dart';
|
||||
import 'package:stackwallet/services/mixins/wallet_cache.dart';
|
||||
import 'package:stackwallet/services/mixins/wallet_db.dart';
|
||||
import 'package:stackwallet/services/node_service.dart';
|
||||
|
@ -33,6 +33,7 @@ import 'package:stackwallet/utilities/assets.dart';
|
|||
import 'package:stackwallet/utilities/constants.dart';
|
||||
import 'package:stackwallet/utilities/default_nodes.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/derive_path_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/fee_rate_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/flutter_secure_storage_interface.dart';
|
||||
import 'package:stackwallet/utilities/format.dart';
|
||||
|
@ -50,8 +51,6 @@ const String GENESIS_HASH_MAINNET =
|
|||
const String GENESIS_HASH_TESTNET =
|
||||
"4966625a4b2851d9fdee139e56211a0d88575f59ed816ff5e6a63deb4e3e29a0";
|
||||
|
||||
enum DerivePathType { bip44, bip49, bip84 }
|
||||
|
||||
bip32.BIP32 getBip32Node(
|
||||
int chain,
|
||||
int index,
|
||||
|
@ -138,7 +137,8 @@ bip32.BIP32 getBip32RootWrapper(Tuple2<String, NetworkType> args) {
|
|||
return getBip32Root(args.item1, args.item2);
|
||||
}
|
||||
|
||||
class LitecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
||||
class LitecoinWallet extends CoinServiceAPI
|
||||
with WalletCache, WalletDB, ElectrumXParsing {
|
||||
static const integrationTestFlag =
|
||||
bool.fromEnvironment("IS_INTEGRATION_TEST");
|
||||
|
||||
|
@ -193,7 +193,7 @@ class LitecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
.subTypeEqualTo(isar_models.AddressSubType.receiving)
|
||||
.sortByDerivationIndexDesc()
|
||||
.findFirst()) ??
|
||||
await _generateAddressForChain(0, 0, DerivePathType.bip84);
|
||||
await _generateAddressForChain(0, 0, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
Future<String> get currentChangeAddress async =>
|
||||
(await _currentChangeAddress).value;
|
||||
|
@ -206,7 +206,7 @@ class LitecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
.subTypeEqualTo(isar_models.AddressSubType.change)
|
||||
.sortByDerivationIndexDesc()
|
||||
.findFirst()) ??
|
||||
await _generateAddressForChain(1, 0, DerivePathType.bip84);
|
||||
await _generateAddressForChain(1, 0, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
@override
|
||||
Future<void> exit() async {
|
||||
|
@ -1891,7 +1891,7 @@ class LitecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
|
||||
// Use new index to derive a new receiving address
|
||||
final newReceivingAddress = await _generateAddressForChain(
|
||||
0, newReceivingIndex, DerivePathType.bip84);
|
||||
0, newReceivingIndex, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
final existing = await db
|
||||
.getAddresses(walletId)
|
||||
|
@ -1910,7 +1910,7 @@ class LitecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
}
|
||||
} catch (e, s) {
|
||||
Logging.instance.log(
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathType.bip84}): $e\n$s",
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathTypeExt.primaryFor(coin)}): $e\n$s",
|
||||
level: LogLevel.Error);
|
||||
rethrow;
|
||||
}
|
||||
|
@ -1930,7 +1930,7 @@ class LitecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
|
||||
// Use new index to derive a new change address
|
||||
final newChangeAddress = await _generateAddressForChain(
|
||||
1, newChangeIndex, DerivePathType.bip84);
|
||||
1, newChangeIndex, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
final existing = await db
|
||||
.getAddresses(walletId)
|
||||
|
@ -1949,12 +1949,12 @@ class LitecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
}
|
||||
} on SocketException catch (se, s) {
|
||||
Logging.instance.log(
|
||||
"SocketException caught in _checkReceivingAddressForTransactions(${DerivePathType.bip84}): $se\n$s",
|
||||
"SocketException caught in _checkReceivingAddressForTransactions(${DerivePathTypeExt.primaryFor(coin)}): $se\n$s",
|
||||
level: LogLevel.Error);
|
||||
return;
|
||||
} catch (e, s) {
|
||||
Logging.instance.log(
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathType.bip84}): $e\n$s",
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathTypeExt.primaryFor(coin)}): $e\n$s",
|
||||
level: LogLevel.Error);
|
||||
rethrow;
|
||||
}
|
||||
|
@ -2349,7 +2349,7 @@ class LitecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
utxoSigningData: utxoSigningData,
|
||||
recipients: [
|
||||
_recipientAddress,
|
||||
await _getCurrentAddressForChain(1, DerivePathType.bip84),
|
||||
await _getCurrentAddressForChain(1, DerivePathTypeExt.primaryFor(coin)),
|
||||
],
|
||||
satoshiAmounts: [
|
||||
satoshiAmountToSend,
|
||||
|
@ -2388,8 +2388,8 @@ class LitecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
feeForTwoOutputs) {
|
||||
// generate new change address if current change address has been used
|
||||
await _checkChangeAddressForTransactions();
|
||||
final String newChangeAddress =
|
||||
await _getCurrentAddressForChain(1, DerivePathType.bip84);
|
||||
final String newChangeAddress = await _getCurrentAddressForChain(
|
||||
1, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
int feeBeingPaid =
|
||||
satoshisBeingUsed - satoshiAmountToSend - changeOutputSize;
|
||||
|
@ -3345,7 +3345,7 @@ class LitecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
|
||||
// Use new index to derive a new receiving address
|
||||
final newReceivingAddress = await _generateAddressForChain(
|
||||
0, newReceivingIndex, DerivePathType.bip84);
|
||||
0, newReceivingIndex, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
// Add that new receiving address
|
||||
await db.putAddress(newReceivingAddress);
|
||||
|
|
|
@ -9,6 +9,7 @@ import 'package:stackwallet/services/coins/coin_service.dart';
|
|||
import 'package:stackwallet/services/event_bus/events/global/node_connection_status_changed_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/updated_in_background_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/global_event_bus.dart';
|
||||
import 'package:stackwallet/services/mixins/paynym_wallet_interface.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/logger.dart';
|
||||
|
||||
|
@ -214,4 +215,6 @@ class Manager with ChangeNotifier {
|
|||
}
|
||||
|
||||
int get currentHeight => _currentWallet.storedChainHeight;
|
||||
|
||||
bool get hasPaynymSupport => _currentWallet is PaynymWalletInterface;
|
||||
}
|
||||
|
|
|
@ -17,13 +17,13 @@ import 'package:stackwallet/electrumx_rpc/electrumx.dart';
|
|||
import 'package:stackwallet/models/balance.dart';
|
||||
import 'package:stackwallet/models/isar/models/isar_models.dart' as isar_models;
|
||||
import 'package:stackwallet/models/paymint/fee_object_model.dart';
|
||||
import 'package:stackwallet/services/coins/coin_paynym_extension.dart';
|
||||
import 'package:stackwallet/services/coins/coin_service.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/node_connection_status_changed_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/refresh_percent_changed_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/updated_in_background_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/events/global/wallet_sync_status_changed_event.dart';
|
||||
import 'package:stackwallet/services/event_bus/global_event_bus.dart';
|
||||
import 'package:stackwallet/services/mixins/electrum_x_parsing.dart';
|
||||
import 'package:stackwallet/services/mixins/wallet_cache.dart';
|
||||
import 'package:stackwallet/services/mixins/wallet_db.dart';
|
||||
import 'package:stackwallet/services/node_service.dart';
|
||||
|
@ -33,6 +33,7 @@ import 'package:stackwallet/utilities/assets.dart';
|
|||
import 'package:stackwallet/utilities/constants.dart';
|
||||
import 'package:stackwallet/utilities/default_nodes.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/derive_path_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/fee_rate_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/flutter_secure_storage_interface.dart';
|
||||
import 'package:stackwallet/utilities/format.dart';
|
||||
|
@ -50,8 +51,6 @@ const String GENESIS_HASH_MAINNET =
|
|||
const String GENESIS_HASH_TESTNET =
|
||||
"00000007199508e34a9ff81e6ec0c477a4cccff2a4767a8eee39c11db367b008";
|
||||
|
||||
enum DerivePathType { bip44, bip49, bip84 }
|
||||
|
||||
bip32.BIP32 getBip32Node(
|
||||
int chain,
|
||||
int index,
|
||||
|
@ -135,7 +134,8 @@ bip32.BIP32 getBip32RootWrapper(Tuple2<String, NetworkType> args) {
|
|||
return getBip32Root(args.item1, args.item2);
|
||||
}
|
||||
|
||||
class NamecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
||||
class NamecoinWallet extends CoinServiceAPI
|
||||
with WalletCache, WalletDB, ElectrumXParsing {
|
||||
static const integrationTestFlag =
|
||||
bool.fromEnvironment("IS_INTEGRATION_TEST");
|
||||
|
||||
|
@ -188,7 +188,7 @@ class NamecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
.subTypeEqualTo(isar_models.AddressSubType.receiving)
|
||||
.sortByDerivationIndexDesc()
|
||||
.findFirst()) ??
|
||||
await _generateAddressForChain(0, 0, DerivePathType.bip84);
|
||||
await _generateAddressForChain(0, 0, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
Future<String> get currentChangeAddress async =>
|
||||
(await _currentChangeAddress).value;
|
||||
|
@ -201,7 +201,7 @@ class NamecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
.subTypeEqualTo(isar_models.AddressSubType.change)
|
||||
.sortByDerivationIndexDesc()
|
||||
.findFirst()) ??
|
||||
await _generateAddressForChain(1, 0, DerivePathType.bip84);
|
||||
await _generateAddressForChain(1, 0, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
@override
|
||||
Future<void> exit() async {
|
||||
|
@ -1873,7 +1873,7 @@ class NamecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
|
||||
// Use new index to derive a new receiving address
|
||||
final newReceivingAddress = await _generateAddressForChain(
|
||||
0, newReceivingIndex, DerivePathType.bip84);
|
||||
0, newReceivingIndex, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
final existing = await db
|
||||
.getAddresses(walletId)
|
||||
|
@ -1892,7 +1892,7 @@ class NamecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
}
|
||||
} catch (e, s) {
|
||||
Logging.instance.log(
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathType.bip84}): $e\n$s",
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathTypeExt.primaryFor(coin)}): $e\n$s",
|
||||
level: LogLevel.Error);
|
||||
rethrow;
|
||||
}
|
||||
|
@ -1912,7 +1912,7 @@ class NamecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
|
||||
// Use new index to derive a new change address
|
||||
final newChangeAddress = await _generateAddressForChain(
|
||||
1, newChangeIndex, DerivePathType.bip84);
|
||||
1, newChangeIndex, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
final existing = await db
|
||||
.getAddresses(walletId)
|
||||
|
@ -1932,12 +1932,12 @@ class NamecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
}
|
||||
} on SocketException catch (se, s) {
|
||||
Logging.instance.log(
|
||||
"SocketException caught in _checkReceivingAddressForTransactions(${DerivePathType.bip84}): $se\n$s",
|
||||
"SocketException caught in _checkReceivingAddressForTransactions(${DerivePathTypeExt.primaryFor(coin)}): $se\n$s",
|
||||
level: LogLevel.Error);
|
||||
return;
|
||||
} catch (e, s) {
|
||||
Logging.instance.log(
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathType.bip84}): $e\n$s",
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathTypeExt.primaryFor(coin)}): $e\n$s",
|
||||
level: LogLevel.Error);
|
||||
rethrow;
|
||||
}
|
||||
|
@ -2336,7 +2336,7 @@ class NamecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
utxoSigningData: utxoSigningData,
|
||||
recipients: [
|
||||
_recipientAddress,
|
||||
await _getCurrentAddressForChain(1, DerivePathType.bip84),
|
||||
await _getCurrentAddressForChain(1, DerivePathTypeExt.primaryFor(coin)),
|
||||
],
|
||||
satoshiAmounts: [
|
||||
satoshiAmountToSend,
|
||||
|
@ -2375,8 +2375,8 @@ class NamecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
feeForTwoOutputs) {
|
||||
// generate new change address if current change address has been used
|
||||
await _checkChangeAddressForTransactions();
|
||||
final String newChangeAddress =
|
||||
await _getCurrentAddressForChain(1, DerivePathType.bip84);
|
||||
final String newChangeAddress = await _getCurrentAddressForChain(
|
||||
1, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
int feeBeingPaid =
|
||||
satoshisBeingUsed - satoshiAmountToSend - changeOutputSize;
|
||||
|
@ -3336,7 +3336,7 @@ class NamecoinWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
|
||||
// Use new index to derive a new receiving address
|
||||
final newReceivingAddress = await _generateAddressForChain(
|
||||
0, newReceivingIndex, DerivePathType.bip84);
|
||||
0, newReceivingIndex, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
// Add that new receiving address
|
||||
await db.putAddress(newReceivingAddress);
|
||||
|
|
|
@ -32,6 +32,7 @@ import 'package:stackwallet/utilities/assets.dart';
|
|||
import 'package:stackwallet/utilities/constants.dart';
|
||||
import 'package:stackwallet/utilities/default_nodes.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/derive_path_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/fee_rate_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/flutter_secure_storage_interface.dart';
|
||||
import 'package:stackwallet/utilities/format.dart';
|
||||
|
@ -48,8 +49,6 @@ const String GENESIS_HASH_MAINNET =
|
|||
const String GENESIS_HASH_TESTNET =
|
||||
"0000594ada5310b367443ee0afd4fa3d0bbd5850ea4e33cdc7d6a904a7ec7c90";
|
||||
|
||||
enum DerivePathType { bip44, bip84 }
|
||||
|
||||
bip32.BIP32 getBip32Node(
|
||||
int chain,
|
||||
int index,
|
||||
|
@ -184,7 +183,7 @@ class ParticlWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
.subTypeEqualTo(isar_models.AddressSubType.receiving)
|
||||
.sortByDerivationIndexDesc()
|
||||
.findFirst()) ??
|
||||
await _generateAddressForChain(0, 0, DerivePathType.bip84);
|
||||
await _generateAddressForChain(0, 0, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
Future<String> get currentChangeAddress async =>
|
||||
(await _currentChangeAddress).value;
|
||||
|
@ -197,7 +196,7 @@ class ParticlWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
.subTypeEqualTo(isar_models.AddressSubType.change)
|
||||
.sortByDerivationIndexDesc()
|
||||
.findFirst()) ??
|
||||
await _generateAddressForChain(1, 0, DerivePathType.bip84);
|
||||
await _generateAddressForChain(1, 0, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
@override
|
||||
Future<void> exit() async {
|
||||
|
@ -1407,6 +1406,8 @@ class ParticlWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
address = P2WPKH(network: _network, data: data).data.address!;
|
||||
addrType = isar_models.AddressType.p2wpkh;
|
||||
break;
|
||||
default:
|
||||
throw Exception("Unsupported DerivePathType");
|
||||
}
|
||||
|
||||
// add generated address & info to derivations
|
||||
|
@ -1450,6 +1451,8 @@ class ParticlWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
case DerivePathType.bip84:
|
||||
type = isar_models.AddressType.p2wpkh;
|
||||
break;
|
||||
default:
|
||||
throw Exception("Unsupported DerivePathType");
|
||||
}
|
||||
address = await db
|
||||
.getAddresses(walletId)
|
||||
|
@ -1475,6 +1478,8 @@ class ParticlWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
case DerivePathType.bip84:
|
||||
key = "${walletId}_${chainId}DerivationsP2WPKH";
|
||||
break;
|
||||
default:
|
||||
throw Exception("Unsupported DerivePathType");
|
||||
}
|
||||
return key;
|
||||
}
|
||||
|
@ -1761,7 +1766,7 @@ class ParticlWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
|
||||
// Use new index to derive a new receiving address
|
||||
final newReceivingAddress = await _generateAddressForChain(
|
||||
0, newReceivingIndex, DerivePathType.bip84);
|
||||
0, newReceivingIndex, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
final existing = await db
|
||||
.getAddresses(walletId)
|
||||
|
@ -1780,7 +1785,7 @@ class ParticlWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
}
|
||||
} catch (e, s) {
|
||||
Logging.instance.log(
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathType.bip84}): $e\n$s",
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathTypeExt.primaryFor(coin)}): $e\n$s",
|
||||
level: LogLevel.Error);
|
||||
rethrow;
|
||||
}
|
||||
|
@ -1800,7 +1805,7 @@ class ParticlWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
|
||||
// Use new index to derive a new change address
|
||||
final newChangeAddress = await _generateAddressForChain(
|
||||
1, newChangeIndex, DerivePathType.bip84);
|
||||
1, newChangeIndex, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
final existing = await db
|
||||
.getAddresses(walletId)
|
||||
|
@ -1819,12 +1824,12 @@ class ParticlWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
}
|
||||
} on SocketException catch (se, s) {
|
||||
Logging.instance.log(
|
||||
"SocketException caught in _checkReceivingAddressForTransactions(${DerivePathType.bip84}): $se\n$s",
|
||||
"SocketException caught in _checkReceivingAddressForTransactions(${DerivePathTypeExt.primaryFor(coin)}): $se\n$s",
|
||||
level: LogLevel.Error);
|
||||
return;
|
||||
} catch (e, s) {
|
||||
Logging.instance.log(
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathType.bip84}): $e\n$s",
|
||||
"Exception rethrown from _checkReceivingAddressForTransactions(${DerivePathTypeExt.primaryFor(coin)}): $e\n$s",
|
||||
level: LogLevel.Error);
|
||||
rethrow;
|
||||
}
|
||||
|
@ -2501,7 +2506,7 @@ class ParticlWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
utxoSigningData: utxoSigningData,
|
||||
recipients: [
|
||||
_recipientAddress,
|
||||
await _getCurrentAddressForChain(1, DerivePathType.bip84),
|
||||
await _getCurrentAddressForChain(1, DerivePathTypeExt.primaryFor(coin)),
|
||||
],
|
||||
satoshiAmounts: [
|
||||
satoshiAmountToSend,
|
||||
|
@ -2540,8 +2545,8 @@ class ParticlWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
feeForTwoOutputs) {
|
||||
// generate new change address if current change address has been used
|
||||
await _checkChangeAddressForTransactions();
|
||||
final String newChangeAddress =
|
||||
await _getCurrentAddressForChain(1, DerivePathType.bip84);
|
||||
final String newChangeAddress = await _getCurrentAddressForChain(
|
||||
1, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
int feeBeingPaid =
|
||||
satoshisBeingUsed - satoshiAmountToSend - changeOutputSize;
|
||||
|
@ -2743,6 +2748,8 @@ class ParticlWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
case DerivePathType.bip84:
|
||||
addressesP2WPKH.add(address);
|
||||
break;
|
||||
default:
|
||||
throw Exception("Unsupported DerivePathType");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -3328,7 +3335,7 @@ class ParticlWallet extends CoinServiceAPI with WalletCache, WalletDB {
|
|||
|
||||
// Use new index to derive a new receiving address
|
||||
final newReceivingAddress = await _generateAddressForChain(
|
||||
0, newReceivingIndex, DerivePathType.bip84);
|
||||
0, newReceivingIndex, DerivePathTypeExt.primaryFor(coin));
|
||||
|
||||
// Add that new receiving address
|
||||
await db.putAddress(newReceivingAddress);
|
||||
|
|
222
lib/services/mixins/electrum_x_parsing.dart
Normal file
222
lib/services/mixins/electrum_x_parsing.dart
Normal file
|
@ -0,0 +1,222 @@
|
|||
import 'package:bip47/src/util.dart';
|
||||
import 'package:decimal/decimal.dart';
|
||||
import 'package:stackwallet/models/isar/models/isar_models.dart';
|
||||
import 'package:stackwallet/services/mixins/paynym_wallet_interface.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/format.dart';
|
||||
import 'package:tuple/tuple.dart';
|
||||
|
||||
mixin ElectrumXParsing {
|
||||
Future<Tuple4<Transaction, List<Output>, List<Input>, Address>>
|
||||
parseTransaction(
|
||||
Map<String, dynamic> txData,
|
||||
dynamic electrumxClient,
|
||||
List<Address> myAddresses,
|
||||
Coin coin,
|
||||
int minConfirms,
|
||||
String walletId,
|
||||
) async {
|
||||
Set<String> receivingAddresses = myAddresses
|
||||
.where((e) =>
|
||||
e.subType == AddressSubType.receiving ||
|
||||
e.subType == AddressSubType.paynymReceive ||
|
||||
e.subType == AddressSubType.paynymNotification)
|
||||
.map((e) => e.value)
|
||||
.toSet();
|
||||
Set<String> changeAddresses = myAddresses
|
||||
.where((e) => e.subType == AddressSubType.change)
|
||||
.map((e) => e.value)
|
||||
.toSet();
|
||||
|
||||
Set<String> inputAddresses = {};
|
||||
Set<String> outputAddresses = {};
|
||||
|
||||
int totalInputValue = 0;
|
||||
int totalOutputValue = 0;
|
||||
|
||||
int amountSentFromWallet = 0;
|
||||
int amountReceivedInWallet = 0;
|
||||
int changeAmount = 0;
|
||||
|
||||
// parse inputs
|
||||
for (final input in txData["vin"] as List) {
|
||||
final prevTxid = input["txid"] as String;
|
||||
final prevOut = input["vout"] as int;
|
||||
|
||||
// fetch input tx to get address
|
||||
final inputTx = await electrumxClient.getTransaction(
|
||||
txHash: prevTxid,
|
||||
coin: coin,
|
||||
);
|
||||
|
||||
for (final output in inputTx["vout"] as List) {
|
||||
// check matching output
|
||||
if (prevOut == output["n"]) {
|
||||
// get value
|
||||
final value = Format.decimalAmountToSatoshis(
|
||||
Decimal.parse(output["value"].toString()),
|
||||
coin,
|
||||
);
|
||||
|
||||
// add value to total
|
||||
totalInputValue += value;
|
||||
|
||||
// get input(prevOut) address
|
||||
final address = output["scriptPubKey"]?["addresses"]?[0] as String? ??
|
||||
output["scriptPubKey"]?["address"] as String?;
|
||||
|
||||
if (address != null) {
|
||||
inputAddresses.add(address);
|
||||
|
||||
// if input was from my wallet, add value to amount sent
|
||||
if (receivingAddresses.contains(address) ||
|
||||
changeAddresses.contains(address)) {
|
||||
amountSentFromWallet += value;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// parse outputs
|
||||
for (final output in txData["vout"] as List) {
|
||||
// get value
|
||||
final value = Format.decimalAmountToSatoshis(
|
||||
Decimal.parse(output["value"].toString()),
|
||||
coin,
|
||||
);
|
||||
|
||||
// add value to total
|
||||
totalOutputValue += value;
|
||||
|
||||
// get output address
|
||||
final address = output["scriptPubKey"]?["addresses"]?[0] as String? ??
|
||||
output["scriptPubKey"]?["address"] as String?;
|
||||
if (address != null) {
|
||||
outputAddresses.add(address);
|
||||
|
||||
// if output was to my wallet, add value to amount received
|
||||
if (receivingAddresses.contains(address)) {
|
||||
amountReceivedInWallet += value;
|
||||
} else if (changeAddresses.contains(address)) {
|
||||
changeAmount += value;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
final mySentFromAddresses = [
|
||||
...receivingAddresses.intersection(inputAddresses),
|
||||
...changeAddresses.intersection(inputAddresses)
|
||||
];
|
||||
final myReceivedOnAddresses =
|
||||
receivingAddresses.intersection(outputAddresses);
|
||||
final myChangeReceivedOnAddresses =
|
||||
changeAddresses.intersection(outputAddresses);
|
||||
|
||||
final fee = totalInputValue - totalOutputValue;
|
||||
|
||||
// this is the address initially used to fetch the txid
|
||||
Address transactionAddress = txData["address"] as Address;
|
||||
|
||||
TransactionType type;
|
||||
int amount;
|
||||
if (mySentFromAddresses.isNotEmpty && myReceivedOnAddresses.isNotEmpty) {
|
||||
// tx is sent to self
|
||||
type = TransactionType.sentToSelf;
|
||||
|
||||
// should be 0
|
||||
amount =
|
||||
amountSentFromWallet - amountReceivedInWallet - fee - changeAmount;
|
||||
} else if (mySentFromAddresses.isNotEmpty) {
|
||||
// outgoing tx
|
||||
type = TransactionType.outgoing;
|
||||
amount = amountSentFromWallet - changeAmount - fee;
|
||||
|
||||
final possible =
|
||||
outputAddresses.difference(myChangeReceivedOnAddresses).first;
|
||||
|
||||
if (transactionAddress.value != possible) {
|
||||
transactionAddress = Address(
|
||||
walletId: walletId,
|
||||
value: possible,
|
||||
derivationIndex: -1,
|
||||
subType: AddressSubType.nonWallet,
|
||||
type: AddressType.nonWallet,
|
||||
publicKey: [],
|
||||
);
|
||||
}
|
||||
} else {
|
||||
// incoming tx
|
||||
type = TransactionType.incoming;
|
||||
amount = amountReceivedInWallet;
|
||||
}
|
||||
|
||||
List<Output> outs = [];
|
||||
List<Input> ins = [];
|
||||
|
||||
for (final json in txData["vin"] as List) {
|
||||
bool isCoinBase = json['coinbase'] != null;
|
||||
final input = Input(
|
||||
walletId: walletId,
|
||||
txid: json['txid'] as String,
|
||||
vout: json['vout'] as int? ?? -1,
|
||||
scriptSig: json['scriptSig']?['hex'] as String?,
|
||||
scriptSigAsm: json['scriptSig']?['asm'] as String?,
|
||||
isCoinbase: isCoinBase ? isCoinBase : json['is_coinbase'] as bool?,
|
||||
sequence: json['sequence'] as int?,
|
||||
innerRedeemScriptAsm: json['innerRedeemscriptAsm'] as String?,
|
||||
);
|
||||
ins.add(input);
|
||||
}
|
||||
|
||||
for (final json in txData["vout"] as List) {
|
||||
final output = Output(
|
||||
walletId: walletId,
|
||||
scriptPubKey: json['scriptPubKey']?['hex'] as String?,
|
||||
scriptPubKeyAsm: json['scriptPubKey']?['asm'] as String?,
|
||||
scriptPubKeyType: json['scriptPubKey']?['type'] as String?,
|
||||
scriptPubKeyAddress:
|
||||
json["scriptPubKey"]?["addresses"]?[0] as String? ??
|
||||
json['scriptPubKey']?['type'] as String? ??
|
||||
"",
|
||||
value: Format.decimalAmountToSatoshis(
|
||||
Decimal.parse(json["value"].toString()),
|
||||
coin,
|
||||
),
|
||||
);
|
||||
outs.add(output);
|
||||
}
|
||||
|
||||
TransactionSubType txSubType = TransactionSubType.none;
|
||||
if (this is PaynymWalletInterface && outs.length > 1 && ins.isNotEmpty) {
|
||||
List<String>? scriptChunks = outs[1].scriptPubKeyAsm?.split(" ");
|
||||
if (scriptChunks?.length == 2 && scriptChunks?[0] == "OP_RETURN") {
|
||||
final blindedPaymentCode = scriptChunks![1];
|
||||
final bytes = blindedPaymentCode.fromHex;
|
||||
|
||||
// https://en.bitcoin.it/wiki/BIP_0047#Sending
|
||||
if (bytes.length == 80 && bytes.first == 1) {
|
||||
txSubType = TransactionSubType.bip47Notification;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
final tx = Transaction(
|
||||
walletId: walletId,
|
||||
txid: txData["txid"] as String,
|
||||
timestamp: txData["blocktime"] as int? ??
|
||||
(DateTime.now().millisecondsSinceEpoch ~/ 1000),
|
||||
type: type,
|
||||
subType: txSubType,
|
||||
amount: amount,
|
||||
fee: fee,
|
||||
height: txData["height"] as int?,
|
||||
isCancelled: false,
|
||||
isLelantus: false,
|
||||
slateId: null,
|
||||
otherData: null,
|
||||
);
|
||||
|
||||
return Tuple4(tx, outs, ins, transactionAddress);
|
||||
}
|
||||
}
|
1125
lib/services/mixins/paynym_wallet_interface.dart
Normal file
1125
lib/services/mixins/paynym_wallet_interface.dart
Normal file
File diff suppressed because it is too large
Load diff
|
@ -2,6 +2,7 @@ import 'dart:async';
|
|||
|
||||
import 'package:flutter/foundation.dart';
|
||||
import 'package:stackwallet/electrumx_rpc/electrumx.dart';
|
||||
import 'package:stackwallet/exceptions/electrumx/no_such_transaction.dart';
|
||||
import 'package:stackwallet/hive/db.dart';
|
||||
import 'package:stackwallet/models/exchange/response_objects/trade.dart';
|
||||
import 'package:stackwallet/models/notification_model.dart';
|
||||
|
@ -169,12 +170,14 @@ class NotificationsService extends ChangeNotifier {
|
|||
}
|
||||
|
||||
// replaces the current notification with the updated one
|
||||
add(updatedNotification, true);
|
||||
await add(updatedNotification, true);
|
||||
}
|
||||
} else {
|
||||
// TODO: check non electrumx coins
|
||||
}
|
||||
}
|
||||
} on NoSuchTransactionException catch (e, s) {
|
||||
await _deleteWatchedTxNotification(notification);
|
||||
} catch (e, s) {
|
||||
Logging.instance.log("$e $s", level: LogLevel.Error);
|
||||
}
|
||||
|
|
|
@ -54,4 +54,25 @@ class TransactionNotificationTracker {
|
|||
key: "notifiedConfirmedTransactions",
|
||||
value: notifiedConfirmedTransactions);
|
||||
}
|
||||
|
||||
Future<void> deleteTransaction(String txid) async {
|
||||
final notifiedPendingTransactions = DB.instance.get<dynamic>(
|
||||
boxName: walletId, key: "notifiedPendingTransactions") as Map? ??
|
||||
{};
|
||||
final notifiedConfirmedTransactions = DB.instance.get<dynamic>(
|
||||
boxName: walletId, key: "notifiedConfirmedTransactions") as Map? ??
|
||||
{};
|
||||
|
||||
notifiedPendingTransactions.remove(txid);
|
||||
notifiedConfirmedTransactions.remove(txid);
|
||||
|
||||
await DB.instance.put<dynamic>(
|
||||
boxName: walletId,
|
||||
key: "notifiedConfirmedTransactions",
|
||||
value: notifiedConfirmedTransactions);
|
||||
await DB.instance.put<dynamic>(
|
||||
boxName: walletId,
|
||||
key: "notifiedPendingTransactions",
|
||||
value: notifiedPendingTransactions);
|
||||
}
|
||||
}
|
||||
|
|
32
lib/utilities/bip32_utils.dart
Normal file
32
lib/utilities/bip32_utils.dart
Normal file
|
@ -0,0 +1,32 @@
|
|||
import 'package:bip32/bip32.dart' as bip32;
|
||||
import 'package:bip39/bip39.dart' as bip39;
|
||||
import 'package:bitcoindart/bitcoindart.dart';
|
||||
import 'package:flutter/foundation.dart';
|
||||
import 'package:tuple/tuple.dart';
|
||||
|
||||
abstract class Bip32Utils {
|
||||
static bip32.BIP32 getBip32RootSync(String mnemonic, NetworkType network) {
|
||||
final seed = bip39.mnemonicToSeed(mnemonic);
|
||||
final networkType = bip32.NetworkType(
|
||||
wif: network.wif,
|
||||
bip32: bip32.Bip32Type(
|
||||
public: network.bip32.public,
|
||||
private: network.bip32.private,
|
||||
),
|
||||
);
|
||||
|
||||
final root = bip32.BIP32.fromSeed(seed, networkType);
|
||||
return root;
|
||||
}
|
||||
|
||||
static Future<bip32.BIP32> getBip32Root(
|
||||
String mnemonic, NetworkType network) async {
|
||||
final root = await compute(_getBip32RootWrapper, Tuple2(mnemonic, network));
|
||||
return root;
|
||||
}
|
||||
|
||||
/// wrapper for compute()
|
||||
static bip32.BIP32 _getBip32RootWrapper(Tuple2<String, NetworkType> args) {
|
||||
return getBip32RootSync(args.item1, args.item2);
|
||||
}
|
||||
}
|
|
@ -171,30 +171,6 @@ extension CoinExt on Coin {
|
|||
}
|
||||
}
|
||||
|
||||
bool get hasPaynymSupport {
|
||||
switch (this) {
|
||||
case Coin.bitcoin:
|
||||
case Coin.litecoin:
|
||||
case Coin.bitcoincash:
|
||||
case Coin.firo:
|
||||
case Coin.namecoin:
|
||||
case Coin.particl:
|
||||
case Coin.bitcoinTestNet:
|
||||
case Coin.litecoinTestNet:
|
||||
case Coin.bitcoincashTestnet:
|
||||
case Coin.firoTestNet:
|
||||
case Coin.epicCash:
|
||||
case Coin.monero:
|
||||
case Coin.wownero:
|
||||
return false;
|
||||
|
||||
case Coin.dogecoin:
|
||||
case Coin.dogecoinTestNet:
|
||||
// return true;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
bool get hasBuySupport {
|
||||
switch (this) {
|
||||
case Coin.bitcoin:
|
||||
|
|
35
lib/utilities/enums/derive_path_type_enum.dart
Normal file
35
lib/utilities/enums/derive_path_type_enum.dart
Normal file
|
@ -0,0 +1,35 @@
|
|||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
|
||||
enum DerivePathType {
|
||||
bip44,
|
||||
bip49,
|
||||
bip84,
|
||||
}
|
||||
|
||||
extension DerivePathTypeExt on DerivePathType {
|
||||
static DerivePathType primaryFor(Coin coin) {
|
||||
switch (coin) {
|
||||
case Coin.bitcoincash:
|
||||
case Coin.bitcoincashTestnet:
|
||||
case Coin.dogecoin:
|
||||
case Coin.dogecoinTestNet:
|
||||
case Coin.firo:
|
||||
case Coin.firoTestNet:
|
||||
return DerivePathType.bip44;
|
||||
|
||||
case Coin.bitcoin:
|
||||
case Coin.bitcoinTestNet:
|
||||
case Coin.litecoin:
|
||||
case Coin.litecoinTestNet:
|
||||
case Coin.namecoin:
|
||||
case Coin.particl:
|
||||
return DerivePathType.bip84;
|
||||
|
||||
case Coin.epicCash:
|
||||
case Coin.monero:
|
||||
case Coin.wownero:
|
||||
throw UnsupportedError(
|
||||
"$coin does not use bitcoin style derivation paths");
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,12 +1,12 @@
|
|||
abstract class FeaturedPaynyms {
|
||||
// TODO: replace with actual values
|
||||
static const String samouraiWalletDevFund =
|
||||
"PM8TJYkuSdYXJnwDBq8ChfinfXv3srxhQrx3eoEwbSw51wMjdo9JJ2DsycwT3gt3zHQ7cV1grvabMmmf1Btj6fY7tgkgSz9B8MZuR3kjYfgMLMURJCXN";
|
||||
// TODO: replace with actual value
|
||||
// static const String samouraiWalletDevFund =
|
||||
// "PM8TJYkuSdYXJnwDBq8ChfinfXv3srxhQrx3eoEwbSw51wMjdo9JJ2DsycwT3gt3zHQ7cV1grvabMmmf1Btj6fY7tgkgSz9B8MZuR3kjYfgMLMURJCXN";
|
||||
static const String stackWallet =
|
||||
"PM8TJYkuSdYXJnwDBq8ChfinfXv3srxhQrx3eoEwbSw51wMjdo9JJ2DsycwT3gt3zHQ7cV1grvabMmmf1Btj6fY7tgkgSz9B8MZuR3kjYfgMLMURJCXN";
|
||||
"PM8TJPdEeH3A77h4xJYQeXPWix2W5yAJrzVQ8ggET1n92utnc57FXCoH94Z2wUSJNfGwkX1kNDTCQLkHecVsjQHGkDE8MUyWE4xWJcc1EDDYCeSSBfLL";
|
||||
|
||||
static Map<String, String> get featured => {
|
||||
"Stack Wallet": stackWallet,
|
||||
"Samourai Wallet Dev Fund": samouraiWalletDevFund,
|
||||
// "Samourai Wallet Dev Fund": samouraiWalletDevFund,
|
||||
};
|
||||
}
|
||||
|
|
|
@ -46,6 +46,8 @@ abstract class SecureStorageInterface {
|
|||
MacOsOptions? mOptions,
|
||||
WindowsOptions? wOptions,
|
||||
});
|
||||
|
||||
Future<List<String>> get keys;
|
||||
}
|
||||
|
||||
class DesktopSecureStore {
|
||||
|
@ -110,6 +112,10 @@ class DesktopSecureStore {
|
|||
await isar.encryptedStringValues.deleteByKey(key);
|
||||
});
|
||||
}
|
||||
|
||||
Future<List<String>> get keys async {
|
||||
return await isar.encryptedStringValues.where().keyProperty().findAll();
|
||||
}
|
||||
}
|
||||
|
||||
/// all *Options params ignored on desktop
|
||||
|
@ -229,6 +235,15 @@ class SecureStorageWrapper implements SecureStorageInterface {
|
|||
);
|
||||
}
|
||||
}
|
||||
|
||||
@override
|
||||
Future<List<String>> get keys async {
|
||||
if (_isDesktop) {
|
||||
return (_store as DesktopSecureStore).keys;
|
||||
} else {
|
||||
return (await (_store as FlutterSecureStorage).readAll()).keys.toList();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Mock class for testing purposes
|
||||
|
@ -305,4 +320,7 @@ class FakeSecureStorage implements SecureStorageInterface {
|
|||
|
||||
@override
|
||||
dynamic get store => throw UnimplementedError();
|
||||
|
||||
@override
|
||||
Future<List<String>> get keys => Future(() => _store.keys.toList());
|
||||
}
|
||||
|
|
|
@ -9,9 +9,9 @@ import 'package:stackwallet/notifications/show_flush_bar.dart';
|
|||
import 'package:stackwallet/providers/global/paynym_api_provider.dart';
|
||||
import 'package:stackwallet/providers/global/wallets_provider.dart';
|
||||
import 'package:stackwallet/providers/wallet/my_paynym_account_state_provider.dart';
|
||||
import 'package:stackwallet/services/coins/coin_paynym_extension.dart';
|
||||
import 'package:stackwallet/services/coins/dogecoin/dogecoin_wallet.dart';
|
||||
import 'package:stackwallet/services/mixins/paynym_wallet_interface.dart';
|
||||
import 'package:stackwallet/utilities/assets.dart';
|
||||
import 'package:stackwallet/utilities/enums/derive_path_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/theme/stack_colors.dart';
|
||||
import 'package:stackwallet/utilities/util.dart';
|
||||
import 'package:stackwallet/widgets/desktop/primary_button.dart';
|
||||
|
@ -58,16 +58,18 @@ class _PaynymFollowToggleButtonState
|
|||
),
|
||||
);
|
||||
|
||||
final wallet = ref
|
||||
.read(walletsChangeNotifierProvider)
|
||||
.getManager(widget.walletId)
|
||||
.wallet as DogecoinWallet;
|
||||
final manager =
|
||||
ref.read(walletsChangeNotifierProvider).getManager(widget.walletId);
|
||||
|
||||
// get wallet to access paynym calls
|
||||
final wallet = manager.wallet as PaynymWalletInterface;
|
||||
|
||||
final followedAccount = await ref
|
||||
.read(paynymAPIProvider)
|
||||
.nym(widget.paymentCodeStringToFollow, true);
|
||||
|
||||
final myPCode = await wallet.getPaymentCode();
|
||||
final myPCode =
|
||||
await wallet.getPaymentCode(DerivePathTypeExt.primaryFor(manager.coin));
|
||||
|
||||
PaynymResponse<String> token =
|
||||
await ref.read(paynymAPIProvider).token(myPCode.toString());
|
||||
|
@ -158,16 +160,17 @@ class _PaynymFollowToggleButtonState
|
|||
),
|
||||
);
|
||||
|
||||
final wallet = ref
|
||||
.read(walletsChangeNotifierProvider)
|
||||
.getManager(widget.walletId)
|
||||
.wallet as DogecoinWallet;
|
||||
final manager =
|
||||
ref.read(walletsChangeNotifierProvider).getManager(widget.walletId);
|
||||
|
||||
final wallet = manager.wallet as PaynymWalletInterface;
|
||||
|
||||
final followedAccount = await ref
|
||||
.read(paynymAPIProvider)
|
||||
.nym(widget.paymentCodeStringToFollow, true);
|
||||
|
||||
final myPCode = await wallet.getPaymentCode();
|
||||
final myPCode =
|
||||
await wallet.getPaymentCode(DerivePathTypeExt.primaryFor(manager.coin));
|
||||
|
||||
PaynymResponse<String> token =
|
||||
await ref.read(paynymAPIProvider).token(myPCode.toString());
|
||||
|
|
|
@ -100,8 +100,8 @@ packages:
|
|||
dependency: "direct main"
|
||||
description:
|
||||
path: "."
|
||||
ref: testing
|
||||
resolved-ref: "8ed2f6245c71a4457ed4ffdd3a74e4bcb9f9d2d0"
|
||||
ref: "87bb760be323228aed6ca7bd4532a709a4f10690"
|
||||
resolved-ref: "87bb760be323228aed6ca7bd4532a709a4f10690"
|
||||
url: "https://github.com/cypherstack/bip47.git"
|
||||
source: git
|
||||
version: "1.0.0"
|
||||
|
@ -1408,8 +1408,8 @@ packages:
|
|||
dependency: "direct main"
|
||||
description:
|
||||
path: "."
|
||||
ref: "93e2687bcc10fc7258c7dab038c363fc9ff8ba5d"
|
||||
resolved-ref: "93e2687bcc10fc7258c7dab038c363fc9ff8ba5d"
|
||||
ref: e4b08d2b8965a5ae49bd57f598fa9011dd0c25e9
|
||||
resolved-ref: e4b08d2b8965a5ae49bd57f598fa9011dd0c25e9
|
||||
url: "https://github.com/cypherstack/stack_wallet_backup.git"
|
||||
source: git
|
||||
version: "0.0.1"
|
||||
|
|
|
@ -59,7 +59,7 @@ dependencies:
|
|||
bip47:
|
||||
git:
|
||||
url: https://github.com/cypherstack/bip47.git
|
||||
ref: testing
|
||||
ref: 87bb760be323228aed6ca7bd4532a709a4f10690
|
||||
|
||||
# Utility plugins
|
||||
# provider: ^6.0.1
|
||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -363,6 +363,11 @@ class MockManager extends _i1.Mock implements _i11.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -324,6 +324,11 @@ class MockManager extends _i1.Mock implements _i9.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -322,6 +322,11 @@ class MockManager extends _i1.Mock implements _i9.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -631,6 +631,11 @@ class MockManager extends _i1.Mock implements _i12.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -418,6 +418,11 @@ class MockManager extends _i1.Mock implements _i9.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -418,6 +418,11 @@ class MockManager extends _i1.Mock implements _i9.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -418,6 +418,11 @@ class MockManager extends _i1.Mock implements _i9.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -193,6 +193,11 @@ class MockManager extends _i1.Mock implements _i5.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -416,6 +416,11 @@ class MockManager extends _i1.Mock implements _i9.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -631,6 +631,11 @@ class MockManager extends _i1.Mock implements _i12.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -472,6 +472,11 @@ class MockManager extends _i1.Mock implements _i12.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -193,6 +193,11 @@ class MockManager extends _i1.Mock implements _i5.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -193,6 +193,11 @@ class MockManager extends _i1.Mock implements _i5.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -408,6 +408,11 @@ class MockManager extends _i1.Mock implements _i11.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -408,6 +408,11 @@ class MockManager extends _i1.Mock implements _i11.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -193,6 +193,11 @@ class MockManager extends _i1.Mock implements _i5.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -193,6 +193,11 @@ class MockManager extends _i1.Mock implements _i5.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -416,6 +416,11 @@ class MockManager extends _i1.Mock implements _i9.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -673,6 +673,11 @@ class MockManager extends _i1.Mock implements _i15.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -416,6 +416,11 @@ class MockManager extends _i1.Mock implements _i9.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -195,6 +195,11 @@ class MockManager extends _i1.Mock implements _i5.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -194,6 +194,11 @@ class MockManager extends _i1.Mock implements _i5.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -193,6 +193,11 @@ class MockManager extends _i1.Mock implements _i5.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -235,6 +235,11 @@ class MockManager extends _i1.Mock implements _i8.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -195,6 +195,11 @@ class MockManager extends _i1.Mock implements _i5.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -11,6 +11,7 @@ import 'package:stackwallet/models/paymint/fee_object_model.dart';
|
|||
import 'package:stackwallet/services/coins/bitcoin/bitcoin_wallet.dart';
|
||||
import 'package:stackwallet/services/transaction_notification_tracker.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/derive_path_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/flutter_secure_storage_interface.dart';
|
||||
|
||||
import 'bitcoin_wallet_test.mocks.dart';
|
||||
|
@ -39,12 +40,6 @@ void main() async {
|
|||
});
|
||||
});
|
||||
|
||||
test("bitcoin DerivePathType enum", () {
|
||||
expect(DerivePathType.values.length, 3);
|
||||
expect(DerivePathType.values.toString(),
|
||||
"[DerivePathType.bip44, DerivePathType.bip49, DerivePathType.bip84]");
|
||||
});
|
||||
|
||||
group("bip32 node/root", () {
|
||||
test("getBip32Root", () {
|
||||
final root = getBip32Root(TEST_MNEMONIC, bitcoin);
|
||||
|
|
|
@ -11,6 +11,7 @@ import 'package:stackwallet/models/paymint/fee_object_model.dart';
|
|||
import 'package:stackwallet/services/coins/bitcoincash/bitcoincash_wallet.dart';
|
||||
import 'package:stackwallet/services/transaction_notification_tracker.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/derive_path_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/flutter_secure_storage_interface.dart';
|
||||
|
||||
import 'bitcoincash_wallet_test.mocks.dart';
|
||||
|
@ -40,12 +41,6 @@ void main() async {
|
|||
});
|
||||
});
|
||||
|
||||
test("bitcoincash DerivePathType enum", () {
|
||||
expect(DerivePathType.values.length, 2);
|
||||
expect(DerivePathType.values.toString(),
|
||||
"[DerivePathType.bip44, DerivePathType.bip49]");
|
||||
});
|
||||
|
||||
group("bip32 node/root", () {
|
||||
test("getBip32Root", () {
|
||||
final root = getBip32Root(TEST_MNEMONIC, bitcoincash);
|
||||
|
|
|
@ -11,6 +11,7 @@ import 'package:stackwallet/models/paymint/fee_object_model.dart';
|
|||
import 'package:stackwallet/services/coins/dogecoin/dogecoin_wallet.dart';
|
||||
import 'package:stackwallet/services/transaction_notification_tracker.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/derive_path_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/flutter_secure_storage_interface.dart';
|
||||
|
||||
import 'dogecoin_wallet_test.mocks.dart';
|
||||
|
@ -39,11 +40,6 @@ void main() {
|
|||
});
|
||||
});
|
||||
|
||||
test("dogecoin DerivePathType enum", () {
|
||||
expect(DerivePathType.values.length, 1);
|
||||
expect(DerivePathType.values.toString(), "[DerivePathType.bip44]");
|
||||
});
|
||||
|
||||
group("bip32 node/root", () {
|
||||
test("getBip32Root", () {
|
||||
final root = getBip32Root(TEST_MNEMONIC, dogecoin);
|
||||
|
|
|
@ -10,6 +10,7 @@ import 'package:stackwallet/models/paymint/fee_object_model.dart';
|
|||
import 'package:stackwallet/services/coins/namecoin/namecoin_wallet.dart';
|
||||
import 'package:stackwallet/services/transaction_notification_tracker.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/derive_path_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/flutter_secure_storage_interface.dart';
|
||||
|
||||
import 'namecoin_wallet_test.mocks.dart';
|
||||
|
@ -38,12 +39,6 @@ void main() {
|
|||
});
|
||||
});
|
||||
|
||||
test("namecoin DerivePathType enum", () {
|
||||
expect(DerivePathType.values.length, 3);
|
||||
expect(DerivePathType.values.toString(),
|
||||
"[DerivePathType.bip44, DerivePathType.bip49, DerivePathType.bip84]");
|
||||
});
|
||||
|
||||
group("bip32 node/root", () {
|
||||
test("getBip32Root", () {
|
||||
final root = getBip32Root(TEST_MNEMONIC, namecoin);
|
||||
|
|
|
@ -10,6 +10,7 @@ import 'package:stackwallet/models/paymint/fee_object_model.dart';
|
|||
import 'package:stackwallet/services/coins/particl/particl_wallet.dart';
|
||||
import 'package:stackwallet/services/transaction_notification_tracker.dart';
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart';
|
||||
import 'package:stackwallet/utilities/enums/derive_path_type_enum.dart';
|
||||
import 'package:stackwallet/utilities/flutter_secure_storage_interface.dart';
|
||||
|
||||
import 'particl_wallet_test.mocks.dart';
|
||||
|
@ -39,12 +40,6 @@ void main() {
|
|||
});
|
||||
});
|
||||
|
||||
test("particl DerivePathType enum", () {
|
||||
expect(DerivePathType.values.length, 2);
|
||||
expect(DerivePathType.values.toString(),
|
||||
"[DerivePathType.bip44, DerivePathType.bip84]");
|
||||
});
|
||||
|
||||
group("bip32 node/root", () {
|
||||
test("getBip32Root", () {
|
||||
final root = getBip32Root(TEST_MNEMONIC, particl);
|
||||
|
|
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
|
@ -538,6 +538,11 @@ class MockManager extends _i1.Mock implements _i6.Manager {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
bool get hasPaynymSupport => (super.noSuchMethod(
|
||||
Invocation.getter(#hasPaynymSupport),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
bool get hasListeners => (super.noSuchMethod(
|
||||
Invocation.getter(#hasListeners),
|
||||
returnValue: false,
|
||||
|
|
|
@ -3,8 +3,8 @@
|
|||
// Do not manually edit this file.
|
||||
|
||||
// ignore_for_file: no_leading_underscores_for_library_prefixes
|
||||
import 'dart:async' as _i15;
|
||||
import 'dart:ui' as _i17;
|
||||
import 'dart:async' as _i16;
|
||||
import 'dart:ui' as _i18;
|
||||
|
||||
import 'package:flutter/foundation.dart' as _i4;
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart' as _i5;
|
||||
|
@ -13,18 +13,20 @@ import 'package:stackwallet/db/main_db.dart' as _i12;
|
|||
import 'package:stackwallet/electrumx_rpc/cached_electrumx.dart' as _i10;
|
||||
import 'package:stackwallet/electrumx_rpc/electrumx.dart' as _i9;
|
||||
import 'package:stackwallet/models/balance.dart' as _i11;
|
||||
import 'package:stackwallet/models/isar/models/isar_models.dart' as _i19;
|
||||
import 'package:stackwallet/models/isar/models/isar_models.dart' as _i20;
|
||||
import 'package:stackwallet/models/paymint/fee_object_model.dart' as _i8;
|
||||
import 'package:stackwallet/services/coins/bitcoin/bitcoin_wallet.dart' as _i18;
|
||||
import 'package:stackwallet/services/coins/bitcoin/bitcoin_wallet.dart' as _i19;
|
||||
import 'package:stackwallet/services/coins/manager.dart' as _i6;
|
||||
import 'package:stackwallet/services/locale_service.dart' as _i20;
|
||||
import 'package:stackwallet/services/locale_service.dart' as _i22;
|
||||
import 'package:stackwallet/services/node_service.dart' as _i3;
|
||||
import 'package:stackwallet/services/transaction_notification_tracker.dart'
|
||||
as _i7;
|
||||
import 'package:stackwallet/services/wallets.dart' as _i13;
|
||||
import 'package:stackwallet/services/wallets.dart' as _i14;
|
||||
import 'package:stackwallet/services/wallets_service.dart' as _i2;
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart' as _i14;
|
||||
import 'package:stackwallet/utilities/prefs.dart' as _i16;
|
||||
import 'package:stackwallet/utilities/enums/coin_enum.dart' as _i15;
|
||||
import 'package:stackwallet/utilities/enums/derive_path_type_enum.dart' as _i21;
|
||||
import 'package:stackwallet/utilities/prefs.dart' as _i17;
|
||||
import 'package:tuple/tuple.dart' as _i13;
|
||||
|
||||
// ignore_for_file: type=lint
|
||||
// ignore_for_file: avoid_redundant_argument_values
|
||||
|
@ -151,10 +153,21 @@ class _FakeElectrumXNode_10 extends _i1.SmartFake implements _i9.ElectrumXNode {
|
|||
);
|
||||
}
|
||||
|
||||
class _FakeTuple4_11<T1, T2, T3, T4> extends _i1.SmartFake
|
||||
implements _i13.Tuple4<T1, T2, T3, T4> {
|
||||
_FakeTuple4_11(
|
||||
Object parent,
|
||||
Invocation parentInvocation,
|
||||
) : super(
|
||||
parent,
|
||||
parentInvocation,
|
||||
);
|
||||
}
|
||||
|
||||
/// A class which mocks [Wallets].
|
||||
///
|
||||
/// See the documentation for Mockito's code generation for more information.
|
||||
class MockWallets extends _i1.Mock implements _i13.Wallets {
|
||||
class MockWallets extends _i1.Mock implements _i14.Wallets {
|
||||
MockWallets() {
|
||||
_i1.throwOnMissingStub(this);
|
||||
}
|
||||
|
@ -221,7 +234,7 @@ class MockWallets extends _i1.Mock implements _i13.Wallets {
|
|||
returnValueForMissingStub: null,
|
||||
);
|
||||
@override
|
||||
List<String> getWalletIdsFor({required _i14.Coin? coin}) =>
|
||||
List<String> getWalletIdsFor({required _i15.Coin? coin}) =>
|
||||
(super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#getWalletIdsFor,
|
||||
|
@ -231,18 +244,18 @@ class MockWallets extends _i1.Mock implements _i13.Wallets {
|
|||
returnValue: <String>[],
|
||||
) as List<String>);
|
||||
@override
|
||||
Map<_i14.Coin, List<_i5.ChangeNotifierProvider<_i6.Manager>>>
|
||||
Map<_i15.Coin, List<_i5.ChangeNotifierProvider<_i6.Manager>>>
|
||||
getManagerProvidersByCoin() => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#getManagerProvidersByCoin,
|
||||
[],
|
||||
),
|
||||
returnValue: <_i14.Coin,
|
||||
returnValue: <_i15.Coin,
|
||||
List<_i5.ChangeNotifierProvider<_i6.Manager>>>{},
|
||||
) as Map<_i14.Coin, List<_i5.ChangeNotifierProvider<_i6.Manager>>>);
|
||||
) as Map<_i15.Coin, List<_i5.ChangeNotifierProvider<_i6.Manager>>>);
|
||||
@override
|
||||
List<_i5.ChangeNotifierProvider<_i6.Manager>> getManagerProvidersForCoin(
|
||||
_i14.Coin? coin) =>
|
||||
_i15.Coin? coin) =>
|
||||
(super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#getManagerProvidersForCoin,
|
||||
|
@ -306,17 +319,17 @@ class MockWallets extends _i1.Mock implements _i13.Wallets {
|
|||
returnValueForMissingStub: null,
|
||||
);
|
||||
@override
|
||||
_i15.Future<void> load(_i16.Prefs? prefs) => (super.noSuchMethod(
|
||||
_i16.Future<void> load(_i17.Prefs? prefs) => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#load,
|
||||
[prefs],
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
_i15.Future<void> loadAfterStackRestore(
|
||||
_i16.Prefs? prefs,
|
||||
_i16.Future<void> loadAfterStackRestore(
|
||||
_i17.Prefs? prefs,
|
||||
List<_i6.Manager>? managers,
|
||||
) =>
|
||||
(super.noSuchMethod(
|
||||
|
@ -327,11 +340,11 @@ class MockWallets extends _i1.Mock implements _i13.Wallets {
|
|||
managers,
|
||||
],
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
void addListener(_i17.VoidCallback? listener) => super.noSuchMethod(
|
||||
void addListener(_i18.VoidCallback? listener) => super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#addListener,
|
||||
[listener],
|
||||
|
@ -339,7 +352,7 @@ class MockWallets extends _i1.Mock implements _i13.Wallets {
|
|||
returnValueForMissingStub: null,
|
||||
);
|
||||
@override
|
||||
void removeListener(_i17.VoidCallback? listener) => super.noSuchMethod(
|
||||
void removeListener(_i18.VoidCallback? listener) => super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#removeListener,
|
||||
[listener],
|
||||
|
@ -359,13 +372,13 @@ class MockWallets extends _i1.Mock implements _i13.Wallets {
|
|||
/// A class which mocks [BitcoinWallet].
|
||||
///
|
||||
/// See the documentation for Mockito's code generation for more information.
|
||||
class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
||||
class MockBitcoinWallet extends _i1.Mock implements _i19.BitcoinWallet {
|
||||
MockBitcoinWallet() {
|
||||
_i1.throwOnMissingStub(this);
|
||||
}
|
||||
|
||||
@override
|
||||
set timer(_i15.Timer? _timer) => super.noSuchMethod(
|
||||
set timer(_i16.Timer? _timer) => super.noSuchMethod(
|
||||
Invocation.setter(
|
||||
#timer,
|
||||
_timer,
|
||||
|
@ -442,59 +455,59 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
_i14.Coin get coin => (super.noSuchMethod(
|
||||
_i15.Coin get coin => (super.noSuchMethod(
|
||||
Invocation.getter(#coin),
|
||||
returnValue: _i14.Coin.bitcoin,
|
||||
) as _i14.Coin);
|
||||
returnValue: _i15.Coin.bitcoin,
|
||||
) as _i15.Coin);
|
||||
@override
|
||||
_i15.Future<List<_i19.UTXO>> get utxos => (super.noSuchMethod(
|
||||
_i16.Future<List<_i20.UTXO>> get utxos => (super.noSuchMethod(
|
||||
Invocation.getter(#utxos),
|
||||
returnValue: _i15.Future<List<_i19.UTXO>>.value(<_i19.UTXO>[]),
|
||||
) as _i15.Future<List<_i19.UTXO>>);
|
||||
returnValue: _i16.Future<List<_i20.UTXO>>.value(<_i20.UTXO>[]),
|
||||
) as _i16.Future<List<_i20.UTXO>>);
|
||||
@override
|
||||
_i15.Future<List<_i19.Transaction>> get transactions => (super.noSuchMethod(
|
||||
_i16.Future<List<_i20.Transaction>> get transactions => (super.noSuchMethod(
|
||||
Invocation.getter(#transactions),
|
||||
returnValue:
|
||||
_i15.Future<List<_i19.Transaction>>.value(<_i19.Transaction>[]),
|
||||
) as _i15.Future<List<_i19.Transaction>>);
|
||||
_i16.Future<List<_i20.Transaction>>.value(<_i20.Transaction>[]),
|
||||
) as _i16.Future<List<_i20.Transaction>>);
|
||||
@override
|
||||
_i15.Future<String> get currentReceivingAddress => (super.noSuchMethod(
|
||||
_i16.Future<String> get currentReceivingAddress => (super.noSuchMethod(
|
||||
Invocation.getter(#currentReceivingAddress),
|
||||
returnValue: _i15.Future<String>.value(''),
|
||||
) as _i15.Future<String>);
|
||||
returnValue: _i16.Future<String>.value(''),
|
||||
) as _i16.Future<String>);
|
||||
@override
|
||||
_i15.Future<String> get currentChangeAddress => (super.noSuchMethod(
|
||||
_i16.Future<String> get currentChangeAddress => (super.noSuchMethod(
|
||||
Invocation.getter(#currentChangeAddress),
|
||||
returnValue: _i15.Future<String>.value(''),
|
||||
) as _i15.Future<String>);
|
||||
returnValue: _i16.Future<String>.value(''),
|
||||
) as _i16.Future<String>);
|
||||
@override
|
||||
bool get hasCalledExit => (super.noSuchMethod(
|
||||
Invocation.getter(#hasCalledExit),
|
||||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
_i15.Future<_i8.FeeObject> get fees => (super.noSuchMethod(
|
||||
_i16.Future<_i8.FeeObject> get fees => (super.noSuchMethod(
|
||||
Invocation.getter(#fees),
|
||||
returnValue: _i15.Future<_i8.FeeObject>.value(_FakeFeeObject_5(
|
||||
returnValue: _i16.Future<_i8.FeeObject>.value(_FakeFeeObject_5(
|
||||
this,
|
||||
Invocation.getter(#fees),
|
||||
)),
|
||||
) as _i15.Future<_i8.FeeObject>);
|
||||
) as _i16.Future<_i8.FeeObject>);
|
||||
@override
|
||||
_i15.Future<int> get maxFee => (super.noSuchMethod(
|
||||
_i16.Future<int> get maxFee => (super.noSuchMethod(
|
||||
Invocation.getter(#maxFee),
|
||||
returnValue: _i15.Future<int>.value(0),
|
||||
) as _i15.Future<int>);
|
||||
returnValue: _i16.Future<int>.value(0),
|
||||
) as _i16.Future<int>);
|
||||
@override
|
||||
_i15.Future<List<String>> get mnemonic => (super.noSuchMethod(
|
||||
_i16.Future<List<String>> get mnemonic => (super.noSuchMethod(
|
||||
Invocation.getter(#mnemonic),
|
||||
returnValue: _i15.Future<List<String>>.value(<String>[]),
|
||||
) as _i15.Future<List<String>>);
|
||||
returnValue: _i16.Future<List<String>>.value(<String>[]),
|
||||
) as _i16.Future<List<String>>);
|
||||
@override
|
||||
_i15.Future<int> get chainHeight => (super.noSuchMethod(
|
||||
_i16.Future<int> get chainHeight => (super.noSuchMethod(
|
||||
Invocation.getter(#chainHeight),
|
||||
returnValue: _i15.Future<int>.value(0),
|
||||
) as _i15.Future<int>);
|
||||
returnValue: _i16.Future<int>.value(0),
|
||||
) as _i16.Future<int>);
|
||||
@override
|
||||
int get storedChainHeight => (super.noSuchMethod(
|
||||
Invocation.getter(#storedChainHeight),
|
||||
|
@ -583,26 +596,26 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
),
|
||||
) as _i12.MainDB);
|
||||
@override
|
||||
_i15.Future<void> exit() => (super.noSuchMethod(
|
||||
_i16.Future<void> exit() => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#exit,
|
||||
[],
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
_i18.DerivePathType addressType({required String? address}) =>
|
||||
_i21.DerivePathType addressType({required String? address}) =>
|
||||
(super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#addressType,
|
||||
[],
|
||||
{#address: address},
|
||||
),
|
||||
returnValue: _i18.DerivePathType.bip44,
|
||||
) as _i18.DerivePathType);
|
||||
returnValue: _i21.DerivePathType.bip44,
|
||||
) as _i21.DerivePathType);
|
||||
@override
|
||||
_i15.Future<void> recoverFromMnemonic({
|
||||
_i16.Future<void> recoverFromMnemonic({
|
||||
required String? mnemonic,
|
||||
required int? maxUnusedAddressGap,
|
||||
required int? maxNumberOfIndexesToCheck,
|
||||
|
@ -619,47 +632,47 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
#height: height,
|
||||
},
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
_i15.Future<void> getTransactionCacheEarly(List<String>? allAddresses) =>
|
||||
_i16.Future<void> getTransactionCacheEarly(List<String>? allAddresses) =>
|
||||
(super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#getTransactionCacheEarly,
|
||||
[allAddresses],
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
_i15.Future<bool> refreshIfThereIsNewData() => (super.noSuchMethod(
|
||||
_i16.Future<bool> refreshIfThereIsNewData() => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#refreshIfThereIsNewData,
|
||||
[],
|
||||
),
|
||||
returnValue: _i15.Future<bool>.value(false),
|
||||
) as _i15.Future<bool>);
|
||||
returnValue: _i16.Future<bool>.value(false),
|
||||
) as _i16.Future<bool>);
|
||||
@override
|
||||
_i15.Future<void> getAllTxsToWatch() => (super.noSuchMethod(
|
||||
_i16.Future<void> getAllTxsToWatch() => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#getAllTxsToWatch,
|
||||
[],
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
_i15.Future<void> refresh() => (super.noSuchMethod(
|
||||
_i16.Future<void> refresh() => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#refresh,
|
||||
[],
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
_i15.Future<Map<String, dynamic>> prepareSend({
|
||||
_i16.Future<Map<String, dynamic>> prepareSend({
|
||||
required String? address,
|
||||
required int? satoshiAmount,
|
||||
Map<String, dynamic>? args,
|
||||
|
@ -675,26 +688,26 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
},
|
||||
),
|
||||
returnValue:
|
||||
_i15.Future<Map<String, dynamic>>.value(<String, dynamic>{}),
|
||||
) as _i15.Future<Map<String, dynamic>>);
|
||||
_i16.Future<Map<String, dynamic>>.value(<String, dynamic>{}),
|
||||
) as _i16.Future<Map<String, dynamic>>);
|
||||
@override
|
||||
_i15.Future<String> confirmSend({required Map<String, dynamic>? txData}) =>
|
||||
_i16.Future<String> confirmSend({required Map<String, dynamic>? txData}) =>
|
||||
(super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#confirmSend,
|
||||
[],
|
||||
{#txData: txData},
|
||||
),
|
||||
returnValue: _i15.Future<String>.value(''),
|
||||
) as _i15.Future<String>);
|
||||
returnValue: _i16.Future<String>.value(''),
|
||||
) as _i16.Future<String>);
|
||||
@override
|
||||
_i15.Future<bool> testNetworkConnection() => (super.noSuchMethod(
|
||||
_i16.Future<bool> testNetworkConnection() => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#testNetworkConnection,
|
||||
[],
|
||||
),
|
||||
returnValue: _i15.Future<bool>.value(false),
|
||||
) as _i15.Future<bool>);
|
||||
returnValue: _i16.Future<bool>.value(false),
|
||||
) as _i16.Future<bool>);
|
||||
@override
|
||||
void startNetworkAlivePinging() => super.noSuchMethod(
|
||||
Invocation.method(
|
||||
|
@ -712,33 +725,33 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
returnValueForMissingStub: null,
|
||||
);
|
||||
@override
|
||||
_i15.Future<void> initializeNew() => (super.noSuchMethod(
|
||||
_i16.Future<void> initializeNew() => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#initializeNew,
|
||||
[],
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
_i15.Future<void> initializeExisting() => (super.noSuchMethod(
|
||||
_i16.Future<void> initializeExisting() => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#initializeExisting,
|
||||
[],
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
_i15.Future<void> updateSentCachedTxData(Map<String, dynamic>? txData) =>
|
||||
_i16.Future<void> updateSentCachedTxData(Map<String, dynamic>? txData) =>
|
||||
(super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#updateSentCachedTxData,
|
||||
[txData],
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
bool validateAddress(String? address) => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
|
@ -748,35 +761,35 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
_i15.Future<void> updateNode(bool? shouldRefresh) => (super.noSuchMethod(
|
||||
_i16.Future<void> updateNode(bool? shouldRefresh) => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#updateNode,
|
||||
[shouldRefresh],
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
_i15.Future<_i9.ElectrumXNode> getCurrentNode() => (super.noSuchMethod(
|
||||
_i16.Future<_i9.ElectrumXNode> getCurrentNode() => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#getCurrentNode,
|
||||
[],
|
||||
),
|
||||
returnValue: _i15.Future<_i9.ElectrumXNode>.value(_FakeElectrumXNode_10(
|
||||
returnValue: _i16.Future<_i9.ElectrumXNode>.value(_FakeElectrumXNode_10(
|
||||
this,
|
||||
Invocation.method(
|
||||
#getCurrentNode,
|
||||
[],
|
||||
),
|
||||
)),
|
||||
) as _i15.Future<_i9.ElectrumXNode>);
|
||||
) as _i16.Future<_i9.ElectrumXNode>);
|
||||
@override
|
||||
_i15.Future<void> addDerivation({
|
||||
_i16.Future<void> addDerivation({
|
||||
required int? chain,
|
||||
required String? address,
|
||||
required String? pubKey,
|
||||
required String? wif,
|
||||
required _i18.DerivePathType? derivePathType,
|
||||
required _i21.DerivePathType? derivePathType,
|
||||
}) =>
|
||||
(super.noSuchMethod(
|
||||
Invocation.method(
|
||||
|
@ -790,13 +803,13 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
#derivePathType: derivePathType,
|
||||
},
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
_i15.Future<void> addDerivations({
|
||||
_i16.Future<void> addDerivations({
|
||||
required int? chain,
|
||||
required _i18.DerivePathType? derivePathType,
|
||||
required _i21.DerivePathType? derivePathType,
|
||||
required Map<String, dynamic>? derivationsToAdd,
|
||||
}) =>
|
||||
(super.noSuchMethod(
|
||||
|
@ -809,50 +822,50 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
#derivationsToAdd: derivationsToAdd,
|
||||
},
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
_i15.Future<List<Map<String, dynamic>>> fastFetch(
|
||||
_i16.Future<List<Map<String, dynamic>>> fastFetch(
|
||||
List<String>? allTxHashes) =>
|
||||
(super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#fastFetch,
|
||||
[allTxHashes],
|
||||
),
|
||||
returnValue: _i15.Future<List<Map<String, dynamic>>>.value(
|
||||
returnValue: _i16.Future<List<Map<String, dynamic>>>.value(
|
||||
<Map<String, dynamic>>[]),
|
||||
) as _i15.Future<List<Map<String, dynamic>>>);
|
||||
) as _i16.Future<List<Map<String, dynamic>>>);
|
||||
@override
|
||||
_i15.Future<int> getTxCount({required String? address}) =>
|
||||
_i16.Future<int> getTxCount({required String? address}) =>
|
||||
(super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#getTxCount,
|
||||
[],
|
||||
{#address: address},
|
||||
),
|
||||
returnValue: _i15.Future<int>.value(0),
|
||||
) as _i15.Future<int>);
|
||||
returnValue: _i16.Future<int>.value(0),
|
||||
) as _i16.Future<int>);
|
||||
@override
|
||||
_i15.Future<void> checkCurrentReceivingAddressesForTransactions() =>
|
||||
_i16.Future<void> checkCurrentReceivingAddressesForTransactions() =>
|
||||
(super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#checkCurrentReceivingAddressesForTransactions,
|
||||
[],
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
_i15.Future<void> checkCurrentChangeAddressesForTransactions() =>
|
||||
_i16.Future<void> checkCurrentChangeAddressesForTransactions() =>
|
||||
(super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#checkCurrentChangeAddressesForTransactions,
|
||||
[],
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
int estimateTxFee({
|
||||
required int? vSize,
|
||||
|
@ -876,7 +889,7 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
String? _recipientAddress,
|
||||
bool? isSendAll, {
|
||||
int? additionalOutputs = 0,
|
||||
List<_i19.UTXO>? utxos,
|
||||
List<_i20.UTXO>? utxos,
|
||||
}) =>
|
||||
super.noSuchMethod(Invocation.method(
|
||||
#coinSelection,
|
||||
|
@ -892,19 +905,19 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
},
|
||||
));
|
||||
@override
|
||||
_i15.Future<Map<String, dynamic>> fetchBuildTxData(
|
||||
List<_i19.UTXO>? utxosToUse) =>
|
||||
_i16.Future<Map<String, dynamic>> fetchBuildTxData(
|
||||
List<_i20.UTXO>? utxosToUse) =>
|
||||
(super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#fetchBuildTxData,
|
||||
[utxosToUse],
|
||||
),
|
||||
returnValue:
|
||||
_i15.Future<Map<String, dynamic>>.value(<String, dynamic>{}),
|
||||
) as _i15.Future<Map<String, dynamic>>);
|
||||
_i16.Future<Map<String, dynamic>>.value(<String, dynamic>{}),
|
||||
) as _i16.Future<Map<String, dynamic>>);
|
||||
@override
|
||||
_i15.Future<Map<String, dynamic>> buildTransaction({
|
||||
required List<_i19.UTXO>? utxosToUse,
|
||||
_i16.Future<Map<String, dynamic>> buildTransaction({
|
||||
required List<_i20.UTXO>? utxosToUse,
|
||||
required Map<String, dynamic>? utxoSigningData,
|
||||
required List<String>? recipients,
|
||||
required List<int>? satoshiAmounts,
|
||||
|
@ -921,10 +934,10 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
},
|
||||
),
|
||||
returnValue:
|
||||
_i15.Future<Map<String, dynamic>>.value(<String, dynamic>{}),
|
||||
) as _i15.Future<Map<String, dynamic>>);
|
||||
_i16.Future<Map<String, dynamic>>.value(<String, dynamic>{}),
|
||||
) as _i16.Future<Map<String, dynamic>>);
|
||||
@override
|
||||
_i15.Future<void> fullRescan(
|
||||
_i16.Future<void> fullRescan(
|
||||
int? maxUnusedAddressGap,
|
||||
int? maxNumberOfIndexesToCheck,
|
||||
) =>
|
||||
|
@ -936,11 +949,11 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
maxNumberOfIndexesToCheck,
|
||||
],
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
_i15.Future<int> estimateFeeFor(
|
||||
_i16.Future<int> estimateFeeFor(
|
||||
int? satoshiAmount,
|
||||
int? feeRate,
|
||||
) =>
|
||||
|
@ -952,8 +965,8 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
feeRate,
|
||||
],
|
||||
),
|
||||
returnValue: _i15.Future<int>.value(0),
|
||||
) as _i15.Future<int>);
|
||||
returnValue: _i16.Future<int>.value(0),
|
||||
) as _i16.Future<int>);
|
||||
@override
|
||||
int roughFeeEstimate(
|
||||
int? inputCount,
|
||||
|
@ -972,25 +985,25 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
_i15.Future<int> sweepAllEstimate(int? feeRate) => (super.noSuchMethod(
|
||||
_i16.Future<int> sweepAllEstimate(int? feeRate) => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#sweepAllEstimate,
|
||||
[feeRate],
|
||||
),
|
||||
returnValue: _i15.Future<int>.value(0),
|
||||
) as _i15.Future<int>);
|
||||
returnValue: _i16.Future<int>.value(0),
|
||||
) as _i16.Future<int>);
|
||||
@override
|
||||
_i15.Future<bool> generateNewAddress() => (super.noSuchMethod(
|
||||
_i16.Future<bool> generateNewAddress() => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#generateNewAddress,
|
||||
[],
|
||||
),
|
||||
returnValue: _i15.Future<bool>.value(false),
|
||||
) as _i15.Future<bool>);
|
||||
returnValue: _i16.Future<bool>.value(false),
|
||||
) as _i16.Future<bool>);
|
||||
@override
|
||||
void initCache(
|
||||
String? walletId,
|
||||
_i14.Coin? coin,
|
||||
_i15.Coin? coin,
|
||||
) =>
|
||||
super.noSuchMethod(
|
||||
Invocation.method(
|
||||
|
@ -1003,14 +1016,14 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
returnValueForMissingStub: null,
|
||||
);
|
||||
@override
|
||||
_i15.Future<void> updateCachedId(String? id) => (super.noSuchMethod(
|
||||
_i16.Future<void> updateCachedId(String? id) => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#updateCachedId,
|
||||
[id],
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
int getCachedChainHeight() => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
|
@ -1020,14 +1033,14 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
returnValue: 0,
|
||||
) as int);
|
||||
@override
|
||||
_i15.Future<void> updateCachedChainHeight(int? height) => (super.noSuchMethod(
|
||||
_i16.Future<void> updateCachedChainHeight(int? height) => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#updateCachedChainHeight,
|
||||
[height],
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
bool getCachedIsFavorite() => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
|
@ -1037,15 +1050,15 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
_i15.Future<void> updateCachedIsFavorite(bool? isFavorite) =>
|
||||
_i16.Future<void> updateCachedIsFavorite(bool? isFavorite) =>
|
||||
(super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#updateCachedIsFavorite,
|
||||
[isFavorite],
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
_i11.Balance getCachedBalance() => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
|
@ -1061,15 +1074,15 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
),
|
||||
) as _i11.Balance);
|
||||
@override
|
||||
_i15.Future<void> updateCachedBalance(_i11.Balance? balance) =>
|
||||
_i16.Future<void> updateCachedBalance(_i11.Balance? balance) =>
|
||||
(super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#updateCachedBalance,
|
||||
[balance],
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
_i11.Balance getCachedBalanceSecondary() => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
|
@ -1085,15 +1098,15 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
),
|
||||
) as _i11.Balance);
|
||||
@override
|
||||
_i15.Future<void> updateCachedBalanceSecondary(_i11.Balance? balance) =>
|
||||
_i16.Future<void> updateCachedBalanceSecondary(_i11.Balance? balance) =>
|
||||
(super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#updateCachedBalanceSecondary,
|
||||
[balance],
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
void initWalletDB({_i12.MainDB? mockableOverride}) => super.noSuchMethod(
|
||||
Invocation.method(
|
||||
|
@ -1103,12 +1116,55 @@ class MockBitcoinWallet extends _i1.Mock implements _i18.BitcoinWallet {
|
|||
),
|
||||
returnValueForMissingStub: null,
|
||||
);
|
||||
@override
|
||||
_i16.Future<
|
||||
_i13.Tuple4<_i20.Transaction, List<_i20.Output>, List<_i20.Input>,
|
||||
_i20.Address>> parseTransaction(
|
||||
Map<String, dynamic>? txData,
|
||||
dynamic electrumxClient,
|
||||
List<_i20.Address>? myAddresses,
|
||||
_i15.Coin? coin,
|
||||
int? minConfirms,
|
||||
String? walletId,
|
||||
) =>
|
||||
(super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#parseTransaction,
|
||||
[
|
||||
txData,
|
||||
electrumxClient,
|
||||
myAddresses,
|
||||
coin,
|
||||
minConfirms,
|
||||
walletId,
|
||||
],
|
||||
),
|
||||
returnValue: _i16.Future<
|
||||
_i13.Tuple4<_i20.Transaction, List<_i20.Output>, List<_i20.Input>,
|
||||
_i20.Address>>.value(_FakeTuple4_11<_i20.Transaction,
|
||||
List<_i20.Output>, List<_i20.Input>, _i20.Address>(
|
||||
this,
|
||||
Invocation.method(
|
||||
#parseTransaction,
|
||||
[
|
||||
txData,
|
||||
electrumxClient,
|
||||
myAddresses,
|
||||
coin,
|
||||
minConfirms,
|
||||
walletId,
|
||||
],
|
||||
),
|
||||
)),
|
||||
) as _i16.Future<
|
||||
_i13.Tuple4<_i20.Transaction, List<_i20.Output>, List<_i20.Input>,
|
||||
_i20.Address>>);
|
||||
}
|
||||
|
||||
/// A class which mocks [LocaleService].
|
||||
///
|
||||
/// See the documentation for Mockito's code generation for more information.
|
||||
class MockLocaleService extends _i1.Mock implements _i20.LocaleService {
|
||||
class MockLocaleService extends _i1.Mock implements _i22.LocaleService {
|
||||
MockLocaleService() {
|
||||
_i1.throwOnMissingStub(this);
|
||||
}
|
||||
|
@ -1124,17 +1180,17 @@ class MockLocaleService extends _i1.Mock implements _i20.LocaleService {
|
|||
returnValue: false,
|
||||
) as bool);
|
||||
@override
|
||||
_i15.Future<void> loadLocale({bool? notify = true}) => (super.noSuchMethod(
|
||||
_i16.Future<void> loadLocale({bool? notify = true}) => (super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#loadLocale,
|
||||
[],
|
||||
{#notify: notify},
|
||||
),
|
||||
returnValue: _i15.Future<void>.value(),
|
||||
returnValueForMissingStub: _i15.Future<void>.value(),
|
||||
) as _i15.Future<void>);
|
||||
returnValue: _i16.Future<void>.value(),
|
||||
returnValueForMissingStub: _i16.Future<void>.value(),
|
||||
) as _i16.Future<void>);
|
||||
@override
|
||||
void addListener(_i17.VoidCallback? listener) => super.noSuchMethod(
|
||||
void addListener(_i18.VoidCallback? listener) => super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#addListener,
|
||||
[listener],
|
||||
|
@ -1142,7 +1198,7 @@ class MockLocaleService extends _i1.Mock implements _i20.LocaleService {
|
|||
returnValueForMissingStub: null,
|
||||
);
|
||||
@override
|
||||
void removeListener(_i17.VoidCallback? listener) => super.noSuchMethod(
|
||||
void removeListener(_i18.VoidCallback? listener) => super.noSuchMethod(
|
||||
Invocation.method(
|
||||
#removeListener,
|
||||
[listener],
|
||||
|
|
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
Loading…
Reference in a new issue