CW-371-Restore-height-issue-with-QR-code-Wallet-incorrectly-assigns-today's-restore-height-to-legacy-wallets (#925)

* fix height for legacy wallets * get height by first tx under singular seed

Serhii committed May 25, 2023 at 00:00 UTC c835059d139f39482bc3a1e3f06a0e509c417859
2 files changed +52 -15
cw_core/lib/get_height_by_date.dart
+2
@@ -122,6 +122,8 @@ int getMoneroHeigthByDate({required DateTime date}) {
122 }
123
124 const havenDates = {
125 + "2023-05": 1352995,
126 + "2023-04": 1331460,
127 "2023-03": 1309180,
128 "2023-01": 1266810,
129 "2022-12": 1244510,
lib/view_model/wallet_keys_view_model.dart
+50 -15
@@ -1,4 +1,6 @@
1 import 'package:cake_wallet/store/app_store.dart';
2 +import 'package:cw_core/transaction_direction.dart';
3 +import 'package:cw_core/transaction_info.dart';
4 import 'package:cw_core/wallet_type.dart';
5 import 'package:mobx/mobx.dart';
6 import 'package:cake_wallet/generated/i18n.dart';
@@ -19,12 +21,26 @@ abstract class WalletKeysViewModelBase with Store {
21 ? S.current.wallet_seed
22 : S.current.wallet_keys,
23 _restoreHeight = _appStore.wallet!.walletInfo.restoreHeight,
24 + _restoreHeightByTransactions = 0,
25 items = ObservableList<StandartListItem>() {
26 _populateItems();
27
28 reaction((_) => _appStore.wallet, (WalletBase? _wallet) {
29 _populateItems();
30 });
31 +
32 + if (_appStore.wallet!.type == WalletType.monero || _appStore.wallet!.type == WalletType.haven) {
33 + final accountTransactions = _getWalletTransactions(_appStore.wallet!);
34 + if (accountTransactions.isNotEmpty) {
35 + final incomingAccountTransactions =
36 + accountTransactions.where((tx) => tx.direction == TransactionDirection.incoming);
37 + if (incomingAccountTransactions.isNotEmpty) {
38 + incomingAccountTransactions.toList().sort((a, b) => a.date.compareTo(b.date));
39 + _restoreHeightByTransactions = _getRestoreHeightByTransactions(
40 + _appStore.wallet!.type, incomingAccountTransactions.first.date);
41 + }
42 + }
43 + }
44 }
45
46 final ObservableList<StandartListItem> items;
@@ -35,6 +51,8 @@ abstract class WalletKeysViewModelBase with Store {
51
52 final int _restoreHeight;
53
54 + int _restoreHeightByTransactions;
55 +
56 void _populateItems() {
57 items.clear();
58
@@ -78,7 +96,7 @@ abstract class WalletKeysViewModelBase with Store {
96 }
97 }
98
81 - Future<int?> currentHeight() async {
99 + Future<int?> _currentHeight() async {
100 if (_appStore.wallet!.type == WalletType.haven) {
101 return await haven!.getCurrentHeight();
102 }
@@ -88,7 +106,6 @@ abstract class WalletKeysViewModelBase with Store {
106 return null;
107 }
108
91 -
109 String get _scheme {
110 switch (_appStore.wallet!.type) {
111 case WalletType.monero:
@@ -105,14 +122,14 @@ abstract class WalletKeysViewModelBase with Store {
122 }
123
124 Future<String?> get restoreHeight async {
108 - if (_restoreHeight != 0) {
109 - return _restoreHeight.toString();
110 - }
111 - final _currentHeight = await currentHeight();
112 - if (_currentHeight == null) {
113 - return null;
114 - }
115 - return ((_currentHeight / 1000).floor() * 1000).toString();
125 + if (_restoreHeightByTransactions != 0)
126 + return getRoundedRestoreHeight(_restoreHeightByTransactions);
127 + if (_restoreHeight != 0) return _restoreHeight.toString();
128 +
129 + final currentHeight = await _currentHeight();
130 + if (currentHeight == null) return null;
131 +
132 + return getRoundedRestoreHeight(currentHeight);
133 }
134
135 Future<Map<String, String>> get _queryParams async {
@@ -123,10 +140,28 @@ abstract class WalletKeysViewModelBase with Store {
140 };
141 }
142
126 - Future<Uri> get url async {
127 - return Uri(
128 - scheme: _scheme,
129 - queryParameters: await _queryParams,
130 - );
143 + Future<Uri> get url async => Uri(
144 + scheme: _scheme,
145 + queryParameters: await _queryParams,
146 + );
147 +
148 + List<TransactionInfo> _getWalletTransactions(WalletBase wallet) {
149 + if (wallet.type == WalletType.monero) {
150 + return monero!.getTransactionHistory(wallet).transactions.values.toList();
151 + } else if (wallet.type == WalletType.haven) {
152 + return haven!.getTransactionHistory(wallet).transactions.values.toList();
153 + }
154 + return [];
155 }
156 +
157 + int _getRestoreHeightByTransactions(WalletType type, DateTime date) {
158 + if (type == WalletType.monero) {
159 + return monero!.getHeigthByDate(date: date);
160 + } else if (type == WalletType.haven) {
161 + return haven!.getHeightByDate(date: date);
162 + }
163 + return 0;
164 + }
165 +
166 + String getRoundedRestoreHeight(int height) => ((height / 1000).floor() * 1000).toString();
167 }