From 71114605537f43dafe281da14fbd605f5ec18213 Mon Sep 17 00:00:00 2001
From: acrespo <alvaro.andres.crespo@gmail.com>
Date: Fri, 2 Aug 2024 19:13:09 -0300
Subject: [PATCH] Apollo: Release source code for 52.1

---
 android/CHANGELOG.md                          |  21 ++
 android/Dockerfile                            |   2 +-
 android/apollo/build.gradle                   |  15 +-
 .../data/analytics/AnalyticsProvider.kt       |   2 +-
 .../java/io/muun/apollo/data/external/Gen.kt  |  17 --
 .../os/BackgroundExecutionMetricsProvider.kt  |  12 +-
 .../apollo/data/os/DateTimeZoneProvider.kt    |  37 +++
 .../SecureStoragePreferences.java             |  11 +-
 .../secure_storage/SecureStorageProvider.java |   4 +
 .../data/preferences/UserRepository.java      |  75 +++--
 .../SafeCurrencyUnitDeserializer.kt           |  33 +++
 .../serialization/SerializationUtils.java     |  52 ++--
 .../java/io/muun/apollo/domain/Flags.java     |   2 -
 .../apollo/domain/action/LogoutActions.java   |   9 +-
 .../operation/ResolveBitcoinUriAction.java    |  24 +-
 .../operation/ResolveLnInvoiceAction.kt       |  22 +-
 .../operation/ResolveMuunUriAction.java       |  29 +-
 .../apollo/domain/libwallet/BitcoinUri.kt     |  14 +
 .../domain/model/NextTransactionSize.java     |   2 +-
 .../apollo/domain/model/PaymentRequest.kt     |  25 --
 .../muun/apollo/domain/model/user/User.java   |   3 +
 .../domain/selector/LogoutOptionsSelector.kt  |  18 +-
 .../domain/utils/DeprecatedCurrencyUnit.kt    |  44 +++
 .../io/muun/apollo/domain/utils/Extensions.kt |   8 +
 .../domain/action/OperationActionsTest.java   |  34 +--
 android/apolloui/build.gradle                 |  16 +-
 .../presentation/LoginAndSignUpTests.kt       |  51 +++-
 .../muun/apollo/presentation/ReceiveTests.kt  |  27 ++
 .../muun/apollo/presentation/SettingsTests.kt |  37 ++-
 .../java/io/muun/apollo/utils/AutoFlows.kt    | 136 ++++++++-
 .../utils/screens/ChangePasswordScreen.kt     |   7 +-
 .../apollo/utils/screens/ReceiveScreen.kt     | 176 +++++++++++-
 .../apollo/utils/screens/SettingsScreen.kt    |  16 +-
 .../muun/apollo/utils/screens/SignInScreen.kt |  29 +-
 .../apollo/presentation/app/Navigator.java    |   2 +-
 .../presentation/ui/base/BaseActivity.java    |   2 +-
 .../presentation/ui/base/BaseFragment.java    |   4 +-
 .../ek_save/EmergencyKitSaveFragment.kt       |   2 +-
 .../ui/fragments/home/HomeFragment.kt         |   4 +-
 .../fragments/manual_fee/ManualFeeFragment.kt |  31 --
 .../ui/fragments/settings/SettingsFragment.kt |   4 +-
 .../fragments/settings/SettingsPresenter.kt   |   4 +-
 .../ui/fragments/settings/SettingsView.java   |   2 +-
 .../ui/launcher/LauncherPresenter.java        |   4 +
 .../edit_password/ChangePasswordFragment.kt   |  64 ++++-
 .../edit_password/ChangePasswordPresenter.kt  |   7 +-
 .../edit_password/ChangePasswordView.java     |   2 +
 .../presentation/ui/view/FeeManualInput.java  |  18 +-
 .../res/layout/change_password_fragment.xml   |  15 +-
 .../layout/manual_fee_selection_fragment.xml  |  16 --
 .../src/main/res/values-es/strings.xml        |   2 +-
 .../apolloui/src/main/res/values/strings.xml  |   2 +-
 build.gradle                                  |   2 +-
 .../java/io/muun/common/api/SessionJson.java  |   2 +-
 .../io/muun/common/api/error/ErrorCode.java   |   4 +-
 .../io/muun/common/utils/Preconditions.java   |  17 +-
 gradle/wrapper/gradle-wrapper.jar             | Bin 55616 -> 60756 bytes
 gradle/wrapper/gradle-wrapper.properties      |   2 +-
 gradlew                                       | 266 +++++++++++-------
 gradlew.bat                                   |  37 +--
 libwallet/go.mod                              |  11 +-
 libwallet/go.sum                              | 228 +++++----------
 libwallet/newop/state.go                      |  15 +-
 libwallet/operation/payment_analyzer.go       |  27 --
 libwallet/operation/payment_analyzer_test.go  | 167 -----------
 tools/bootstrap-gomobile.sh                   |   2 +-
 tools/libwallet-android.sh                    |  15 +-
 67 files changed, 1117 insertions(+), 873 deletions(-)
 create mode 100644 android/apollo/src/main/java/io/muun/apollo/data/os/DateTimeZoneProvider.kt
 create mode 100644 android/apollo/src/main/java/io/muun/apollo/data/serialization/SafeCurrencyUnitDeserializer.kt
 create mode 100644 android/apollo/src/main/java/io/muun/apollo/domain/utils/DeprecatedCurrencyUnit.kt
 create mode 100644 android/apolloui/src/androidTest/java/io/muun/apollo/presentation/ReceiveTests.kt

diff --git a/android/CHANGELOG.md b/android/CHANGELOG.md
index 228e10d7..775975ca 100644
--- a/android/CHANGELOG.md
+++ b/android/CHANGELOG.md
@@ -6,6 +6,27 @@ follow [https://changelog.md/](https://changelog.md/) guidelines.
 
 ## [Unreleased]
 
+## [52.1] - 2024-08-02
+
+### ADDED
+
+- Background notification processing reliability improvements
+- Wallet delete checks client-side (e.g prevent it wallet not fully empty)
+
+### FIXED
+
+- Handling of missing or deprecated currencies
+- Tiny text copy when updating emergency kit
+
+### CHANGED
+
+- Upgraded compiledSdkVersion and targetSdkVersion to 34
+- Upgraded go version to 1.21.11
+- Enhanced password input for change password flow (consistency with rest of the app)
+- Enhanced error metadata for strange secure storage errors
+- Removed never used "max fee" button and calculations
+- Revamped to UI test suite. Enhancing reliability and coverage.
+
 ## [52] - 2024-06-14
 
 ### ADDED
diff --git a/android/Dockerfile b/android/Dockerfile
index 97a2826d..0781f849 100644
--- a/android/Dockerfile
+++ b/android/Dockerfile
@@ -3,7 +3,7 @@ FROM --platform=linux/amd64 openjdk:17-jdk-buster@sha256:9217da81dcff19e60861791
 ENV NDK_VERSION 22.0.7026061
 ENV ANDROID_PLATFORM_VERSION 28
 ENV ANDROID_BUILD_TOOLS_VERSION 28.0.3
-ENV GO_VERSION 1.18.1
+ENV GO_VERSION 1.21.11
 
 RUN apt-get update \
     && apt-get install --yes --no-install-recommends \
diff --git a/android/apollo/build.gradle b/android/apollo/build.gradle
index 1340d203..a95528c2 100644
--- a/android/apollo/build.gradle
+++ b/android/apollo/build.gradle
@@ -21,20 +21,17 @@ apply from: "${project.rootDir}/linters/pmd/check-android.gradle"
 //apply from: "${project.rootDir}/linters/findbugs/check-android.gradle"
 
 android {
-    compileSdkVersion 31
+    compileSdk 34
 
     defaultConfig {
-        minSdkVersion 19
-        targetSdkVersion 31
-        versionCode 1
-        versionName "1.0"
+        minSdk 19
+        targetSdk 34
 
         testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
     }
 
     buildTypes {
         minified {
-            debuggable true
             minifyEnabled true
         }
     }
@@ -48,12 +45,12 @@ android {
         jvmTarget = JavaVersion.VERSION_1_8.toString()
     }
 
-    lintOptions {
+    lint {
         abortOnError true
         htmlReport true
         textReport true
-        lintConfig file("${project.rootDir}/linters/android-lint/config.xml")
-        baseline file("lint-baseline.xml")
+        lintConfig file("$rootDir/linters/android-lint/config.xml")
+        baseline file('lint-baseline.xml')
     }
 
     testOptions {
diff --git a/android/apollo/src/main/java/io/muun/apollo/data/analytics/AnalyticsProvider.kt b/android/apollo/src/main/java/io/muun/apollo/data/analytics/AnalyticsProvider.kt
index b2c5f5df..e453d3c5 100644
--- a/android/apollo/src/main/java/io/muun/apollo/data/analytics/AnalyticsProvider.kt
+++ b/android/apollo/src/main/java/io/muun/apollo/data/analytics/AnalyticsProvider.kt
@@ -55,7 +55,7 @@ class AnalyticsProvider @Inject constructor(context: Context) {
 
             // Avoid recursion (Timber.i reports a breadcrumb). TODO proper design and fix this
             if (event !is AnalyticsEvent.E_BREADCRUMB) {
-                Timber.i("AnalyticsProvider", event.toString())
+                Timber.i("AnalyticsProvider: $event")
             }
 
         } catch (t: Throwable) {
diff --git a/android/apollo/src/main/java/io/muun/apollo/data/external/Gen.kt b/android/apollo/src/main/java/io/muun/apollo/data/external/Gen.kt
index 75f22cf5..010cc851 100644
--- a/android/apollo/src/main/java/io/muun/apollo/data/external/Gen.kt
+++ b/android/apollo/src/main/java/io/muun/apollo/data/external/Gen.kt
@@ -292,23 +292,6 @@ object Gen {
     private fun muunAddress() =
         MuunAddress(1, "m/1/2/3", address())
 
-    /**
-     * Get a PaymentRequest
-     */
-    fun payReq(
-        amount: MonetaryAmount = Money.of(0, "USD"),
-        feeRate: Double = 10.0,
-        takeFeeFromAmount: Boolean = false,
-
-        ) = PaymentRequest(
-        type = PaymentRequest.Type.TO_ADDRESS,
-        amount = amount,
-        description = "foo",
-        address = address(),
-        feeInSatoshisPerByte = feeRate,
-        takeFeeFromAmount = takeFeeFromAmount
-    )
-
     fun submarineSwap(
         outputAmountInSatoshis: Long,
         sweepFeeInSatoshis: Long = 0,
diff --git a/android/apollo/src/main/java/io/muun/apollo/data/os/BackgroundExecutionMetricsProvider.kt b/android/apollo/src/main/java/io/muun/apollo/data/os/BackgroundExecutionMetricsProvider.kt
index 6241e0f1..16b8e008 100644
--- a/android/apollo/src/main/java/io/muun/apollo/data/os/BackgroundExecutionMetricsProvider.kt
+++ b/android/apollo/src/main/java/io/muun/apollo/data/os/BackgroundExecutionMetricsProvider.kt
@@ -11,7 +11,6 @@ import io.muun.apollo.data.net.ConnectivityInfoProvider
 import io.muun.apollo.data.net.NetworkInfoProvider
 import kotlinx.serialization.Serializable
 import java.util.Locale
-import java.util.TimeZone
 import javax.inject.Inject
 
 private const val UNSUPPORTED = -1
@@ -27,6 +26,7 @@ class BackgroundExecutionMetricsProvider @Inject constructor(
     private val activityManagerInfoProvider: ActivityManagerInfoProvider,
     private val resourcesInfoProvider: ResourcesInfoProvider,
     private val systemCapabilitiesProvider: SystemCapabilitiesProvider,
+    private val dateTimeZoneProvider: DateTimeZoneProvider,
 ) {
 
     private val powerManager: PowerManager by lazy {
@@ -54,7 +54,7 @@ class BackgroundExecutionMetricsProvider @Inject constructor(
             SystemClock.elapsedRealtime(),
             hardwareCapabilitiesProvider.bootCount,
             Locale.getDefault().toString(),
-            TimeZone.getDefault().rawOffset / 1000L,
+            dateTimeZoneProvider.timeZoneOffsetSeconds,
             telephonyInfoProvider.region.orElse(""),
             telephonyInfoProvider.simRegion,
             appInfoProvider.appDatadir,
@@ -68,7 +68,10 @@ class BackgroundExecutionMetricsProvider @Inject constructor(
             systemCapabilitiesProvider.developerEnabled,
             connectivityInfoProvider.proxyHttp,
             connectivityInfoProvider.proxyHttps,
-            connectivityInfoProvider.proxySocks
+            connectivityInfoProvider.proxySocks,
+            dateTimeZoneProvider.autoDateTime,
+            dateTimeZoneProvider.autoTimeZone,
+            dateTimeZoneProvider.timeZoneId
         )
 
     @Suppress("ArrayInDataClass")
@@ -108,6 +111,9 @@ class BackgroundExecutionMetricsProvider @Inject constructor(
         private val proxyHttp: String,
         private val proxyHttps: String,
         private val proxySocks: String,
+        private val autoDateTime: Int,
+        private val autoTimeZone: Int,
+        private val timeZoneId: String,
     )
 
     /**
diff --git a/android/apollo/src/main/java/io/muun/apollo/data/os/DateTimeZoneProvider.kt b/android/apollo/src/main/java/io/muun/apollo/data/os/DateTimeZoneProvider.kt
new file mode 100644
index 00000000..281b3696
--- /dev/null
+++ b/android/apollo/src/main/java/io/muun/apollo/data/os/DateTimeZoneProvider.kt
@@ -0,0 +1,37 @@
+package io.muun.apollo.data.os
+
+import android.content.Context
+import android.provider.Settings
+import java.util.TimeZone
+import javax.inject.Inject
+
+class DateTimeZoneProvider @Inject constructor(private val context: Context) {
+
+    val autoTimeZone: Int
+        get() {
+            return Settings.Global.getInt(
+                context.contentResolver,
+                Settings.Global.AUTO_TIME_ZONE,
+                -1
+            )
+        }
+
+    val autoDateTime: Int
+        get() {
+            return Settings.Global.getInt(
+                context.contentResolver,
+                Settings.Global.AUTO_TIME,
+                -1
+            )
+        }
+
+    val timeZoneId: String
+        get() {
+            return TimeZone.getDefault().id.take(100)
+        }
+
+    val timeZoneOffsetSeconds: Long
+        get() {
+            return TimeZone.getDefault().rawOffset / 1000L
+        }
+}
\ No newline at end of file
diff --git a/android/apollo/src/main/java/io/muun/apollo/data/os/secure_storage/SecureStoragePreferences.java b/android/apollo/src/main/java/io/muun/apollo/data/os/secure_storage/SecureStoragePreferences.java
index 103d5fe8..6f9bf591 100644
--- a/android/apollo/src/main/java/io/muun/apollo/data/os/secure_storage/SecureStoragePreferences.java
+++ b/android/apollo/src/main/java/io/muun/apollo/data/os/secure_storage/SecureStoragePreferences.java
@@ -77,6 +77,7 @@ public byte[] getAesIv(String key) {
      */
     public synchronized byte[] getPersistentSecureRandomBytes(String key, int size) {
         if (sharedPreferences.contains(key)) {
+            Timber.i("getPersistentSecureRandomBytes for " + key + ". Cached.");
             final byte[] iv = getBytes(key);
 
             // We've had a few InvalidKeyExceptions that might come from invalid IVs
@@ -90,6 +91,7 @@ public synchronized byte[] getPersistentSecureRandomBytes(String key, int size)
             return iv;
 
         } else {
+            Timber.i("getPersistentSecureRandomBytes for " + key + ". Generate new");
             final byte[] bytes = RandomGenerator.getBytes(size);
             saveBytes(bytes, key);
             return bytes;
@@ -102,7 +104,14 @@ public synchronized byte[] getPersistentSecureRandomBytes(String key, int size)
     public void saveBytes(byte[] bytes, String key) {
         initSecureStorage();
 
-        sharedPreferences.edit().putString(key, SerializationUtils.serializeBytes(bytes)).commit();
+        final boolean writeSuccess = sharedPreferences.edit()
+                .putString(key, SerializationUtils.serializeBytes(bytes))
+                .commit();
+
+        Timber.i("SaveBytes for " + key + " success:" + writeSuccess );
+        if (!writeSuccess) {
+            Timber.e("Error while committing write to secure storage preferences");
+        }
     }
 
     /**
diff --git a/android/apollo/src/main/java/io/muun/apollo/data/os/secure_storage/SecureStorageProvider.java b/android/apollo/src/main/java/io/muun/apollo/data/os/secure_storage/SecureStorageProvider.java
index 3d0ce9cc..65fee134 100644
--- a/android/apollo/src/main/java/io/muun/apollo/data/os/secure_storage/SecureStorageProvider.java
+++ b/android/apollo/src/main/java/io/muun/apollo/data/os/secure_storage/SecureStorageProvider.java
@@ -123,6 +123,9 @@ public boolean has(String key) {
             // our error report infra offers more metadata/insights on this issue
             if (hasKeyInPreferences != hasKeyInKeystore) {
                 final SecureStorageError error = new SecureStorageError(debugSnapshot());
+                error.addMetadata("key", key);
+                error.addMetadata("hasKeyInPreferences", hasKeyInPreferences);
+                error.addMetadata("hasKeyInKeystore", hasKeyInKeystore);
                 Timber.e(error);
                 throw error;
             }
@@ -196,6 +199,7 @@ private void storeEncrypted(String key, byte[] input) {
             preferences.saveBytes(keyStore.encryptData(input, key, preferences.getAesIv(key)), key);
         } catch (Throwable e) {
             Timber.i("SecureStorageError on WRITE for key: " + key);
+            Timber.e(e);
             final SecureStorageError ssError = new SecureStorageError(e, debugSnapshot());
             enhanceError(ssError, key);
             throw ssError;
diff --git a/android/apollo/src/main/java/io/muun/apollo/data/preferences/UserRepository.java b/android/apollo/src/main/java/io/muun/apollo/data/preferences/UserRepository.java
index e47e3907..14807b8c 100644
--- a/android/apollo/src/main/java/io/muun/apollo/data/preferences/UserRepository.java
+++ b/android/apollo/src/main/java/io/muun/apollo/data/preferences/UserRepository.java
@@ -12,6 +12,7 @@
 import io.muun.apollo.domain.model.user.UserPhoneNumber;
 import io.muun.apollo.domain.model.user.UserProfile;
 import io.muun.common.Optional;
+import io.muun.common.model.Currency;
 import io.muun.common.model.PhoneNumber;
 import io.muun.common.utils.Preconditions;
 
@@ -32,6 +33,7 @@
 import javax.annotation.Nullable;
 import javax.inject.Inject;
 import javax.inject.Singleton;
+import javax.money.CurrencyUnit;
 
 @Singleton
 public class UserRepository extends BaseRepository {
@@ -487,26 +489,37 @@ public static class StoredUserJson {
         // and migrate the preference to a non-minified JSON this class is APPEND-ONLY.
 
         public long hid;
+
         public String email;
+
         public String createdAt;
 
         public String phoneNumber;
+
         public boolean isPhoneNumberVerified;
 
         public String firstName;
+
         public String lastName;
+
         public String profilePictureUrl;
 
         public boolean isEmailVerified;
+
         public boolean hasRecoveryCode;
+
         public boolean hasPassword;
+
         public boolean hasP2PEnabled;
+
         public boolean hasExportedKeys;
 
         public String currency;
 
         public String emergencyKitLastExportedAt;
+
         public Integer emergencyKitVersion;
+
         public String emergencyKitExportMethod;
 
         @NonNull // Not backed by Houston, cached locally
@@ -551,25 +564,27 @@ public StoredUserJson() {
         /**
          * Manual constructor.
          */
-        public StoredUserJson(long hid,
-                              String email,
-                              String createdAt,
-                              String phoneNumber,
-                              boolean isPhoneNumberVerified,
-                              String firstName,
-                              String lastName,
-                              String profilePictureUrl,
-                              boolean isEmailVerified,
-                              boolean hasRecoveryCode,
-                              boolean hasPassword,
-                              boolean hasP2PEnabled,
-                              boolean hasExportedKeys,
-                              String currency,
-                              String emergencyKitLastExportedAt,
-                              Integer emergencyKitVersion,
-                              EmergencyKitExport.Method emergencyKitExportMethod,
-                              @NonNull StoredEkVerificationCodes ekVerificationCodes,
-                              @NonNull List<Integer> ekVersions) {
+        public StoredUserJson(
+                long hid,
+                String email,
+                String createdAt,
+                String phoneNumber,
+                boolean isPhoneNumberVerified,
+                String firstName,
+                String lastName,
+                String profilePictureUrl,
+                boolean isEmailVerified,
+                boolean hasRecoveryCode,
+                boolean hasPassword,
+                boolean hasP2PEnabled,
+                boolean hasExportedKeys,
+                String currency,
+                String emergencyKitLastExportedAt,
+                Integer emergencyKitVersion,
+                EmergencyKitExport.Method emergencyKitExportMethod,
+                @NonNull StoredEkVerificationCodes ekVerificationCodes,
+                @NonNull List<Integer> ekVersions
+        ) {
 
             this.hid = hid;
             this.email = email;
@@ -608,7 +623,7 @@ User toUser() {
                             ? Optional.of(new UserProfile(firstName, lastName, profilePictureUrl))
                             : Optional.empty(),
 
-                    SerializationUtils.deserializeCurrencyUnit(currency != null ? currency : "USD"),
+                    loadCurrencyFromStorage(),
 
                     hasRecoveryCode,
                     hasPassword,
@@ -626,6 +641,18 @@ User toUser() {
             );
         }
 
+        private CurrencyUnit loadCurrencyFromStorage() {
+            try {
+                final String currencyCode = currency != null ? currency : "USD";
+                return SerializationUtils.deserializeCurrencyUnit(currencyCode);
+
+            } catch (Exception e) {
+                // This can happen for example if user primary currency is no longer supported
+                // after an app or OS update.
+                return Currency.getUnit(Currency.DEFAULT.getCode()).get();
+            }
+        }
+
         void initEmergencyKitVersion() {
             if (emergencyKitLastExportedAt != null) {
                 emergencyKitVersion = (int) Libwallet.EKVersionDescriptors;
@@ -683,9 +710,11 @@ public StoredUserJson get(@NonNull String key, @NonNull SharedPreferences prefer
         }
 
         @Override
-        public void set(@NonNull String key,
-                        @NonNull StoredUserJson value,
-                        @NonNull SharedPreferences.Editor editor) {
+        public void set(
+                @NonNull String key,
+                @NonNull StoredUserJson value,
+                @NonNull SharedPreferences.Editor editor
+        ) {
             super.set(key, value, editor);
         }
     }
diff --git a/android/apollo/src/main/java/io/muun/apollo/data/serialization/SafeCurrencyUnitDeserializer.kt b/android/apollo/src/main/java/io/muun/apollo/data/serialization/SafeCurrencyUnitDeserializer.kt
new file mode 100644
index 00000000..058f84a1
--- /dev/null
+++ b/android/apollo/src/main/java/io/muun/apollo/data/serialization/SafeCurrencyUnitDeserializer.kt
@@ -0,0 +1,33 @@
+package io.muun.apollo.data.serialization
+
+import com.fasterxml.jackson.core.JsonParser
+import com.fasterxml.jackson.databind.DeserializationContext
+import com.fasterxml.jackson.databind.JsonDeserializer
+import io.muun.apollo.domain.errors.MissingCurrencyError
+import io.muun.apollo.domain.utils.DeprecatedCurrencyUnit
+import timber.log.Timber
+import java.io.IOException
+import javax.money.CurrencyUnit
+import javax.money.Monetary
+import javax.money.UnknownCurrencyException
+
+class SafeCurrencyUnitDeserializer : JsonDeserializer<CurrencyUnit>() {
+
+    @Throws(IOException::class)
+    override fun deserialize(parser: JsonParser, context: DeserializationContext): CurrencyUnit {
+        val currencyCode = parser.valueAsString
+
+        if (Monetary.isCurrencyAvailable(currencyCode)) {
+            return Monetary.getCurrency(currencyCode)
+
+        } else {
+            // In practice, only this type of error should arise.
+            Timber.e(MissingCurrencyError(UnknownCurrencyException(currencyCode)))
+
+            // This can happen for example if user primary currency is no longer supported
+            // after an app or OS update, or if user has changed to a device that no longer supports
+            // their primary currency.
+            return DeprecatedCurrencyUnit(currencyCode)
+        }
+    }
+}
\ No newline at end of file
diff --git a/android/apollo/src/main/java/io/muun/apollo/data/serialization/SerializationUtils.java b/android/apollo/src/main/java/io/muun/apollo/data/serialization/SerializationUtils.java
index 11e72515..2c1fc596 100644
--- a/android/apollo/src/main/java/io/muun/apollo/data/serialization/SerializationUtils.java
+++ b/android/apollo/src/main/java/io/muun/apollo/data/serialization/SerializationUtils.java
@@ -8,6 +8,7 @@
 import io.muun.apollo.domain.errors.data.MuunDeserializationError;
 import io.muun.apollo.domain.model.BitcoinAmount;
 import io.muun.apollo.domain.utils.DateUtils;
+import io.muun.apollo.domain.utils.DeprecatedCurrencyUnit;
 import io.muun.common.dates.MuunZonedDateTime;
 import io.muun.common.model.PhoneNumber;
 
@@ -63,11 +64,13 @@ public final class SerializationUtils {
                         .addDeserializer(PhoneNumber.class, new PhoneNumberDeserializer())
 
                         .addSerializer(BitcoinAmount.class, new BitcoinAmountSerializer())
-                        .addDeserializer(BitcoinAmount.class, new BitcoinAmountDeserializer());
+                        .addDeserializer(BitcoinAmount.class, new BitcoinAmountDeserializer())
+
+                        .addDeserializer(CurrencyUnit.class, new SafeCurrencyUnitDeserializer());
 
         JSON_MAPPER = new ObjectMapper()
-                .registerModule(simpleModule)
-                .registerModule(new MoneyModule());
+                .registerModule(new MoneyModule())
+                .registerModule(simpleModule); // Last so our custom deserializers take precedence
 
         // Allows unknown Enum values to be ignored and a predefined value specified through
         // @JsonEnumDefaultValue annotation. If enabled, but no predefined default Enum value is
@@ -90,8 +93,10 @@ public static <T extends Enum<T>> String serializeEnum(@NotNull T enumValue) {
      * Deserialize an enum.
      */
     @NotNull
-    public static <T extends Enum<T>> T deserializeEnum(@NotNull Class<T> enumClass,
-                                                        @NotNull String enumString) {
+    public static <T extends Enum<T>> T deserializeEnum(
+            @NotNull Class<T> enumClass,
+            @NotNull String enumString
+    ) {
 
         return Enum.valueOf(enumClass, enumString);
     }
@@ -131,8 +136,10 @@ public static <T> String serializeJson(@NotNull Class<T> jsonType, @NotNull T js
      * Serialize a class to JSON.
      */
     @NotNull
-    public static <T> String serializeJson(@NotNull TypeReference<? extends T> jsonType,
-                                           @NotNull T jsonValue) {
+    public static <T> String serializeJson(
+            @NotNull TypeReference<? extends T> jsonType,
+            @NotNull T jsonValue
+    ) {
 
         try {
             return JSON_MAPPER.writerFor(jsonType).writeValueAsString(jsonValue);
@@ -158,8 +165,10 @@ public static <T> T deserializeJson(@NotNull Class<T> jsonType, @NotNull String
      * Deserialize a class from JSON.
      */
     @NotNull
-    public static <T> T deserializeJson(@NotNull TypeReference<? extends T> jsonType,
-                                        @NotNull String jsonString) {
+    public static <T> T deserializeJson(
+            @NotNull TypeReference<? extends T> jsonType,
+            @NotNull String jsonString
+    ) {
 
         try {
             return JSON_MAPPER.readValue(jsonString, jsonType);
@@ -214,7 +223,6 @@ public static String serializeCurrencyUnit(@NotNull CurrencyUnit currencyValue)
      */
     @NotNull
     public static CurrencyUnit deserializeCurrencyUnit(@NotNull String currencyString) {
-
         try {
             return Monetary.getCurrency(currencyString);
 
@@ -253,11 +261,19 @@ public static MonetaryAmount deserializeMonetaryAmount(@NotNull String moneyStri
         }
 
         final BigDecimal number = deserializeBigDecimal(parts[0]);
-        final CurrencyUnit currency = deserializeCurrencyUnit(parts[1]);
-
+        final CurrencyUnit currency = safeDeserializeCurrencyUnit(parts[1]);
         return Money.of(number, currency);
     }
 
+    private static CurrencyUnit safeDeserializeCurrencyUnit(@NotNull String currencyString) {
+        if (!Monetary.isCurrencyAvailable(currencyString)) {
+            return new DeprecatedCurrencyUnit(currencyString);
+
+        } else {
+            return deserializeCurrencyUnit(currencyString);
+        }
+    }
+
     /**
      * Serialize a BitcoinAmount.
      */
@@ -282,8 +298,8 @@ public static BitcoinAmount deserializeBitcoinAmount(@NotNull String string) {
         }
 
         final Long inSatoshis = Long.valueOf(parts[0]);
-        final MonetaryAmount inInputCurrency =  deserializeMonetaryAmount(parts[1]);
-        final MonetaryAmount inPrimaryCurrency =  deserializeMonetaryAmount(parts[2]);
+        final MonetaryAmount inInputCurrency = deserializeMonetaryAmount(parts[1]);
+        final MonetaryAmount inPrimaryCurrency = deserializeMonetaryAmount(parts[2]);
 
         return new BitcoinAmount(inSatoshis, inInputCurrency, inPrimaryCurrency);
     }
@@ -335,9 +351,11 @@ public static <K, V> String serializeMap(Class<K> keyType, Class<V> valueType, M
     /**
      * Deserialize a list of objects from a JSON array.
      */
-    public static <K, V>  Map<K, V> deserializeMap(Class<K> keyType,
-                                                   Class<V> valueType,
-                                                   String json) {
+    public static <K, V> Map<K, V> deserializeMap(
+            Class<K> keyType,
+            Class<V> valueType,
+            String json
+    ) {
         try {
             return JSON_MAPPER
                     .readerFor(TYPE_FACTORY.constructMapType(Map.class, keyType, valueType))
diff --git a/android/apollo/src/main/java/io/muun/apollo/domain/Flags.java b/android/apollo/src/main/java/io/muun/apollo/domain/Flags.java
index 760918e3..4e116603 100644
--- a/android/apollo/src/main/java/io/muun/apollo/domain/Flags.java
+++ b/android/apollo/src/main/java/io/muun/apollo/domain/Flags.java
@@ -5,6 +5,4 @@
  */
 public class Flags {
 
-    public static final boolean USE_MAXIMUM_FEE_ENABLED = false;
-
 }
\ No newline at end of file
diff --git a/android/apollo/src/main/java/io/muun/apollo/domain/action/LogoutActions.java b/android/apollo/src/main/java/io/muun/apollo/domain/action/LogoutActions.java
index 1baa678e..5b8d6517 100644
--- a/android/apollo/src/main/java/io/muun/apollo/domain/action/LogoutActions.java
+++ b/android/apollo/src/main/java/io/muun/apollo/domain/action/LogoutActions.java
@@ -100,11 +100,14 @@ public void destroyRecoverableWallet() {
     }
 
     /**
-     * Wipe all user associated data from the app (unrecoverable only).
+     * Wipe all user associated data from the app.
+     * Note: if user is unrecoverable or recoverable user has performed "delete wallet" this
+     * action is irreversible (and its intended to be). We're naming this "dangerously" because
+     * callers should be careful when calling this.
      */
-    public void dangerouslyDestroyUnrecoverableWallet() {
+    public void dangerouslyDestroyWallet() {
         final LogoutOptions logoutOptions = logoutOptionsSel.get();
-        Preconditions.checkState(!logoutOptions.isBlocked()); // just checking
+        Preconditions.checkState(logoutOptions.canDeleteWallet()); // just checking
 
         destroyWallet();
     }
diff --git a/android/apollo/src/main/java/io/muun/apollo/domain/action/operation/ResolveBitcoinUriAction.java b/android/apollo/src/main/java/io/muun/apollo/domain/action/operation/ResolveBitcoinUriAction.java
index fa18bf3b..223bb2b5 100644
--- a/android/apollo/src/main/java/io/muun/apollo/domain/action/operation/ResolveBitcoinUriAction.java
+++ b/android/apollo/src/main/java/io/muun/apollo/domain/action/operation/ResolveBitcoinUriAction.java
@@ -1,34 +1,27 @@
 package io.muun.apollo.domain.action.operation;
 
-import io.muun.apollo.data.preferences.FeeWindowRepository;
 import io.muun.apollo.domain.action.base.BaseAsyncAction1;
 import io.muun.apollo.domain.errors.newop.InvalidPaymentRequestError;
 import io.muun.apollo.domain.libwallet.LibwalletBridge;
 import io.muun.apollo.domain.model.BitcoinUriContent;
-import io.muun.apollo.domain.model.FeeWindow;
 import io.muun.apollo.domain.model.OperationUri;
 import io.muun.apollo.domain.model.PaymentRequest;
-import io.muun.apollo.domain.utils.StringUtils;
-import io.muun.common.utils.BitcoinUtils;
 
 import rx.Observable;
 
 import javax.inject.Inject;
 import javax.inject.Singleton;
-import javax.money.MonetaryAmount;
 
 @Singleton
 public class ResolveBitcoinUriAction extends BaseAsyncAction1<OperationUri, PaymentRequest> {
 
-    private final FeeWindowRepository feeWindowRepository;
 
     /**
      * Resolves a Bitcoin URI, using BIP-72 or BIP-21 as appropriate.
      */
     @Inject
-    public ResolveBitcoinUriAction(FeeWindowRepository feeWindowRepository) {
+    public ResolveBitcoinUriAction() {
 
-        this.feeWindowRepository = feeWindowRepository;
     }
 
     @Override
@@ -44,22 +37,9 @@ public Observable<PaymentRequest> action(OperationUri operationUri) {
     }
 
     private PaymentRequest resolveBitcoinUri(OperationUri uri) {
-        final FeeWindow feeWindow = feeWindowRepository.fetchOne();
-
         final BitcoinUriContent uriContent = LibwalletBridge.getBitcoinUriContent(uri);
 
-        final MonetaryAmount amount = (uriContent.amountInStatoshis != null)
-                ? BitcoinUtils.satoshisToBitcoins(uriContent.amountInStatoshis)
-                : null;
-
-        final String description = StringUtils.joinText(": ", new String[]{
-                uriContent.merchant,
-                uriContent.memo
-        });
-
-        final double feeRate = feeWindow.getFastestFeeInSatoshisPerByte();
-
-        return PaymentRequest.toAddress(uriContent.address, amount, description, feeRate);
+        return PaymentRequest.toAddress(uriContent.address);
     }
 
 }
diff --git a/android/apollo/src/main/java/io/muun/apollo/domain/action/operation/ResolveLnInvoiceAction.kt b/android/apollo/src/main/java/io/muun/apollo/domain/action/operation/ResolveLnInvoiceAction.kt
index 07b84ad6..fe0d008c 100644
--- a/android/apollo/src/main/java/io/muun/apollo/domain/action/operation/ResolveLnInvoiceAction.kt
+++ b/android/apollo/src/main/java/io/muun/apollo/domain/action/operation/ResolveLnInvoiceAction.kt
@@ -3,7 +3,6 @@ package io.muun.apollo.domain.action.operation
 import androidx.annotation.VisibleForTesting
 import io.muun.apollo.data.net.HoustonClient
 import io.muun.apollo.data.preferences.BackgroundTimesRepository
-import io.muun.apollo.data.preferences.FeeWindowRepository
 import io.muun.apollo.data.preferences.KeysRepository
 import io.muun.apollo.domain.action.base.BaseAsyncAction2
 import io.muun.apollo.domain.analytics.NewOperationOrigin
@@ -12,14 +11,12 @@ import io.muun.apollo.domain.errors.newop.InvoiceExpiredException
 import io.muun.apollo.domain.libwallet.DecodedInvoice
 import io.muun.apollo.domain.libwallet.Invoice.decodeInvoice
 import io.muun.apollo.domain.model.PaymentRequest
-import io.muun.apollo.domain.model.PaymentRequest.Companion.toLnInvoice
 import io.muun.apollo.domain.model.SubmarineSwap
 import io.muun.apollo.domain.model.SubmarineSwapRequest
 import io.muun.apollo.domain.utils.DateUtils
 import io.muun.common.api.SubmarineSwapJson
 import io.muun.common.crypto.hd.PublicKey
 import io.muun.common.crypto.hd.PublicKeyPair
-import io.muun.common.utils.BitcoinUtils
 import io.muun.common.utils.Encodings
 import io.muun.common.utils.Hashes
 import io.muun.common.utils.LnInvoice
@@ -45,14 +42,12 @@ import org.bitcoinj.script.ScriptOpCodes.OP_SWAP
 import rx.Observable
 import javax.inject.Inject
 import javax.inject.Singleton
-import javax.money.MonetaryAmount
 
 @Singleton
 class ResolveLnInvoiceAction @Inject internal constructor(
     private val network: NetworkParameters,
     private val houstonClient: HoustonClient,
     private val keysRepository: KeysRepository,
-    private val feeWindowRepository: FeeWindowRepository,
     private val backgroundTimesRepository: BackgroundTimesRepository
 ) : BaseAsyncAction2<String, NewOperationOrigin, PaymentRequest>() {
 
@@ -99,9 +94,6 @@ class ResolveLnInvoiceAction @Inject internal constructor(
     }
 
     private fun buildPaymentRequest(invoice: DecodedInvoice, swap: SubmarineSwap): PaymentRequest {
-        val feeWindow = feeWindowRepository.fetchOne()
-        val amount = getInvoiceAmount(invoice)
-
         if (!swap.isLend) {
             validateNonLendSwap(invoice, swap)
         }
@@ -110,14 +102,9 @@ class ResolveLnInvoiceAction @Inject internal constructor(
             throw InvalidSwapException(swap.houstonUuid)
         }
 
-        // For AmountLess Invoices, fee rate is initially unknown
-        val feeRate = if (invoice.amountInSat != null) feeWindow.getFeeRate(swap) else null
-        return toLnInvoice(
+        return PaymentRequest.toLnInvoice(
             invoice,
-            amount,
-            invoice.description,
             swap,
-            feeRate
         )
     }
 
@@ -143,13 +130,6 @@ class ResolveLnInvoiceAction @Inject internal constructor(
         }
     }
 
-    private fun getInvoiceAmount(invoice: DecodedInvoice): MonetaryAmount? {
-        return if (invoice.amountInSat != null) {
-            BitcoinUtils.satoshisToBitcoins(invoice.amountInSat)
-        } else
-            null
-    }
-
     /**
      * Create a new Submarine Swap.
      */
diff --git a/android/apollo/src/main/java/io/muun/apollo/domain/action/operation/ResolveMuunUriAction.java b/android/apollo/src/main/java/io/muun/apollo/domain/action/operation/ResolveMuunUriAction.java
index 7119ceb1..b823a004 100644
--- a/android/apollo/src/main/java/io/muun/apollo/domain/action/operation/ResolveMuunUriAction.java
+++ b/android/apollo/src/main/java/io/muun/apollo/domain/action/operation/ResolveMuunUriAction.java
@@ -1,45 +1,38 @@
 package io.muun.apollo.domain.action.operation;
 
 import io.muun.apollo.data.db.contact.ContactDao;
-import io.muun.apollo.data.preferences.FeeWindowRepository;
 import io.muun.apollo.data.preferences.UserRepository;
 import io.muun.apollo.domain.action.base.BaseAsyncAction1;
 import io.muun.apollo.domain.model.Contact;
 import io.muun.apollo.domain.model.ExchangeRateWindow;
-import io.muun.apollo.domain.model.FeeWindow;
 import io.muun.apollo.domain.model.OperationUri;
 import io.muun.apollo.domain.model.PaymentRequest;
 import io.muun.apollo.domain.model.user.User;
 import io.muun.apollo.domain.selector.ExchangeRateSelector;
 
-import org.javamoney.moneta.Money;
 import rx.Observable;
 
-import java.math.BigDecimal;
 import javax.inject.Inject;
 import javax.inject.Singleton;
-import javax.money.MonetaryAmount;
 
 @Singleton
 public class ResolveMuunUriAction extends BaseAsyncAction1<OperationUri, PaymentRequest> {
 
     private final UserRepository userRepository;
     private final ContactDao contactDao;
-    private final FeeWindowRepository feeWindowRepository;
     private final ExchangeRateSelector rateSelector;
 
     /**
      * Resolves a Muun URI, fetching User and/or Contact as needed.
      */
     @Inject
-    public ResolveMuunUriAction(UserRepository userRepository,
-                                ContactDao contactDao,
-                                FeeWindowRepository feeWindowRepository,
-                                ExchangeRateSelector rateSelector) {
-
+    public ResolveMuunUriAction(
+            UserRepository userRepository,
+            ContactDao contactDao,
+            ExchangeRateSelector rateSelector
+    ) {
         this.userRepository = userRepository;
         this.contactDao = contactDao;
-        this.feeWindowRepository = feeWindowRepository;
         this.rateSelector = rateSelector;
     }
 
@@ -50,7 +43,6 @@ public Observable<PaymentRequest> action(OperationUri operationUri) {
 
     private PaymentRequest resolveMuunUri(OperationUri uri) {
         final User user = userRepository.fetchOne();
-        final FeeWindow feeWindow = feeWindowRepository.fetchOne();
         // TODO: this could cause unexpected behaviour since it may not be same rate window as
         // the one used in paymentContext. We've seen rates for some currencies suddenly being
         // dropped which may cause trouble if the primary currency is one of them.
@@ -66,13 +58,6 @@ private PaymentRequest resolveMuunUri(OperationUri uri) {
         final String descriptionParam = uri.getParam(OperationUri.MUUN_DESCRIPTION)
                 .orElse("");
 
-        final MonetaryAmount amount = Money.of(
-                new BigDecimal(amountParam),
-                currencyParam.toUpperCase()
-        );
-
-        final double feeRate = feeWindow.getFastestFeeInSatoshisPerByte();
-
         switch (uri.getHost()) {
             case OperationUri.MUUN_HOST_CONTACT:
                 final Contact contact = contactDao
@@ -80,11 +65,11 @@ private PaymentRequest resolveMuunUri(OperationUri uri) {
                         .toBlocking()
                         .first();
 
-                return PaymentRequest.toContact(contact, amount, descriptionParam, feeRate);
+                return PaymentRequest.toContact(contact);
 
             case OperationUri.MUUN_HOST_EXTERNAL:
                 final String externalAddress = uri.getExternalAddress();
-                return PaymentRequest.toAddress(externalAddress, amount, descriptionParam, feeRate);
+                return PaymentRequest.toAddress(externalAddress);
 
             default:
                 throw new IllegalArgumentException("Invalid host: " + uri.getHost());
diff --git a/android/apollo/src/main/java/io/muun/apollo/domain/libwallet/BitcoinUri.kt b/android/apollo/src/main/java/io/muun/apollo/domain/libwallet/BitcoinUri.kt
index 23d465a3..4fbee3d9 100644
--- a/android/apollo/src/main/java/io/muun/apollo/domain/libwallet/BitcoinUri.kt
+++ b/android/apollo/src/main/java/io/muun/apollo/domain/libwallet/BitcoinUri.kt
@@ -1,6 +1,7 @@
 package io.muun.apollo.domain.libwallet
 
 import androidx.annotation.VisibleForTesting
+import io.muun.apollo.data.external.Globals
 import io.muun.apollo.domain.model.BitcoinAmount
 import io.muun.common.utils.BitcoinUtils
 import libwallet.Libwallet
@@ -31,4 +32,17 @@ object BitcoinUri {
             .number
             .numberValue(BigDecimal::class.java)
             .toPlainString() // Avoid scientific notation for golang to parse/compare smoothly
+
+    /**
+     * This is a utility method meant EXCLUSIVELY for testing. It's required since UiTests can't
+     * directly call Libwallet's go code yet.
+     * Note: DO NOT use in main code.
+     */
+    @VisibleForTesting
+    fun parse(rawBip21Uri: String): Triple<String, Long?, String> {
+        val bitcoinUri = io.muun.common.bitcoinj.BitcoinUri(Globals.INSTANCE.network, rawBip21Uri)
+        val invoice = bitcoinUri.getParameterByName("lightning") as String
+        return Triple(bitcoinUri.address!!, bitcoinUri.amount?.value, invoice)
+    }
+
 }
\ No newline at end of file
diff --git a/android/apollo/src/main/java/io/muun/apollo/domain/model/NextTransactionSize.java b/android/apollo/src/main/java/io/muun/apollo/domain/model/NextTransactionSize.java
index d2037020..2ad67a31 100644
--- a/android/apollo/src/main/java/io/muun/apollo/domain/model/NextTransactionSize.java
+++ b/android/apollo/src/main/java/io/muun/apollo/domain/model/NextTransactionSize.java
@@ -58,7 +58,7 @@ public long getUtxoBalance() {
      * Get the spendable balance (considering debt).
      */
     public long getUserBalance() {
-        return Preconditions.checkNonNegative(getUtxoBalance() - getExpectedDebtInSat());
+        return Preconditions.checkNotNegative(getUtxoBalance() - getExpectedDebtInSat());
     }
 
     /**
diff --git a/android/apollo/src/main/java/io/muun/apollo/domain/model/PaymentRequest.kt b/android/apollo/src/main/java/io/muun/apollo/domain/model/PaymentRequest.kt
index 75461263..b3edf05b 100644
--- a/android/apollo/src/main/java/io/muun/apollo/domain/model/PaymentRequest.kt
+++ b/android/apollo/src/main/java/io/muun/apollo/domain/model/PaymentRequest.kt
@@ -2,18 +2,12 @@ package io.muun.apollo.domain.model
 
 import io.muun.apollo.domain.libwallet.DecodedInvoice
 import io.muun.common.utils.Preconditions
-import javax.money.MonetaryAmount
 
 data class PaymentRequest(
     val type: Type,
-    val amount: MonetaryAmount? = null,
-    val description: String? = null,
     val contact: Contact? = null,
     val address: String? = null,
-    val invoice: DecodedInvoice? = null,
     val swap: SubmarineSwap? = null,
-    val feeInSatoshisPerByte: Double?, //initially null for AmountLess Invoice
-    val takeFeeFromAmount: Boolean = false,
 ) {
 
     enum class Type {
@@ -28,19 +22,13 @@ data class PaymentRequest(
         @JvmStatic
         fun toContact(
             contact: Contact,
-            amount: MonetaryAmount,
-            description: String,
-            feeInSatoshisPerByte: Double,
         ): PaymentRequest {
 
             Preconditions.checkNotNull(contact)
 
             return PaymentRequest(
                 Type.TO_CONTACT,
-                amount = amount,
-                description = description,
                 contact = contact,
-                feeInSatoshisPerByte = feeInSatoshisPerByte
             )
         }
 
@@ -48,19 +36,13 @@ data class PaymentRequest(
         @JvmStatic
         fun toAddress(
             address: String,
-            amount: MonetaryAmount?,
-            description: String?,
-            feeInSatoshisPerByte: Double,
         ): PaymentRequest {
 
             Preconditions.checkNotNull(address)
 
             return PaymentRequest(
                 Type.TO_ADDRESS,
-                amount = amount,
-                description = description,
                 address = address,
-                feeInSatoshisPerByte = feeInSatoshisPerByte
             )
         }
 
@@ -68,21 +50,14 @@ data class PaymentRequest(
         @JvmStatic
         fun toLnInvoice(
             invoice: DecodedInvoice,
-            amount: MonetaryAmount?,
-            description: String,
             submarineSwap: SubmarineSwap,
-            feeInSatoshisPerByte: Double?,
         ): PaymentRequest {
 
             Preconditions.checkNotNull(invoice)
 
             return PaymentRequest(
                 Type.TO_LN_INVOICE,
-                amount = amount,
-                description = description,
-                invoice = invoice,
                 swap = submarineSwap,
-                feeInSatoshisPerByte = feeInSatoshisPerByte
             )
         }
     }
diff --git a/android/apollo/src/main/java/io/muun/apollo/domain/model/user/User.java b/android/apollo/src/main/java/io/muun/apollo/domain/model/user/User.java
index ff999cea..11ea5d43 100644
--- a/android/apollo/src/main/java/io/muun/apollo/domain/model/user/User.java
+++ b/android/apollo/src/main/java/io/muun/apollo/domain/model/user/User.java
@@ -169,7 +169,10 @@ public CurrencyUnit getPrimaryCurrency(ExchangeRateProvider rateProvider) {
         // flawed. It will (strangely) return true when there's no rate for certain currencies.
         if (rateProvider.getCurrencies().contains(targetCurrency)) {
             return targetCurrency;
+
         } else {
+            // TODO this "defaulting" to btc is contrary to our defaulting to usd elsewhere
+            // We should probably unify behavior.
             return Currency.getUnit("BTC").get();
         }
     }
diff --git a/android/apollo/src/main/java/io/muun/apollo/domain/selector/LogoutOptionsSelector.kt b/android/apollo/src/main/java/io/muun/apollo/domain/selector/LogoutOptionsSelector.kt
index 2588463d..d111415c 100644
--- a/android/apollo/src/main/java/io/muun/apollo/domain/selector/LogoutOptionsSelector.kt
+++ b/android/apollo/src/main/java/io/muun/apollo/domain/selector/LogoutOptionsSelector.kt
@@ -1,28 +1,30 @@
 package io.muun.apollo.domain.selector
 
 import io.muun.common.model.OperationStatus
+import io.muun.common.utils.Preconditions
 import rx.Observable
 import javax.inject.Inject
 
 class LogoutOptionsSelector @Inject constructor(
     private val userSel: UserSelector,
     private val paymentContextSel: PaymentContextSelector,
-    private val operationSel: OperationSelector
+    private val operationSel: OperationSelector,
 ) {
 
     class LogoutOptions(
         private val isRecoverable: Boolean,
         private val hasBalance: Boolean,
         private val hasUnsettledOps: Boolean,
-        private val hasPendingIncomingSwaps: Boolean
+        private val hasPendingIncomingSwaps: Boolean,
     ) {
 
-        fun isBlocked(): Boolean {
-            return if (isRecoverable) {
-                hasPendingIncomingSwaps
-            } else {
-                hasBalance || hasUnsettledOps
-            }
+        fun isLogoutBlocked(): Boolean {
+            Preconditions.checkArgument(isRecoverable)
+            return hasPendingIncomingSwaps
+        }
+
+        fun canDeleteWallet(): Boolean {
+            return !hasBalance && !hasUnsettledOps
         }
 
         fun isRecoverable(): Boolean {
diff --git a/android/apollo/src/main/java/io/muun/apollo/domain/utils/DeprecatedCurrencyUnit.kt b/android/apollo/src/main/java/io/muun/apollo/domain/utils/DeprecatedCurrencyUnit.kt
new file mode 100644
index 00000000..562c7f63
--- /dev/null
+++ b/android/apollo/src/main/java/io/muun/apollo/domain/utils/DeprecatedCurrencyUnit.kt
@@ -0,0 +1,44 @@
+package io.muun.apollo.domain.utils
+
+import javax.money.CurrencyContext
+import javax.money.CurrencyContextBuilder
+import javax.money.CurrencyUnit
+
+/**
+ * This is our "placeholder" ad-hoc CurrencyUnit implementation. It helps us in the edge case where
+ * a user's primary currency is no longer supported (by the Moneta lib) after an app or OS update,
+ * or if user has changed to a device that no longer supports their primary currency. Notice this
+ * situation also affects operation in user's operation history (e.g an operation amount is recorded
+ * in btc and the user's primary currency at the time of the operation).
+ *
+ * Note: main goal for this class is to be able to distinguish a primary currency when its
+ * deprecated (via instance of) and to still be able to display amounts in
+ * {@link #wrappedCurrencyCode} in the user's operation history.
+ */
+class DeprecatedCurrencyUnit(private val wrappedCurrencyCode: String) : CurrencyUnit {
+
+    override fun compareTo(other: CurrencyUnit?): Int {
+        if (other == null) {
+            return -1
+        }
+
+        // wrappedCurrencyCode is deprecated so we shouldn't find it "in the wild"
+        return wrappedCurrencyCode.compareTo(other.currencyCode)
+    }
+
+    override fun getCurrencyCode(): String =
+        wrappedCurrencyCode
+
+    override fun getNumericCode(): Int =
+        0
+
+    /**
+     * Using 0 default fraction digits as we expect currencies to be deprecated to be high
+     * inflationary or otherwise very devalued.
+     */
+    override fun getDefaultFractionDigits(): Int =
+        0
+
+    override fun getContext(): CurrencyContext =
+        CurrencyContextBuilder.of("FAKE_PROVIDER").build()
+}
\ No newline at end of file
diff --git a/android/apollo/src/main/java/io/muun/apollo/domain/utils/Extensions.kt b/android/apollo/src/main/java/io/muun/apollo/domain/utils/Extensions.kt
index 8e02bbce..fff4230f 100644
--- a/android/apollo/src/main/java/io/muun/apollo/domain/utils/Extensions.kt
+++ b/android/apollo/src/main/java/io/muun/apollo/domain/utils/Extensions.kt
@@ -24,6 +24,7 @@ import java.util.concurrent.TimeoutException
 import javax.crypto.BadPaddingException
 import javax.money.Monetary
 import javax.money.MonetaryException
+import javax.money.UnknownCurrencyException
 
 fun <T> Observable<T>.toVoid(): Observable<Void> =
     map(RxHelper::toVoid)
@@ -54,6 +55,13 @@ fun <T : Fragment> T.applyArgs(f: Bundle.() -> Unit) =
         arguments = (arguments ?: Bundle()).apply(f)
     }
 
+
+/**
+ * Needed as inline reified functions can't be called from Java.
+ */
+fun Throwable.isInstanceOrIsCausedByUnknownCurrencyException() =
+    isInstanceOrIsCausedByError<UnknownCurrencyException>()
+
 /**
  * Needed as inline reified functions can't be called from Java.
  */
diff --git a/android/apollo/src/test/java/io/muun/apollo/domain/action/OperationActionsTest.java b/android/apollo/src/test/java/io/muun/apollo/domain/action/OperationActionsTest.java
index 52f27161..bea2283b 100644
--- a/android/apollo/src/test/java/io/muun/apollo/domain/action/OperationActionsTest.java
+++ b/android/apollo/src/test/java/io/muun/apollo/domain/action/OperationActionsTest.java
@@ -9,7 +9,6 @@
 import io.muun.apollo.domain.action.operation.OperationMetadataMapper;
 import io.muun.apollo.domain.action.operation.SubmitPaymentAction;
 import io.muun.apollo.domain.model.Contact;
-import io.muun.apollo.domain.model.ExchangeRateWindow;
 import io.muun.apollo.domain.model.Operation;
 import io.muun.apollo.domain.model.PaymentRequest;
 import io.muun.apollo.domain.model.PreparedPayment;
@@ -18,9 +17,7 @@
 import io.muun.common.crypto.hd.MuunAddress;
 import io.muun.common.crypto.hd.PrivateKey;
 import io.muun.common.crypto.hd.PublicKey;
-import io.muun.common.model.ExchangeRateProvider;
 import io.muun.common.model.OperationDirection;
-import io.muun.common.utils.BitcoinUtils;
 
 import androidx.core.util.Pair;
 import br.com.six2six.fixturefactory.Fixture;
@@ -33,7 +30,6 @@
 import rx.Observable;
 
 import java.util.List;
-import javax.money.MonetaryAmount;
 
 import static io.muun.apollo.TestUtils.fetchItemFromObservable;
 import static org.assertj.core.api.Assertions.assertThat;
@@ -106,8 +102,6 @@ public void fetchReplaceOperations() {
     @Test
     public void buildPaymentToContact() {
 
-        final ExchangeRateWindow rates = Fixture.from(ExchangeRateWindow.class).gimme("valid");
-
         final Contact contact = Fixture.from(Contact.class).gimme("valid");
         final PublicKey publicKey = contact.publicKey;
         final MuunAddress contactAddress = new MuunAddress(
@@ -118,10 +112,7 @@ public void buildPaymentToContact() {
         final long someFee = 123456;
 
         final PaymentRequest payReq = PaymentRequest.toContact(
-                contact,
-                TemplateHelpers.money().generateValue(),
-                "some description",
-                10.0
+                contact
         );
 
         doReturn(contact.publicProfile)
@@ -156,14 +147,6 @@ public void buildPaymentToContact() {
                 contactAddress.getDerivationPath()
         );
 
-        // check amount
-        final ExchangeRateProvider provider = new ExchangeRateProvider(rates.toJson());
-        final MonetaryAmount inBtc = payReq.getAmount().with(provider.getCurrencyConversion("BTC"));
-        final long inSatoshis = BitcoinUtils.bitcoinsToSatoshis(inBtc);
-
-        assertThat(operation.amount.inInputCurrency).isEqualTo(payReq.getAmount());
-        assertThat(operation.amount.inSatoshis).isEqualTo(inSatoshis);
-
         // check fee
         assertThat(operation.fee.inSatoshis).isEqualTo(someFee);
     }
@@ -171,13 +154,8 @@ public void buildPaymentToContact() {
     @Test
     public void buildPaymentToAddress() {
 
-        final ExchangeRateWindow rates = Fixture.from(ExchangeRateWindow.class).gimme("valid");
-
         final PaymentRequest payReq = PaymentRequest.toAddress(
-                TemplateHelpers.address().generateValue(),
-                TemplateHelpers.money().generateValue(),
-                "some description",
-                10.0
+                TemplateHelpers.address().generateValue()
         );
 
         final long someFee = 123456;
@@ -205,14 +183,6 @@ public void buildPaymentToAddress() {
         assertThat(operation.receiverAddress).isEqualTo(payReq.getAddress());
         assertThat(operation.receiverAddressDerivationPath).isEqualTo(null);
 
-        // check amount
-        final ExchangeRateProvider provider = new ExchangeRateProvider(rates.toJson());
-        final MonetaryAmount inBtc = payReq.getAmount().with(provider.getCurrencyConversion("BTC"));
-        final long inSatoshis = BitcoinUtils.bitcoinsToSatoshis(inBtc);
-
-        assertThat(operation.amount.inInputCurrency).isEqualTo(payReq.getAmount());
-        assertThat(operation.amount.inSatoshis).isEqualTo(inSatoshis);
-
         // check fee
         assertThat(operation.fee.inSatoshis).isEqualTo(someFee);
     }
diff --git a/android/apolloui/build.gradle b/android/apolloui/build.gradle
index 727f11dc..502e5b68 100644
--- a/android/apolloui/build.gradle
+++ b/android/apolloui/build.gradle
@@ -84,7 +84,7 @@ static def configExternalLinks(productFlavor, String host) {
 
 
 android {
-    compileSdkVersion 33
+    compileSdk 34
 
     buildFeatures {
         viewBinding true
@@ -92,10 +92,10 @@ android {
 
     defaultConfig {
         applicationId "io.muun.apollo"
-        minSdkVersion 19
-        targetSdkVersion 33
-        versionCode 1200
-        versionName "52"
+        minSdk 19
+        targetSdk 34
+        versionCode 1201
+        versionName "52.1"
 
         // Needed to make sure these classes are available in the main DEX file for API 19
         // See: https://spin.atomicobject.com/2018/07/16/support-kitkat-multidex/
@@ -282,12 +282,12 @@ android {
         jvmTarget = JavaVersion.VERSION_1_8.toString()
     }
 
-    lintOptions {
+    lint {
         abortOnError true
         htmlReport true
         textReport true
-        lintConfig file("${project.rootDir}/linters/android-lint/config.xml")
-        baseline file("lint-baseline.xml")
+        lintConfig file("$rootDir/linters/android-lint/config.xml")
+        baseline file('lint-baseline.xml')
     }
 
     packagingOptions {
diff --git a/android/apolloui/src/androidTest/java/io/muun/apollo/presentation/LoginAndSignUpTests.kt b/android/apolloui/src/androidTest/java/io/muun/apollo/presentation/LoginAndSignUpTests.kt
index a65ec396..aac228e7 100644
--- a/android/apolloui/src/androidTest/java/io/muun/apollo/presentation/LoginAndSignUpTests.kt
+++ b/android/apolloui/src/androidTest/java/io/muun/apollo/presentation/LoginAndSignUpTests.kt
@@ -110,7 +110,7 @@ open class LoginAndSignUpTests : BaseInstrumentationTest() {
         signInScreen.awaitEmailVerification(user.email)
 
         signInScreen.back()
-        signInScreen.abortDialogCancel()
+        signInScreen.abortDialogCancelWithSafeguard()
         signInScreen.back()
         signInScreen.abortDialogAbort()
 
@@ -130,7 +130,7 @@ open class LoginAndSignUpTests : BaseInstrumentationTest() {
         signInScreen.back()
 
         signInScreen.back()
-        signInScreen.abortDialogCancel()
+        signInScreen.abortDialogCancelWithSafeguard()
         signInScreen.back()
         signInScreen.abortDialogAbort()
     }
@@ -143,31 +143,64 @@ open class LoginAndSignUpTests : BaseInstrumentationTest() {
         autoFlows.signUp()
         autoFlows.receiveMoneyFromNetwork(Money.of(0.02, "BTC"))
 
-        // Case 1) U.u user with balance > 0 but unconfirmed receiving tx
+        testDeleteWalletCases(isRecoverableUser = false)
+    }
+
+    @Test
+    fun test_06_a_recoverable_user_can_delete_wallet() {
+        val user = RandomUser()
+
+        autoFlows.createRecoverableUser(user.pin, user.email, user.password)
+        val recoveryCodeParts = autoFlows.setUpRecoveryCode()
+
+        autoFlows.receiveMoneyFromNetwork(Money.of(0.02, "BTC"))
+
+        testDeleteWalletCases(isRecoverableUser = true)
+
+        // Let's check user credentials don't work anymore
+        signInScreen.startLogin()
+
+        // Reject invalid email:
+        signInScreen.checkEmailConfirmEnabled(false)
+        signInScreen.enterEmail(user.email)
+        signInScreen.checkEmailConfirmEnabled(true)
+        signInScreen.confirmEmail()
+        signInScreen.checkEmailError()
+
+        signInScreen.recoverWithRecoveryCode()
+        signInScreen.enterRecoveryCode(recoveryCodeParts)
+        signInScreen.confirmRecoveryCodeOnlyLogin()
+
+        label(R.string.error_incorrect_recovery_code)
+    }
+
+    private fun testDeleteWalletCases(isRecoverableUser: Boolean) {
+
+        // Case 1) user with balance > 0 but unconfirmed receiving tx
         autoFlows.checkCannotDeleteWallet()
 
-        // Case 2) U.u user with balance > 0 with confirmed receiving tx but not settled
+        // Case 2) user with balance > 0 with confirmed receiving tx but not settled
         generateBlocksAndWaitForUpdate(1)
         autoFlows.checkCannotDeleteWallet()
 
-        // Case 3) U.u user with balance > 0 with settled receiving tx
+        // Case 3) user with balance > 0 with settled receiving tx
         generateBlocksAndWaitForUpdate(5) // Transaction Settled
         autoFlows.checkCannotDeleteWallet()
 
-        // Case 4) U.u user with balance = 0 but unconfirmed spending tx
+        // Case 4) user with balance = 0 but unconfirmed spending tx
 
         autoFlows.spendAllFunds("some description")
         autoFlows.checkCannotDeleteWallet()
 
-        // Case 5) U.u user with balance = 0 with confirmed spending tx but not settled
+        // Case 5) user with balance = 0 with confirmed spending tx but not settled
 
         generateBlocksAndWaitForUpdate(1)
         autoFlows.checkCannotDeleteWallet()
 
-        // Case 6) U.u user with balance = 0 with settled spending tx
+        // Case 6) user with balance = 0 with settled spending tx
 
         generateBlocksAndWaitForUpdate(5) // Transaction Settled
-        autoFlows.deleteWallet()
+        autoFlows.deleteWallet(isRecoverableUser = isRecoverableUser)
 
         // TODO make more convoluted scenarios? Failed txs, failed swaps, etc...?
     }
diff --git a/android/apolloui/src/androidTest/java/io/muun/apollo/presentation/ReceiveTests.kt b/android/apolloui/src/androidTest/java/io/muun/apollo/presentation/ReceiveTests.kt
new file mode 100644
index 00000000..be63cdde
--- /dev/null
+++ b/android/apolloui/src/androidTest/java/io/muun/apollo/presentation/ReceiveTests.kt
@@ -0,0 +1,27 @@
+package io.muun.apollo.presentation
+
+import androidx.test.ext.junit.runners.AndroidJUnit4
+import io.muun.apollo.domain.model.AddressType
+import org.javamoney.moneta.Money
+import org.junit.Test
+import org.junit.runner.RunWith
+
+@RunWith(AndroidJUnit4::class)
+open class ReceiveTests : BaseInstrumentationTest() {
+
+    @Test
+    fun test_01_a_user_can_receive_money_onchain_with_fixed_amount_aka_bitcoin_uri() {
+        autoFlows.signUp()
+
+        // Try with SEGWIT, default
+        val amount = Money.of(0.000102, "BTC")
+        autoFlows.receiveMoneyFromNetworkViaBitcoinUri(amount)
+
+        // Try with LEGACY
+        autoFlows.receiveMoneyFromNetworkViaBitcoinUri(amount, AddressType.LEGACY)
+
+        // Try with Taproot
+        autoFlows.receiveMoneyFromNetworkViaBitcoinUri(amount, AddressType.TAPROOT)
+
+    }
+}
\ No newline at end of file
diff --git a/android/apolloui/src/androidTest/java/io/muun/apollo/presentation/SettingsTests.kt b/android/apolloui/src/androidTest/java/io/muun/apollo/presentation/SettingsTests.kt
index 9eda3806..19105df0 100644
--- a/android/apolloui/src/androidTest/java/io/muun/apollo/presentation/SettingsTests.kt
+++ b/android/apolloui/src/androidTest/java/io/muun/apollo/presentation/SettingsTests.kt
@@ -1,7 +1,8 @@
 package io.muun.apollo.presentation
 
 import io.muun.apollo.utils.RandomUser
-import org.junit.Ignore
+import io.muun.apollo.utils.screens.ReceiveScreen
+import io.muun.common.model.ReceiveFormatPreference
 import org.junit.Test
 
 open class SettingsTests : BaseInstrumentationTest() {
@@ -41,18 +42,40 @@ open class SettingsTests : BaseInstrumentationTest() {
     }
 
     @Test
-    @Ignore("feature is not yet turned on")
-    fun test_03_a_user_can_change_lightning_default() {
+    fun test_03_a_user_can_change_receive_preference_and_receive_funds() {
         val user = RandomUser()
 
         autoFlows.signUp(user.pin)
 
-        autoFlows.checkOnReceiveIfQRIs(false)
+        // Check Default receive preference is bitcoin (no actual receive, other tests exercise that)
+        autoFlows.checkReceivePreferenceIs(ReceiveFormatPreference.ONCHAIN)
 
+        // Change to Lightning + receive
         autoFlows.turnOnReceiveLightningByDefault()
-        autoFlows.checkOnReceiveIfQRIs(true)
+        autoFlows.checkReceivePreferenceIs(ReceiveFormatPreference.LIGHTNING)
 
-        autoFlows.turnOnReceiveBitcoinByDefault()
-        autoFlows.checkOnReceiveIfQRIs(false)
+        autoFlows.receiveMoneyFromLNWithAmountLessInvoice(100_000)
+
+        // Change to Unified QR + receive
+        autoFlows.turnOnUnifiedQr()
+        autoFlows.checkReceivePreferenceIs(ReceiveFormatPreference.UNIFIED)
+
+        autoFlows.receiveMoneyFromUnifiedQrViaLightning(
+            100_000,
+            ReceiveScreen.UnifiedQrDraft.OffChain(100_000)
+        )
+
+        // Test Unified QR changes in config
+
+        homeScreen.goToReceive()
+        receiveScreen.checkUnifiedQrConfig()
+
+        // Test receive unified QR with amountless invoice
+
+        autoFlows.receiveMoneyFromUnifiedQrViaLightning(
+            200_000,
+            ReceiveScreen.UnifiedQrDraft.OffChain()
+        )
     }
+
 }
diff --git a/android/apolloui/src/androidTest/java/io/muun/apollo/utils/AutoFlows.kt b/android/apolloui/src/androidTest/java/io/muun/apollo/utils/AutoFlows.kt
index ef2a472b..37b1dd0c 100644
--- a/android/apolloui/src/androidTest/java/io/muun/apollo/utils/AutoFlows.kt
+++ b/android/apolloui/src/androidTest/java/io/muun/apollo/utils/AutoFlows.kt
@@ -6,6 +6,9 @@ import androidx.test.uiautomator.UiDevice
 import io.muun.apollo.R
 import io.muun.apollo.data.debug.LappClient
 import io.muun.apollo.data.external.Gen
+import io.muun.apollo.data.external.Globals
+import io.muun.apollo.domain.libwallet.BitcoinUri
+import io.muun.apollo.domain.model.AddressType
 import io.muun.apollo.domain.model.user.UserPhoneNumber
 import io.muun.apollo.presentation.ui.helper.isBtc
 import io.muun.apollo.presentation.ui.utils.OS
@@ -13,8 +16,10 @@ import io.muun.apollo.presentation.ui.utils.UiUtils
 import io.muun.apollo.utils.WithMuunInstrumentationHelpers.Companion.balanceNotEqualsErrorMessage
 import io.muun.apollo.utils.screens.ReceiveScreen
 import io.muun.common.model.DebtType
+import io.muun.common.model.ReceiveFormatPreference
 import io.muun.common.utils.BitcoinUtils
 import io.muun.common.utils.LnInvoice
+import io.muun.common.utils.Preconditions
 import org.javamoney.moneta.Money
 import javax.money.MonetaryAmount
 
@@ -149,12 +154,19 @@ class AutoFlows(
     }
 
     /**
-     * For Unrecoverable Users (some extra logic may apply, e.g u.u with positive balance may not
+     * Delete Wallet (some extra logic may apply, e.g u.u with positive balance may not
      * delete their wallets).
      */
-    fun deleteWallet() {
+    fun deleteWallet(isRecoverableUser: Boolean = false) {
         goToSettingsAndClickDeleteWallet()
 
+        if (isRecoverableUser) {
+            label(R.string.settings_delete_wallet_alert_body_recoverable_user).await()
+
+        } else {
+            label(R.string.settings_delete_wallet_alert_body_unrecoverable_user).await()
+        }
+
         // Confirm on pop-up message.
         normalizedLabel(R.string.settings_delete_wallet_alert_yes).click()
 
@@ -163,7 +175,7 @@ class AutoFlows(
     }
 
     /**
-     * For Unrecoverable Users, in some cases, we won't let them delete wallet if they can lose
+     * In some cases, we won't let them delete wallet if they can lose
      * money. This AutoFlow is what happens in those scenarios.
      */
     fun checkCannotDeleteWallet() {
@@ -175,6 +187,54 @@ class AutoFlows(
         backToHome()
     }
 
+    /**
+     * Receive funds using Unified QR feature, using the LN invoice embedded.
+     * Receive funds via Lightning Network using an AmountLess Invoice. TurboChannels flag hints
+     * whether we should check for operation status pending or not.
+     *
+     * NOTE: BEWARE if amount is low (< debt limit) and turboChannels is disabled, this method will
+     * fail as our Receive LN feature confirms the payment instantly (full debt mechanism).
+     */
+    fun receiveMoneyFromUnifiedQrViaLightning(
+        amountInSat: Long,
+        unifiedQrDraft: ReceiveScreen.UnifiedQrDraft,
+    ) {
+        val prevBalance = homeScreen.balanceInBtc
+
+        val unifiedQr = unifiedQrDraft as ReceiveScreen.UnifiedQrDraft.OffChain
+        Preconditions.checkArgument(
+            unifiedQr.amountInSat == null || unifiedQr.amountInSat == amountInSat
+        )
+
+        // For fixed amount invoices, amount MUST NOT be specified, otherwise an error occurs.
+        val amountToReceive = unifiedQr.amountInSat
+
+        val invoice = getOwnInvoiceFromUnifiedQr(amountToReceive)
+
+        LappClient().receiveBtcViaLN(invoice, amountInSat, unifiedQr.turboChannel)
+
+        // Wait for balance to be updated:
+        val amount = BitcoinUtils.satoshisToBitcoins(amountInSat)
+        homeScreen.waitUntilBalanceEquals(prevBalance.add(amount))
+
+        checkOperationDetails(amount, statusPending = !unifiedQr.turboChannel) {
+            homeScreen.goToOperationDetail(0)
+        }
+    }
+
+    private fun getOwnInvoiceFromUnifiedQr(amountInSat: Long? = null): String {
+        homeScreen.goToReceive()
+
+        if (amountInSat != null) {
+            receiveScreen.addUnifiedQrAmount(amountInSat)
+        }
+
+        val unifiedQr = receiveScreen.unifiedQr
+
+        device.pressBack() // Back to Home
+        return BitcoinUri.parse(unifiedQr).third
+    }
+
     /**
      * Receive funds via Lightning Network using an AmountLess Invoice. TurboChannels flag hints
      * whether we should check for operation status pending or not.
@@ -232,7 +292,55 @@ class AutoFlows(
         return invoice
     }
 
-    fun receiveMoneyFromNetwork(amount: Money) = try {
+    fun receiveMoneyFromNetworkViaBitcoinUri(
+        amount: MonetaryAmount,
+        addressType: AddressType = AddressType.SEGWIT,
+    ) = try {
+        tryReceiveMoneyFromNetworkViaBitcoinUri(amount, addressType)
+    } catch (e: AssertionError) {
+        if (e.message != null && e.message!!.contains(balanceNotEqualsErrorMessage)) {
+
+            LappClient().generateBlocks(30) // we don't want to need this again soon
+            Thread.sleep(2000)
+            tryReceiveMoneyFromNetwork(amount)
+        } else {
+            throw e
+        }
+    }
+
+    private fun tryReceiveMoneyFromNetworkViaBitcoinUri(
+        amount: MonetaryAmount,
+        addressType: AddressType = AddressType.SEGWIT,
+    ) {
+        val expectedBalance = homeScreen.balanceInBtc
+        val balanceAfter = expectedBalance.add(amount)
+
+        // Generate a Bitcoin Uri with amount:
+        val rawClipboard = getOwnBitcoinUri(amount, addressType)
+        val bitcoinUri = io.muun.common.bitcoinj.BitcoinUri(Globals.INSTANCE.network, rawClipboard)
+
+        val amountInBtc = BitcoinUtils.satoshisToBitcoins(bitcoinUri.amount.value)
+        assertMoneyEqualsWithRoundingHack(amountInBtc, amount)
+
+        // Hit RegTest to receive money from the network:
+        LappClient().receiveBtc(amountInBtc.number.toDouble(), bitcoinUri.address!!)
+
+        // Wait for balance to be updated:
+        homeScreen.waitUntilBalanceEquals(balanceAfter)
+    }
+
+    private fun getOwnBitcoinUri(amount: MonetaryAmount, addressType: AddressType): String {
+        homeScreen.goToReceive()
+
+        receiveScreen.addBitcoinUriAmount(amount)
+        receiveScreen.selectAddressType(addressType)
+
+        val bitcoinUri = receiveScreen.bitcoinUri
+        device.pressBack() // Back to Home
+        return bitcoinUri
+    }
+
+    fun receiveMoneyFromNetwork(amount: MonetaryAmount) = try {
         tryReceiveMoneyFromNetwork(amount)
     } catch (e: AssertionError) {
         if (e.message != null && e.message!!.contains(balanceNotEqualsErrorMessage)) {
@@ -245,7 +353,7 @@ class AutoFlows(
         }
     }
 
-    private fun tryReceiveMoneyFromNetwork(amount: Money) {
+    private fun tryReceiveMoneyFromNetwork(amount: MonetaryAmount) {
         val expectedBalance = homeScreen.balanceInBtc
         val balanceAfter = expectedBalance.add(amount)
 
@@ -582,16 +690,16 @@ class AutoFlows(
         backToHome()
     }
 
-    fun checkOnReceiveIfQRIs(lightning: Boolean) {
-        homeScreen.goToReceive()
-        if (lightning) {
-            receiveScreen.id(R.id.address_settings).assertDoesntExist()
-            receiveScreen.id(R.id.invoice_settings).exists()
-        } else {
-            receiveScreen.id(R.id.address_settings).exists()
-            receiveScreen.id(R.id.invoice_settings).assertDoesntExist()
-        }
+    fun turnOnUnifiedQr() {
+        homeScreen.goToSettings()
 
+        settingsScreen.turnOnUnifiedQr()
+        backToHome()
+    }
+
+    fun checkReceivePreferenceIs(receiveFormatPreference: ReceiveFormatPreference) {
+        homeScreen.goToReceive()
+        receiveScreen.checkReceivePreferenceIs(receiveFormatPreference)
         device.pressBack()
     }
 
diff --git a/android/apolloui/src/androidTest/java/io/muun/apollo/utils/screens/ChangePasswordScreen.kt b/android/apolloui/src/androidTest/java/io/muun/apollo/utils/screens/ChangePasswordScreen.kt
index dd450439..bca0ecd9 100644
--- a/android/apolloui/src/androidTest/java/io/muun/apollo/utils/screens/ChangePasswordScreen.kt
+++ b/android/apolloui/src/androidTest/java/io/muun/apollo/utils/screens/ChangePasswordScreen.kt
@@ -31,6 +31,7 @@ class ChangePasswordScreen(
         checkEmailVerificationScreenDisplayed(user.email)
 
         editNewPassword(newPassword)
+        reEnterNewPassword(newPassword)
         acceptConditions()
         confirmNewPassword()
 
@@ -67,7 +68,11 @@ class ChangePasswordScreen(
     }
 
     private fun editNewPassword(newPassword: String) {
-        input(R.id.change_password).text = newPassword
+        input(R.id.change_password_input).text = newPassword
+    }
+
+    private fun reEnterNewPassword(newPassword: String) {
+        input(R.id.change_password_confirm_input).text = newPassword
     }
 
     private fun confirmNewPassword() {
diff --git a/android/apolloui/src/androidTest/java/io/muun/apollo/utils/screens/ReceiveScreen.kt b/android/apolloui/src/androidTest/java/io/muun/apollo/utils/screens/ReceiveScreen.kt
index 5e88562c..be92f3e4 100644
--- a/android/apolloui/src/androidTest/java/io/muun/apollo/utils/screens/ReceiveScreen.kt
+++ b/android/apolloui/src/androidTest/java/io/muun/apollo/utils/screens/ReceiveScreen.kt
@@ -3,10 +3,17 @@ package io.muun.apollo.utils.screens
 import android.content.Context
 import androidx.test.uiautomator.UiDevice
 import io.muun.apollo.R
+import io.muun.apollo.data.external.Globals
+import io.muun.apollo.domain.libwallet.BitcoinUri
+import io.muun.apollo.domain.model.AddressType
 import io.muun.apollo.presentation.ui.show_qr.ShowQrPage
 import io.muun.apollo.utils.Clipboard
 import io.muun.apollo.utils.WithMuunInstrumentationHelpers
+import io.muun.common.bitcoinj.ValidationHelpers
+import io.muun.common.model.ReceiveFormatPreference
+import io.muun.common.utils.Bech32SegwitAddress
 import io.muun.common.utils.BitcoinUtils
+import org.assertj.core.api.Assertions.assertThat
 import javax.money.MonetaryAmount
 
 class ReceiveScreen(
@@ -19,6 +26,18 @@ class ReceiveScreen(
             private set
     }
 
+    sealed class UnifiedQrDraft {
+        data class OnChain(
+            val amount: MonetaryAmount? = null,
+            val addressType: AddressType = AddressType.SEGWIT,
+        ) : UnifiedQrDraft()
+
+        data class OffChain(
+            val amountInSat: Long? = null,
+            val turboChannel: Boolean = true,
+        ) : UnifiedQrDraft()
+    }
+
     val address: String
         get() {
             id(R.id.show_qr_copy).click()
@@ -26,6 +45,9 @@ class ReceiveScreen(
             return lastCopiedFromClipboard
         }
 
+    val bitcoinUri: String
+        get() = address // Yes, its obtained the same way, but callers should set up an amount first
+
     val invoice: String
         get() {
             normalizedLabel(ShowQrPage.LN.titleRes).click()
@@ -34,25 +56,173 @@ class ReceiveScreen(
             return lastCopiedFromClipboard
         }
 
+    val unifiedQr: String
+        get() {
+            id(R.id.show_qr_copy).click()
+            lastCopiedFromClipboard = Clipboard.read()
+            return lastCopiedFromClipboard
+        }
+
     fun goToScanLnUrl() {
         desc(R.string.scan_lnurl).click()
     }
 
+    fun selectAddressType(addressType: AddressType) {
+
+        if (!id(R.id.edit_address_type).exists()) {
+            id(R.id.address_settings).click()
+        }
+
+        id(R.id.edit_address_type).click()
+
+        when (addressType) {
+            AddressType.SEGWIT -> label(R.string.address_picker_segwit_title).click()
+            AddressType.LEGACY -> label(R.string.address_picker_legacy_title).click()
+            AddressType.TAPROOT -> label(R.string.address_picker_taproot_title).click()
+        }
+    }
+
+    private fun selectAddressTypeForUnifiedQr(addressType: AddressType) {
+
+        if (!id(R.id.edit_address_type).exists()) {
+            id(R.id.unified_qr_settings).click()
+        }
+
+        id(R.id.edit_address_type).click()
+
+        when (addressType) {
+            AddressType.SEGWIT -> label(R.string.address_picker_segwit_title).click()
+            AddressType.LEGACY -> label(R.string.address_picker_legacy_title).click()
+            AddressType.TAPROOT -> label(R.string.address_picker_taproot_title).click()
+        }
+    }
+
+    fun addUnifiedQrAmount(amountInSat: Long) {
+        id(R.id.unified_qr_settings).click()
+
+        editAmount(amountInSat)
+    }
+
     fun addInvoiceAmount(amountInSat: Long) {
         normalizedLabel(ShowQrPage.LN.titleRes).click()
         id(R.id.invoice_settings).click()
 
-        id(R.id.add_amount).click()
+        editAmount(amountInSat)
+    }
 
-        editAmount(BitcoinUtils.satoshisToBitcoins(amountInSat))
+    fun addBitcoinUriAmount(amount: MonetaryAmount) {
+        normalizedLabel(ShowQrPage.BITCOIN.titleRes).click()
+        id(R.id.address_settings).click()
 
-        pressMuunButton(R.id.confirm_amount_button)
+        editAmount(amount)
+    }
+
+    private fun editAmount(amountInSat: Long) {
+        editAmount(BitcoinUtils.satoshisToBitcoins(amountInSat))
     }
 
     private fun editAmount(amount: MonetaryAmount) {
+        if (id(R.id.add_amount).exists()) {
+            id(R.id.add_amount).click()
+
+        } else {
+            id(R.id.amount_label).click()
+        }
+
         id(R.id.currency_code).click()
         labelWith(amount.currency.currencyCode).click()
 
         id(R.id.muun_amount).text = amount.number.toString()
+
+        pressMuunButton(R.id.confirm_amount_button)
+    }
+
+    fun checkReceivePreferenceIs(receiveFormatPreference: ReceiveFormatPreference) {
+        when (receiveFormatPreference) {
+            ReceiveFormatPreference.ONCHAIN -> {
+                receiveScreen.id(R.id.address_settings).exists()
+                receiveScreen.id(R.id.invoice_settings).assertDoesntExist()
+                receiveScreen.id(R.id.unified_qr_settings).assertDoesntExist()
+            }
+            ReceiveFormatPreference.LIGHTNING -> {
+                receiveScreen.id(R.id.address_settings).assertDoesntExist()
+                receiveScreen.id(R.id.invoice_settings).exists()
+                receiveScreen.id(R.id.unified_qr_settings).assertDoesntExist()
+            }
+            ReceiveFormatPreference.UNIFIED -> {
+                receiveScreen.id(R.id.address_settings).assertDoesntExist()
+                receiveScreen.id(R.id.invoice_settings).assertDoesntExist()
+                receiveScreen.id(R.id.unified_qr_settings).exists()
+            }
+        }
+    }
+
+    fun checkUnifiedQrConfig() {
+        var amountInSat: Long = 100
+        var addressType = AddressType.SEGWIT
+
+        addUnifiedQrAmount(amountInSat)
+        selectAddressTypeForUnifiedQr(addressType)
+        checkUnifiedQrConfig(amountInSat, addressType)
+
+        amountInSat = 200
+        addressType = AddressType.LEGACY
+
+        changeAndCheck(amountInSat, addressType)
+
+        amountInSat = 300
+        addressType = AddressType.TAPROOT
+
+        changeAndCheck(amountInSat, addressType)
+
+        device.pressBack()
+    }
+
+    private fun changeAndCheck(amountInSat: Long, addressType: AddressType) {
+        editAmount(amountInSat)
+        selectAddressTypeForUnifiedQr(addressType)
+
+    }
+
+    private fun checkUnifiedQrConfig(
+        amountInSat: Long,
+        addressType: AddressType,
+    ) {
+        checkAmountIs(amountInSat)
+        checkAddressTypeIs(addressType)
+        id(R.id.expiration_time_item).exists()
+    }
+
+    private fun checkAmountIs(amountInSat: Long) {
+        checkAmountIs(BitcoinUtils.satoshisToBitcoins(amountInSat))
+    }
+
+    private fun checkAmountIs(expectedAmount: MonetaryAmount) {
+        val selectedAmount = id(R.id.selected_amount).text.toMoney()
+        assertMoneyEqualsWithRoundingHack(selectedAmount, expectedAmount)
+    }
+
+    private fun checkAddressTypeIs(expectedAddressType: AddressType) {
+        val addressType = id(R.id.edit_address_type).text
+
+        val (address, _, _) = BitcoinUri.parse(unifiedQr)
+        val params = Globals.INSTANCE.network
+
+        when (expectedAddressType) {
+            AddressType.SEGWIT -> {
+                assert(Bech32SegwitAddress.decode(params, address).fst.toInt() == 0)
+                assertThat(addressType).isEqualTo(context.getString(R.string.segwit))
+            }
+
+            AddressType.LEGACY -> {
+                assert(ValidationHelpers.isValidBase58Address(params, address))
+                assertThat(addressType).isEqualTo(context.getString(R.string.legacy))
+            }
+
+            AddressType.TAPROOT -> {
+                assert(Bech32SegwitAddress.decode(params, address).fst.toInt() == 1)
+                assertThat(addressType).isEqualTo(context.getString(R.string.taproot))
+            }
+        }
     }
 }
\ No newline at end of file
diff --git a/android/apolloui/src/androidTest/java/io/muun/apollo/utils/screens/SettingsScreen.kt b/android/apolloui/src/androidTest/java/io/muun/apollo/utils/screens/SettingsScreen.kt
index 4c53c814..a4d8c25b 100644
--- a/android/apolloui/src/androidTest/java/io/muun/apollo/utils/screens/SettingsScreen.kt
+++ b/android/apolloui/src/androidTest/java/io/muun/apollo/utils/screens/SettingsScreen.kt
@@ -19,7 +19,7 @@ class SettingsScreen(
     }
 
     fun deleteWallet() {
-        id(R.id.log_out_text_view).click()
+        id(R.id.delete_wallet_text_view).click()
     }
 
     fun setBitcoinUnitToSat() {
@@ -43,7 +43,7 @@ class SettingsScreen(
 
         id(R.id.receive_preference_value).click()
 
-        label(R.string.tab_ln_invoice).click()
+        label(R.string.receive_preference_lightning_title).click()
 
         device.pressBack()
     }
@@ -53,7 +53,17 @@ class SettingsScreen(
 
         id(R.id.receive_preference_value).click()
 
-        label(R.string.tab_bitcoin_address).click()
+        label(R.string.receive_preference_bitcoin_title).click()
+
+        device.pressBack()
+    }
+
+    fun turnOnUnifiedQr() {
+        id(R.id.settings_lightning).click()
+
+        id(R.id.receive_preference_value).click()
+
+        label(R.string.receive_preference_unified).click()
 
         device.pressBack()
     }
diff --git a/android/apolloui/src/androidTest/java/io/muun/apollo/utils/screens/SignInScreen.kt b/android/apolloui/src/androidTest/java/io/muun/apollo/utils/screens/SignInScreen.kt
index 25095b01..18da7e76 100644
--- a/android/apolloui/src/androidTest/java/io/muun/apollo/utils/screens/SignInScreen.kt
+++ b/android/apolloui/src/androidTest/java/io/muun/apollo/utils/screens/SignInScreen.kt
@@ -47,16 +47,24 @@ class SignInScreen(
 
         startLogin()
 
-        pressMuunButton(R.id.enter_email_use_rc_only)
+        recoverWithRecoveryCode()
 
         enterRecoveryCode(recoveryCodeParts)
-        pressMuunButton(R.id.rc_only_login_continue)
+        confirmRecoveryCodeOnlyLogin()
 
         if (email != null) {
             checkRcLoginEmailAuthScreenDisplayed(email)
         }
     }
 
+    fun recoverWithRecoveryCode() {
+        pressMuunButton(R.id.enter_email_use_rc_only)
+    }
+
+    fun confirmRecoveryCodeOnlyLogin() {
+        pressMuunButton(R.id.rc_only_login_continue)
+    }
+
     fun startSignup() {
         normalizedLabel(R.string.signup_start).click()
     }
@@ -141,6 +149,19 @@ class SignInScreen(
         checkInputError(R.id.signup_unlock_edit_password, R.string.error_incorrect_password)
     }
 
+    fun abortDialogCancelWithSafeguard() {
+        try {
+            signInScreen.abortDialogCancel()
+        } catch (_: Exception) {
+            // I'm DONE with this annoying issue regarding Google Password Manager.
+            // Not gonna keep suffering flakiness from it. ENOUGH!
+            // TODO: find reliable way to disable Google Password Manager
+            signInScreen.back() // Add extra back to dismiss Google Password Manager popup
+            signInScreen.abortDialogCancel()
+        }
+    }
+
+
     fun abortDialogCancel() {
         normalizedLabel(R.string.cancel).click()
     }
@@ -149,11 +170,11 @@ class SignInScreen(
         normalizedLabel(R.string.abort).click()
     }
 
-    private fun enterRecoveryCode(recoveryCodeParts: List<String>) {
+    fun enterRecoveryCode(recoveryCodeParts: List<String>) {
         recoveryCodeScreen.enterRecoveryCode(recoveryCodeParts)
     }
 
-    private fun confirmRecoveryCode() {
+    fun confirmRecoveryCode() {
         pressMuunButton(R.id.signup_forgot_password_continue)
     }
 }
\ No newline at end of file
diff --git a/android/apolloui/src/main/java/io/muun/apollo/presentation/app/Navigator.java b/android/apolloui/src/main/java/io/muun/apollo/presentation/app/Navigator.java
index 1e68b0bd..f2944d04 100644
--- a/android/apolloui/src/main/java/io/muun/apollo/presentation/app/Navigator.java
+++ b/android/apolloui/src/main/java/io/muun/apollo/presentation/app/Navigator.java
@@ -495,7 +495,7 @@ public void navigateToLauncher(@NotNull Context context) {
     public void navigateToDeleteWallet(@NotNull Context context) {
         final Optional<String> maybeSupportId = userSel.getOptional().flatMap(User::getSupportId);
 
-        logoutActions.dangerouslyDestroyUnrecoverableWallet();
+        logoutActions.dangerouslyDestroyWallet();
 
         final Intent intent = SuccessDeleteWalletActivity
                 .getStartActivityIntent(context, maybeSupportId);
diff --git a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/base/BaseActivity.java b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/base/BaseActivity.java
index ad72d37c..d66f57e6 100644
--- a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/base/BaseActivity.java
+++ b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/base/BaseActivity.java
@@ -160,7 +160,7 @@ protected void onCreate(@Nullable Bundle savedInstanceState) {
         try {
             super.onCreate(savedInstanceState);
 
-            Timber.d("Lifecycle: " + getClass().getSimpleName() + "#onCreate");
+            Timber.i("Lifecycle: " + getClass().getSimpleName() + "#onCreate");
 
             if (savedInstanceState != null) {
                 Timber.i("Lifecycle: " + getClass().getSimpleName() + " is being recreated");
diff --git a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/base/BaseFragment.java b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/base/BaseFragment.java
index d42d0762..121320c5 100644
--- a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/base/BaseFragment.java
+++ b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/base/BaseFragment.java
@@ -160,7 +160,7 @@ public View onCreateView(
             ViewGroup container,
             Bundle savedInstanceState
     ) {
-        Timber.d("Lifecycle: " + getClass().getSimpleName() + "#onCreateView");
+        Timber.i("Lifecycle: " + getClass().getSimpleName() + "#onCreateView");
 
         if (savedInstanceState != null) {
             Timber.i("Lifecycle: " + getClass().getSimpleName() + " is being recreated");
@@ -200,7 +200,7 @@ private View inflateLayout(@NonNull LayoutInflater inflater, ViewGroup container
      */
     @Override
     public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) {
-        Timber.d("Lifecycle: " + getClass().getSimpleName() + "#onViewCreated");
+        Timber.i("Lifecycle: " + getClass().getSimpleName() + "#onViewCreated");
         initializeUi(view);
         presenter.onViewCreated(savedInstanceState);
     }
diff --git a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/ek_save/EmergencyKitSaveFragment.kt b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/ek_save/EmergencyKitSaveFragment.kt
index d9f599f3..8140fdae 100644
--- a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/ek_save/EmergencyKitSaveFragment.kt
+++ b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/ek_save/EmergencyKitSaveFragment.kt
@@ -107,7 +107,7 @@ class EmergencyKitSaveFragment : SingleFragment<EmergencyKitSavePresenter>(),
     override fun setDriveUploading(isUploading: Boolean) {
         if (isUploading) {
             val message = if (argumentsBundle.getBoolean(ARG_UPDATE_KIT)) {
-                R.string.ek_uploading_body
+                R.string.ek_updating_body
             } else {
                 R.string.ek_uploading_body
             }
diff --git a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/home/HomeFragment.kt b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/home/HomeFragment.kt
index ed30d771..0f74d4ca 100644
--- a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/home/HomeFragment.kt
+++ b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/home/HomeFragment.kt
@@ -166,7 +166,7 @@ class HomeFragment : SingleFragment<HomeFragmentPresenter>(), HomeFragmentView {
         private val minTravelDistance = ViewConfiguration.get(context).scaledTouchSlop
 
         override fun onFling(
-            e1: MotionEvent,
+            e1: MotionEvent?,
             e2: MotionEvent,
             velocityX: Float,
             velocityY: Float,
@@ -174,7 +174,7 @@ class HomeFragment : SingleFragment<HomeFragmentPresenter>(), HomeFragmentView {
 
             // Future reader: for MotionEvent we want rawX/Y, other coordinates suck (BIG TIME)
             // See: https://stackoverflow.com/q/1410885/901465
-            if (abs(velocityY) > minVelocity && e1.rawY - e2.rawY > minTravelDistance) {
+            if (abs(velocityY) > minVelocity && e1 != null && e1.rawY - e2.rawY > minTravelDistance) {
                 chevron.performClick()
                 return true
             }
diff --git a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/manual_fee/ManualFeeFragment.kt b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/manual_fee/ManualFeeFragment.kt
index d68aee59..d1b72ab5 100644
--- a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/manual_fee/ManualFeeFragment.kt
+++ b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/manual_fee/ManualFeeFragment.kt
@@ -2,13 +2,11 @@ package io.muun.apollo.presentation.ui.fragments.manual_fee
 
 import android.text.TextUtils
 import android.view.View
-import android.widget.TextView
 import butterknife.BindString
 import butterknife.BindView
 import butterknife.OnClick
 import icepick.State
 import io.muun.apollo.R
-import io.muun.apollo.domain.Flags
 import io.muun.apollo.domain.model.BitcoinAmount
 import io.muun.apollo.domain.model.BitcoinUnit
 import io.muun.apollo.presentation.ui.base.SingleFragment
@@ -36,9 +34,6 @@ class ManualFeeFragment : SingleFragment<ManualFeePresenter>(), ManualFeeView {
     @BindView(R.id.status_message)
     lateinit var statusMessage: StatusMessage
 
-    @BindView(R.id.use_maximum_fee)
-    lateinit var useMaximumFee: TextView
-
     @BindView(R.id.confirm_fee)
     lateinit var confirmButton: MuunButton
 
@@ -51,8 +46,6 @@ class ManualFeeFragment : SingleFragment<ManualFeePresenter>(), ManualFeeView {
     @State
     lateinit var mBitcoinUnit: BitcoinUnit
 
-    private var shouldShowMaxFeeButton = false
-
     override fun inject() {
         component.inject(this)
     }
@@ -89,7 +82,6 @@ class ManualFeeFragment : SingleFragment<ManualFeePresenter>(), ManualFeeView {
             confirmButton.isEnabled = false
             statusMessage.visibility = View.GONE
             feeInput.resetVisibility()
-            useMaximumFee.visibility = if (shouldShowMaxFeeButton) View.VISIBLE else View.GONE
 
             // 1.5 If feeRate is null, we're back at initial state (empty input), nothing else to do
             if (feeRateInSatsPerVByte == null) {
@@ -130,16 +122,6 @@ class ManualFeeFragment : SingleFragment<ManualFeePresenter>(), ManualFeeView {
                 }
             }
         }
-
-        shouldShowMaxFeeButton = showMaximumFeeButton(state)
-
-        if (shouldShowMaxFeeButton) {
-            useMaximumFee.visibility = View.VISIBLE
-            useMaximumFee.setOnClickListener {
-                feeInput.setFeeRate(state.maxFeeRateInSatsPerVByte)
-                useMaximumFee.visibility = View.GONE
-            }
-        }
     }
 
     @OnClick(R.id.confirm_fee)
@@ -189,19 +171,6 @@ class ManualFeeFragment : SingleFragment<ManualFeePresenter>(), ManualFeeView {
         confirmButton.isEnabled = true // just a warning
     }
 
-    private fun showMaximumFeeButton(state: EditFeeState): Boolean {
-
-        // TODO disabled until properly tested and QA vetted
-        if (!Flags.USE_MAXIMUM_FEE_ENABLED) {
-            return false
-        }
-
-        // Replicating Falcon logic here.
-        // The use max fee button is only displayed in case the user is not taking fee from amount
-        // (aka using all funds) and if the user doesn't have a selected fee
-        return !state.amountInfo.takeFeeFromAmount && state.validated.feeNeedsChange
-    }
-
     private fun onHowThisWorksClick() {
         val dialog = TitleAndDescriptionDrawer()
         dialog.setTitle(R.string.manual_fee_how_this_works_explanation_title)
diff --git a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/settings/SettingsFragment.kt b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/settings/SettingsFragment.kt
index cc82daa4..7e8f47a6 100644
--- a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/settings/SettingsFragment.kt
+++ b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/settings/SettingsFragment.kt
@@ -368,8 +368,8 @@ open class SettingsFragment : SingleFragment<SettingsPresenter>(), SettingsView
         showDialog(muunDialog)
     }
 
-    override fun handleDeleteWallet(isActionBlocked: Boolean, isRecoverableUser: Boolean) {
-        if (isActionBlocked) {
+    override fun handleDeleteWallet(canDeleteWallet: Boolean, isRecoverableUser: Boolean) {
+        if (!canDeleteWallet) {
             showCantDeleteNonEmptyWalletDialog()
 
         } else {
diff --git a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/settings/SettingsPresenter.kt b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/settings/SettingsPresenter.kt
index c8c0406f..a4d6cdec 100644
--- a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/settings/SettingsPresenter.kt
+++ b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/settings/SettingsPresenter.kt
@@ -203,7 +203,7 @@ class SettingsPresenter @Inject constructor(
         val options = logoutOptionsSel.watch()
             .toBlocking()
             .first()
-        val shouldBlockAndExplain = options.isBlocked()
+        val shouldBlockAndExplain = options.isLogoutBlocked()
 
         Preconditions.checkArgument(options.isRecoverable())
         view.handleLogout(shouldBlockAndExplain)
@@ -218,7 +218,7 @@ class SettingsPresenter @Inject constructor(
             .toBlocking()
             .first()
 
-        view.handleDeleteWallet(options.isBlocked(), options.isRecoverable())
+        view.handleDeleteWallet(options.canDeleteWallet(), options.isRecoverable())
     }
 
     override fun getEntryEvent(): AnalyticsEvent {
diff --git a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/settings/SettingsView.java b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/settings/SettingsView.java
index b079c19c..dc6b6060 100644
--- a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/settings/SettingsView.java
+++ b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/fragments/settings/SettingsView.java
@@ -42,7 +42,7 @@ public interface SettingsView extends BaseView {
     /**
      * Handle the delete wallet action.
      */
-    void handleDeleteWallet(boolean isActionBlocked, boolean isRecoverableUser);
+    void handleDeleteWallet(boolean canDeleteWallet, boolean isRecoverableUser);
 
     /**
      * Show a simple, standard muun error dialog to communicate that non empty wallet can't be
diff --git a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/launcher/LauncherPresenter.java b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/launcher/LauncherPresenter.java
index 4679eb37..28de2805 100644
--- a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/launcher/LauncherPresenter.java
+++ b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/launcher/LauncherPresenter.java
@@ -12,6 +12,7 @@
 
 import android.net.Uri;
 import androidx.annotation.Nullable;
+import timber.log.Timber;
 
 import javax.inject.Inject;
 
@@ -50,6 +51,9 @@ public void handleLaunch(@Nullable Uri uri, boolean isTaskRoot) {
 
         if (Globals.INSTANCE.getVersionCode() >= minClientVersion) {
 
+            final String maybeUri = uri != null ? uri.toString() : "null";
+            Timber.i("HandleLaunch(isTaskRoot: %s, uri: %s)", isTaskRoot, maybeUri);
+
             // If we caught an Intent with an URI (from an external Muun link), handle it:
             if (uri != null) {
                 useMuunLinkAction.run(uri.toString());
diff --git a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/settings/edit_password/ChangePasswordFragment.kt b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/settings/edit_password/ChangePasswordFragment.kt
index 255a7812..26268521 100644
--- a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/settings/edit_password/ChangePasswordFragment.kt
+++ b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/settings/edit_password/ChangePasswordFragment.kt
@@ -1,5 +1,6 @@
 package io.muun.apollo.presentation.ui.settings.edit_password
 
+import android.text.TextUtils
 import android.view.View
 import android.widget.CheckBox
 import butterknife.BindView
@@ -10,11 +11,15 @@ import io.muun.apollo.presentation.ui.base.BaseActivity
 import io.muun.apollo.presentation.ui.base.SingleFragment
 import io.muun.apollo.presentation.ui.view.MuunButton
 import io.muun.apollo.presentation.ui.view.MuunTextInput
+import io.muun.common.Rules
 
 class ChangePasswordFragment : SingleFragment<ChangePasswordPresenter>(), ChangePasswordView {
 
-    @BindView(R.id.change_password)
-    lateinit var password: MuunTextInput
+    @BindView(R.id.change_password_input)
+    lateinit var passwordInput: MuunTextInput
+
+    @BindView(R.id.change_password_confirm_input)
+    lateinit var passwordConfirmInput: MuunTextInput
 
     @BindView(R.id.change_password_condition)
     lateinit var condition: CheckBox
@@ -31,10 +36,28 @@ class ChangePasswordFragment : SingleFragment<ChangePasswordPresenter>(), Change
     }
 
     override fun initializeUi(view: View) {
-        password.setPasswordRevealEnabled(true)
         continueButton.isEnabled = false
 
-        condition.setOnCheckedChangeListener { _, _ -> onConditionCheckedChanged() }
+        passwordInput.setPasswordRevealEnabled(true)
+        passwordInput.setOnChangeListener(this) {
+            // Ugly check needed for some convoluted scenario where we receive input and fragment
+            // is being re-created or something
+            if (::passwordInput.isInitialized) {
+                validateInputs()
+            }
+        }
+        passwordConfirmInput.setPasswordRevealEnabled(true)
+        passwordConfirmInput.setOnChangeListener(this) {
+            // Ugly check needed for some convoluted scenario where we receive input and fragment
+            // is being re-created or something
+            if (::passwordConfirmInput.isInitialized) {
+                validateInputs()
+            }
+        }
+
+        condition.setOnCheckedChangeListener { _, _ ->
+            validateInputs()
+        }
         continueButton.setOnClickListener { onContinueButtonClick() }
     }
 
@@ -51,7 +74,7 @@ class ChangePasswordFragment : SingleFragment<ChangePasswordPresenter>(), Change
     }
 
     private fun abort() {
-        safeGetParentActivity().ifPresent(BaseActivity<*>::finish)
+        safeGetParentActivity().ifPresent(BaseActivity<*>::finishActivity)
     }
 
     override fun setLoading(loading: Boolean) {
@@ -60,27 +83,44 @@ class ChangePasswordFragment : SingleFragment<ChangePasswordPresenter>(), Change
     }
 
     override fun setPasswordError(error: UserFacingError?) {
-        password.clearError()
+        passwordInput.clearError()
+
+        if (error != null) {
+            passwordInput.setError(error)
+            passwordInput.requestFocusInput()
+        }
+    }
+
+    override fun setConfirmPasswordError(error: UserFacingError?) {
+        passwordConfirmInput.clearError()
+
         if (error != null) {
-            password.setError(error)
-            password.requestFocusInput()
+            passwordConfirmInput.setError(error)
+            passwordConfirmInput.requestFocusInput()
         }
     }
 
     override fun onResume() {
         super.onResume()
-        password.requestFocusInput()
+        passwordInput.requestFocusInput()
     }
 
     override fun blockScreenshots(): Boolean {
         return true
     }
 
-    private fun onConditionCheckedChanged() {
-        continueButton.isEnabled = condition.isChecked
+    private fun validateInputs() {
+        val validPassword = isValidPassword(passwordInput.text.toString())
+        val validPasswordConfirm = isValidPassword(passwordConfirmInput.text.toString())
+
+        continueButton.isEnabled = validPassword && validPasswordConfirm && condition.isChecked
     }
 
     private fun onContinueButtonClick() {
-        presenter.submitPassword(password.text.toString())
+        presenter.submitPassword(passwordInput.text.toString(), passwordConfirmInput.text.toString())
     }
+
+    private fun isValidPassword(password: String) =
+        !TextUtils.isEmpty(password) && password.length >= Rules.PASSWORD_MIN_LENGTH
+
 }
\ No newline at end of file
diff --git a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/settings/edit_password/ChangePasswordPresenter.kt b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/settings/edit_password/ChangePasswordPresenter.kt
index 2ea18c46..89adf99e 100644
--- a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/settings/edit_password/ChangePasswordPresenter.kt
+++ b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/settings/edit_password/ChangePasswordPresenter.kt
@@ -8,6 +8,7 @@ import io.muun.apollo.domain.analytics.AnalyticsEvent.E_PASSWORD_CHANGED
 import io.muun.apollo.domain.analytics.AnalyticsEvent.S_PASSWORD_CHANGE_END
 import io.muun.apollo.domain.errors.EmptyFieldError
 import io.muun.apollo.domain.errors.passwd.PasswordTooShortError
+import io.muun.apollo.domain.errors.passwd.PasswordsDontMatchError
 import io.muun.apollo.presentation.ui.base.di.PerFragment
 import io.muun.common.Rules
 import javax.inject.Inject
@@ -46,7 +47,7 @@ class ChangePasswordPresenter @Inject constructor(
     /**
      * Submit the new password, checking for errors.
      */
-    fun submitPassword(password: String) {
+    fun submitPassword(password: String, confirmPassword: String) {
         view.setPasswordError(null)
 
         if (password == "") {
@@ -55,8 +56,12 @@ class ChangePasswordPresenter @Inject constructor(
         } else if (password.length < Rules.PASSWORD_MIN_LENGTH) {
             view.setPasswordError(PasswordTooShortError())
 
+        } else if (password != confirmPassword) {
+            view.setConfirmPasswordError(PasswordsDontMatchError())
+
         } else {
             view.setPasswordError(null)
+            view.setConfirmPasswordError(null)
             view.setLoading(true)
             finishPasswordChange.run(parentPresenter.currentUuid, password)
         }
diff --git a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/settings/edit_password/ChangePasswordView.java b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/settings/edit_password/ChangePasswordView.java
index 2a24c90b..38111c56 100644
--- a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/settings/edit_password/ChangePasswordView.java
+++ b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/settings/edit_password/ChangePasswordView.java
@@ -7,4 +7,6 @@ public interface ChangePasswordView extends SingleFragmentView {
 
     void setPasswordError(UserFacingError error);
 
+    void setConfirmPasswordError(UserFacingError error);
+
 }
diff --git a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/view/FeeManualInput.java b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/view/FeeManualInput.java
index de893d76..bf55aaa3 100644
--- a/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/view/FeeManualInput.java
+++ b/android/apolloui/src/main/java/io/muun/apollo/presentation/ui/view/FeeManualInput.java
@@ -24,7 +24,6 @@
 import icepick.State;
 import timber.log.Timber;
 
-import java.math.RoundingMode;
 import java.text.DecimalFormatSymbols;
 import java.text.NumberFormat;
 import java.text.ParseException;
@@ -78,8 +77,6 @@ public interface OnChangeListener {
 
     private OnChangeListener onChangeListener;
 
-    private boolean isSkippingListeners;
-
     public FeeManualInput(Context context) {
         super(context);
     }
@@ -115,9 +112,7 @@ public void onTextChanged(CharSequence s, int start, int before, int count) {
 
             @Override
             public void afterTextChanged(Editable s) {
-                if (!isSkippingListeners) {
-                    updateFeeRate(parseNumber(s.toString()));
-                }
+                updateFeeRate(parseNumber(s.toString()));
             }
         });
     }
@@ -133,17 +128,6 @@ public void requestFocusInput() {
         }
     }
 
-    /**
-     * Set input's fee rate, in satoshis per virtual byte.
-     */
-    public void setFeeRate(double feeRateInSatsPerVbyte) {
-        isSkippingListeners = true;
-        feeRateInput.setText(UiUtils.formatFeeRate(feeRateInSatsPerVbyte, RoundingMode.FLOOR));
-        isSkippingListeners = false;
-
-        updateFeeRate(feeRateInSatsPerVbyte);
-    }
-
     private void updateFeeRate(Double feeRateInSatsPerVbyte) {
         this.feeRateInSatsPerVbyte = feeRateInSatsPerVbyte;
         notifyChange();
diff --git a/android/apolloui/src/main/res/layout/change_password_fragment.xml b/android/apolloui/src/main/res/layout/change_password_fragment.xml
index e8f60153..8a888a6c 100644
--- a/android/apolloui/src/main/res/layout/change_password_fragment.xml
+++ b/android/apolloui/src/main/res/layout/change_password_fragment.xml
@@ -26,7 +26,7 @@
                     android:text="@string/change_password_title" />
 
             <io.muun.apollo.presentation.ui.view.MuunTextInput
-                    android:id="@+id/change_password"
+                    android:id="@+id/change_password_input"
                     android:layout_width="match_parent"
                     android:layout_height="wrap_content"
                     android:inputType="textPassword"
@@ -35,6 +35,19 @@
                     android:hint="@string/change_password_hint"
                     app:helperText="@string/change_password_helper_text" />
 
+            <io.muun.apollo.presentation.ui.view.MuunTextInput
+                    android:id="@+id/change_password_confirm_input"
+                    android:layout_width="match_parent"
+                    android:layout_height="wrap_content"
+                    android:layout_marginTop="8dp"
+                    android:layout_gravity="center_horizontal"
+                    android:fontFamily="sans-serif"
+                    android:hint="@string/change_password_confirm_input_hint"
+                    android:imeOptions="actionNext"
+                    android:inputType="textPassword"
+                    app:helperText="@string/change_password_helper_text"
+                    app:passwordToggleEnabled="true" />
+
             <CheckBox
                     style="@style/explanation_checkbox"
                     android:id="@+id/change_password_condition"
diff --git a/android/apolloui/src/main/res/layout/manual_fee_selection_fragment.xml b/android/apolloui/src/main/res/layout/manual_fee_selection_fragment.xml
index 3581d265..ba7aff94 100644
--- a/android/apolloui/src/main/res/layout/manual_fee_selection_fragment.xml
+++ b/android/apolloui/src/main/res/layout/manual_fee_selection_fragment.xml
@@ -37,22 +37,6 @@
                 android:visibility="gone"
                 tools:visibility="visible"/>
 
-        <TextView
-                android:id="@+id/use_maximum_fee"
-                android:layout_width="wrap_content"
-                android:layout_height="wrap_content"
-                android:paddingTop="14dp"
-                android:paddingBottom="14dp"
-                android:paddingEnd="14dp"
-                android:text="@string/use_maximum_fee"
-                android:textAllCaps="true"
-                android:textSize="14sp"
-                android:textColor="@color/blue"
-                android:fontFamily="sans-serif-medium"
-                android:visibility="gone"
-                tools:visibility="visible"
-                tools:ignore="RtlSymmetry" />
-
     </LinearLayout>
 
     <io.muun.apollo.presentation.ui.view.MuunButton
diff --git a/android/apolloui/src/main/res/values-es/strings.xml b/android/apolloui/src/main/res/values-es/strings.xml
index e3c43207..a95676b2 100644
--- a/android/apolloui/src/main/res/values-es/strings.xml
+++ b/android/apolloui/src/main/res/values-es/strings.xml
@@ -908,6 +908,7 @@
     <string name="change_password_title">Ingresa tu nueva contraseña</string>
     <string name="change_password_hint">Nueva contraseña</string>
     <string name="change_password_helper_text">@string/create_password_input_helper</string>
+    <string name="change_password_confirm_input_hint">@string/create_password_confirm_input_hint</string>
     <string name="change_password_condition">Entiendo que mi contraseña anterior ya no será válida.
     </string>
     <string name="change_password_continue">Confirma tu nueva contraseña</string>
@@ -1114,7 +1115,6 @@
         No tienes fondos suficientes para pagar la comisión óptima.
         <annotation fontColor="muunBlue">Elige una comisión</annotation> para continuar.
     </string>
-    <string name="use_maximum_fee">Usar máxima comisión disponible</string>
     <string name="new_op_error_required_amount">Total (Monto + Comisión Mínima)</string>
     <string name="new_op_error_total_balance">Tu balance</string>
 
diff --git a/android/apolloui/src/main/res/values/strings.xml b/android/apolloui/src/main/res/values/strings.xml
index b37e33e4..275a2e59 100644
--- a/android/apolloui/src/main/res/values/strings.xml
+++ b/android/apolloui/src/main/res/values/strings.xml
@@ -875,6 +875,7 @@
     <string name="change_password_title">Enter your new password</string>
     <string name="change_password_hint">New password</string>
     <string name="change_password_helper_text">@string/create_password_input_helper</string>
+    <string name="change_password_confirm_input_hint">@string/create_password_confirm_input_hint</string>
     <string name="change_password_condition">
         I understand that my previous password is no longer valid.
     </string>
@@ -1074,7 +1075,6 @@
         Not enough funds to pay for the optimal network fee.
         <annotation fontColor="muunBlue"> Select a network fee </annotation> to continue.
     </string>
-    <string name="use_maximum_fee">Use maximum fee</string>
     <string name="new_op_error_required_amount">Total (Amount + Minimum Fee)</string>
     <string name="new_op_error_total_balance">Your balance</string>
 
diff --git a/build.gradle b/build.gradle
index 6c5f2510..db6dc2a3 100644
--- a/build.gradle
+++ b/build.gradle
@@ -9,7 +9,7 @@ buildscript {
     }
 
     dependencies { // Add third party gradle plugins
-        classpath 'com.android.tools.build:gradle:7.0.4'
+        classpath 'com.android.tools.build:gradle:7.4.2'
         // We're using a patched version of SQLDelight, for reproducible builds. Thanks JitPack!
         classpath 'com.github.muun.sqldelight:gradle-plugin:1.5.3-reproducible-build'
     }
diff --git a/common/src/main/java/io/muun/common/api/SessionJson.java b/common/src/main/java/io/muun/common/api/SessionJson.java
index 5ea7803e..b9c39223 100644
--- a/common/src/main/java/io/muun/common/api/SessionJson.java
+++ b/common/src/main/java/io/muun/common/api/SessionJson.java
@@ -18,7 +18,7 @@ public class SessionJson {
     public String buildType;
 
     @Nonnegative
-    public int version;
+    public int version; // this is the clientVersion, not a session version.
 
     @NotEmpty
     public String gcmRegistrationToken;
diff --git a/common/src/main/java/io/muun/common/api/error/ErrorCode.java b/common/src/main/java/io/muun/common/api/error/ErrorCode.java
index c8ff5944..26435839 100644
--- a/common/src/main/java/io/muun/common/api/error/ErrorCode.java
+++ b/common/src/main/java/io/muun/common/api/error/ErrorCode.java
@@ -229,7 +229,9 @@ public enum ErrorCode {
             2086, StatusCode.CLIENT_FAILURE, "Cannot delete wallet with funds"
     ),
     UNSETTLED_OPERATIONS(
-            2087, StatusCode.CLIENT_FAILURE, "Cannot delete wallet with unsettled operations"
+            2087,
+            StatusCode.CLIENT_FAILURE,
+            "Cannot delete wallet with unsettled operations"
     ),
 
     // error responses
diff --git a/common/src/main/java/io/muun/common/utils/Preconditions.java b/common/src/main/java/io/muun/common/utils/Preconditions.java
index 240248e2..79655c11 100644
--- a/common/src/main/java/io/muun/common/utils/Preconditions.java
+++ b/common/src/main/java/io/muun/common/utils/Preconditions.java
@@ -187,7 +187,7 @@ public static <T> T checkNotNull(T reference, @Nullable Object errorMessage) {
 
     /**
      * If a condition is true, ensures that an object reference is not null. If it's false, ensure
-     * that the the reference is null.
+     * that the reference is null.
      *
      * @return the null reference that was validated
      * @throws IllegalArgumentException if {@code reference} is not null
@@ -201,7 +201,6 @@ public static <T> T checkNotNullOnlyIf(@Nullable T reference, boolean condition)
         }
     }
 
-
     /**
      * Ensures that an object reference passed as a parameter to the calling method is null.
      *
@@ -349,20 +348,6 @@ public static long checkPositive(long number, @Nullable Object errorMessage) {
         return number;
     }
 
-    /**
-     * Ensures that {@code number} is positive.
-     *
-     * @param number a number
-     * @return the value of {@code number}
-     * @throws IllegalArgumentException if {@code number} is negative
-     */
-    public static long checkNonNegative(long number) {
-        if (number < 0) {
-            throw new IllegalArgumentException("Number " + number + " expected to be non-negative");
-        }
-        return number;
-    }
-
     /**
      * Ensures that {@code index} specifies a valid <i>element</i> in an array, list or string of
      * size {@code size}. An element index may range from zero, inclusive, to {@code size},
diff --git a/gradle/wrapper/gradle-wrapper.jar b/gradle/wrapper/gradle-wrapper.jar
index 5c2d1cf016b3885f6930543d57b744ea8c220a1a..249e5832f090a2944b7473328c07c9755baa3196 100644
GIT binary patch
delta 27732
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%0A;;yf0E35a&Q?rA8EdZaIIm+
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
G>;C}_dM#G~

delta 22714
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
Hf`RdWH%nX+

diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties
index 669386b8..8fad3f5a 100644
--- a/gradle/wrapper/gradle-wrapper.properties
+++ b/gradle/wrapper/gradle-wrapper.properties
@@ -1,5 +1,5 @@
 distributionBase=GRADLE_USER_HOME
 distributionPath=wrapper/dists
-distributionUrl=https\://services.gradle.org/distributions/gradle-7.3.3-all.zip
+distributionUrl=https\://services.gradle.org/distributions/gradle-7.5.1-all.zip
 zipStoreBase=GRADLE_USER_HOME
 zipStorePath=wrapper/dists
diff --git a/gradlew b/gradlew
index 83f2acfd..a69d9cb6 100755
--- a/gradlew
+++ b/gradlew
@@ -1,7 +1,7 @@
-#!/usr/bin/env sh
+#!/bin/sh
 
 #
-# Copyright 2015 the original author or authors.
+# Copyright © 2015-2021 the original authors.
 #
 # Licensed under the Apache License, Version 2.0 (the "License");
 # you may not use this file except in compliance with the License.
@@ -17,78 +17,113 @@
 #
 
 ##############################################################################
-##
-##  Gradle start up script for UN*X
-##
+#
+#   Gradle start up script for POSIX generated by Gradle.
+#
+#   Important for running:
+#
+#   (1) You need a POSIX-compliant shell to run this script. If your /bin/sh is
+#       noncompliant, but you have some other compliant shell such as ksh or
+#       bash, then to run this script, type that shell name before the whole
+#       command line, like:
+#
+#           ksh Gradle
+#
+#       Busybox and similar reduced shells will NOT work, because this script
+#       requires all of these POSIX shell features:
+#         * functions;
+#         * expansions «$var», «${var}», «${var:-default}», «${var+SET}»,
+#           «${var#prefix}», «${var%suffix}», and «$( cmd )»;
+#         * compound commands having a testable exit status, especially «case»;
+#         * various built-in commands including «command», «set», and «ulimit».
+#
+#   Important for patching:
+#
+#   (2) This script targets any POSIX shell, so it avoids extensions provided
+#       by Bash, Ksh, etc; in particular arrays are avoided.
+#
+#       The "traditional" practice of packing multiple parameters into a
+#       space-separated string is a well documented source of bugs and security
+#       problems, so this is (mostly) avoided, by progressively accumulating
+#       options in "$@", and eventually passing that to Java.
+#
+#       Where the inherited environment variables (DEFAULT_JVM_OPTS, JAVA_OPTS,
+#       and GRADLE_OPTS) rely on word-splitting, this is performed explicitly;
+#       see the in-line comments for details.
+#
+#       There are tweaks for specific operating systems such as AIX, CygWin,
+#       Darwin, MinGW, and NonStop.
+#
+#   (3) This script is generated from the Groovy template
+#       https://github.com/gradle/gradle/blob/master/subprojects/plugins/src/main/resources/org/gradle/api/internal/plugins/unixStartScript.txt
+#       within the Gradle project.
+#
+#       You can find Gradle at https://github.com/gradle/gradle/.
+#
 ##############################################################################
 
 # Attempt to set APP_HOME
+
 # Resolve links: $0 may be a link
-PRG="$0"
-# Need this for relative symlinks.
-while [ -h "$PRG" ] ; do
-    ls=`ls -ld "$PRG"`
-    link=`expr "$ls" : '.*-> \(.*\)$'`
-    if expr "$link" : '/.*' > /dev/null; then
-        PRG="$link"
-    else
-        PRG=`dirname "$PRG"`"/$link"
-    fi
+app_path=$0
+
+# Need this for daisy-chained symlinks.
+while
+    APP_HOME=${app_path%"${app_path##*/}"}  # leaves a trailing /; empty if no leading path
+    [ -h "$app_path" ]
+do
+    ls=$( ls -ld "$app_path" )
+    link=${ls#*' -> '}
+    case $link in             #(
+      /*)   app_path=$link ;; #(
+      *)    app_path=$APP_HOME$link ;;
+    esac
 done
-SAVED="`pwd`"
-cd "`dirname \"$PRG\"`/" >/dev/null
-APP_HOME="`pwd -P`"
-cd "$SAVED" >/dev/null
+
+APP_HOME=$( cd "${APP_HOME:-./}" && pwd -P ) || exit
 
 APP_NAME="Gradle"
-APP_BASE_NAME=`basename "$0"`
+APP_BASE_NAME=${0##*/}
 
 # Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
 DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"'
 
 # Use the maximum available, or set MAX_FD != -1 to use that value.
-MAX_FD="maximum"
+MAX_FD=maximum
 
 warn () {
     echo "$*"
-}
+} >&2
 
 die () {
     echo
     echo "$*"
     echo
     exit 1
-}
+} >&2
 
 # OS specific support (must be 'true' or 'false').
 cygwin=false
 msys=false
 darwin=false
 nonstop=false
-case "`uname`" in
-  CYGWIN* )
-    cygwin=true
-    ;;
-  Darwin* )
-    darwin=true
-    ;;
-  MINGW* )
-    msys=true
-    ;;
-  NONSTOP* )
-    nonstop=true
-    ;;
+case "$( uname )" in                #(
+  CYGWIN* )         cygwin=true  ;; #(
+  Darwin* )         darwin=true  ;; #(
+  MSYS* | MINGW* )  msys=true    ;; #(
+  NONSTOP* )        nonstop=true ;;
 esac
 
 CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar
 
+
 # Determine the Java command to use to start the JVM.
 if [ -n "$JAVA_HOME" ] ; then
     if [ -x "$JAVA_HOME/jre/sh/java" ] ; then
         # IBM's JDK on AIX uses strange locations for the executables
-        JAVACMD="$JAVA_HOME/jre/sh/java"
+        JAVACMD=$JAVA_HOME/jre/sh/java
     else
-        JAVACMD="$JAVA_HOME/bin/java"
+        JAVACMD=$JAVA_HOME/bin/java
     fi
     if [ ! -x "$JAVACMD" ] ; then
         die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME
@@ -97,7 +132,7 @@ Please set the JAVA_HOME variable in your environment to match the
 location of your Java installation."
     fi
 else
-    JAVACMD="java"
+    JAVACMD=java
     which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
 
 Please set the JAVA_HOME variable in your environment to match the
@@ -105,84 +140,101 @@ location of your Java installation."
 fi
 
 # Increase the maximum file descriptors if we can.
-if [ "$cygwin" = "false" -a "$darwin" = "false" -a "$nonstop" = "false" ] ; then
-    MAX_FD_LIMIT=`ulimit -H -n`
-    if [ $? -eq 0 ] ; then
-        if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then
-            MAX_FD="$MAX_FD_LIMIT"
-        fi
-        ulimit -n $MAX_FD
-        if [ $? -ne 0 ] ; then
-            warn "Could not set maximum file descriptor limit: $MAX_FD"
-        fi
-    else
-        warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT"
-    fi
+if ! "$cygwin" && ! "$darwin" && ! "$nonstop" ; then
+    case $MAX_FD in #(
+      max*)
+        MAX_FD=$( ulimit -H -n ) ||
+            warn "Could not query maximum file descriptor limit"
+    esac
+    case $MAX_FD in  #(
+      '' | soft) :;; #(
+      *)
+        ulimit -n "$MAX_FD" ||
+            warn "Could not set maximum file descriptor limit to $MAX_FD"
+    esac
 fi
 
-# For Darwin, add options to specify how the application appears in the dock
-if $darwin; then
-    GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\""
-fi
+# Collect all arguments for the java command, stacking in reverse order:
+#   * args from the command line
+#   * the main class name
+#   * -classpath
+#   * -D...appname settings
+#   * --module-path (only if needed)
+#   * DEFAULT_JVM_OPTS, JAVA_OPTS, and GRADLE_OPTS environment variables.
 
 # For Cygwin or MSYS, switch paths to Windows format before running java
-if [ "$cygwin" = "true" -o "$msys" = "true" ] ; then
-    APP_HOME=`cygpath --path --mixed "$APP_HOME"`
-    CLASSPATH=`cygpath --path --mixed "$CLASSPATH"`
-    JAVACMD=`cygpath --unix "$JAVACMD"`
-
-    # We build the pattern for arguments to be converted via cygpath
-    ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null`
-    SEP=""
-    for dir in $ROOTDIRSRAW ; do
-        ROOTDIRS="$ROOTDIRS$SEP$dir"
-        SEP="|"
-    done
-    OURCYGPATTERN="(^($ROOTDIRS))"
-    # Add a user-defined pattern to the cygpath arguments
-    if [ "$GRADLE_CYGPATTERN" != "" ] ; then
-        OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)"
-    fi
+if "$cygwin" || "$msys" ; then
+    APP_HOME=$( cygpath --path --mixed "$APP_HOME" )
+    CLASSPATH=$( cygpath --path --mixed "$CLASSPATH" )
+
+    JAVACMD=$( cygpath --unix "$JAVACMD" )
+
     # Now convert the arguments - kludge to limit ourselves to /bin/sh
-    i=0
-    for arg in "$@" ; do
-        CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -`
-        CHECK2=`echo "$arg"|egrep -c "^-"`                                 ### Determine if an option
-
-        if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then                    ### Added a condition
-            eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"`
-        else
-            eval `echo args$i`="\"$arg\""
+    for arg do
+        if
+            case $arg in                                #(
+              -*)   false ;;                            # don't mess with options #(
+              /?*)  t=${arg#/} t=/${t%%/*}              # looks like a POSIX filepath
+                    [ -e "$t" ] ;;                      #(
+              *)    false ;;
+            esac
+        then
+            arg=$( cygpath --path --ignore --mixed "$arg" )
         fi
-        i=$((i+1))
+        # Roll the args list around exactly as many times as the number of
+        # args, so each arg winds up back in the position where it started, but
+        # possibly modified.
+        #
+        # NB: a `for` loop captures its iteration list before it begins, so
+        # changing the positional parameters here affects neither the number of
+        # iterations, nor the values presented in `arg`.
+        shift                   # remove old arg
+        set -- "$@" "$arg"      # push replacement arg
     done
-    case $i in
-        (0) set -- ;;
-        (1) set -- "$args0" ;;
-        (2) set -- "$args0" "$args1" ;;
-        (3) set -- "$args0" "$args1" "$args2" ;;
-        (4) set -- "$args0" "$args1" "$args2" "$args3" ;;
-        (5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;;
-        (6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;;
-        (7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;;
-        (8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;;
-        (9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;;
-    esac
 fi
 
-# Escape application args
-save () {
-    for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done
-    echo " "
-}
-APP_ARGS=$(save "$@")
+# Collect all arguments for the java command;
+#   * $DEFAULT_JVM_OPTS, $JAVA_OPTS, and $GRADLE_OPTS can contain fragments of
+#     shell script including quotes and variable substitutions, so put them in
+#     double quotes to make sure that they get re-expanded; and
+#   * put everything else in single quotes, so that it's not re-expanded.
+
+set -- \
+        "-Dorg.gradle.appname=$APP_BASE_NAME" \
+        -classpath "$CLASSPATH" \
+        org.gradle.wrapper.GradleWrapperMain \
+        "$@"
+
+# Stop when "xargs" is not available.
+if ! command -v xargs >/dev/null 2>&1
+then
+    die "xargs is not available"
+fi
 
-# Collect all arguments for the java command, following the shell quoting and substitution rules
-eval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS "\"-Dorg.gradle.appname=$APP_BASE_NAME\"" -classpath "\"$CLASSPATH\"" org.gradle.wrapper.GradleWrapperMain "$APP_ARGS"
+# Use "xargs" to parse quoted args.
+#
+# With -n1 it outputs one arg per line, with the quotes and backslashes removed.
+#
+# In Bash we could simply go:
+#
+#   readarray ARGS < <( xargs -n1 <<<"$var" ) &&
+#   set -- "${ARGS[@]}" "$@"
+#
+# but POSIX shell has neither arrays nor command substitution, so instead we
+# post-process each arg (as a line of input to sed) to backslash-escape any
+# character that might be a shell metacharacter, then use eval to reverse
+# that process (while maintaining the separation between arguments), and wrap
+# the whole thing up as a single "set" statement.
+#
+# This will of course break if any of these variables contains a newline or
+# an unmatched quote.
+#
 
-# by default we should be in the correct project dir, but when run from Finder on Mac, the cwd is wrong
-if [ "$(uname)" = "Darwin" ] && [ "$HOME" = "$PWD" ]; then
-  cd "$(dirname "$0")"
-fi
+eval "set -- $(
+        printf '%s\n' "$DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS" |
+        xargs -n1 |
+        sed ' s~[^-[:alnum:]+,./:=@_]~\\&~g; ' |
+        tr '\n' ' '
+    )" '"$@"'
 
 exec "$JAVACMD" "$@"
diff --git a/gradlew.bat b/gradlew.bat
index 24467a14..53a6b238 100644
--- a/gradlew.bat
+++ b/gradlew.bat
@@ -14,7 +14,7 @@
 @rem limitations under the License.
 @rem
 
-@if "%DEBUG%" == "" @echo off
+@if "%DEBUG%"=="" @echo off
 @rem ##########################################################################
 @rem
 @rem  Gradle startup script for Windows
@@ -25,10 +25,13 @@
 if "%OS%"=="Windows_NT" setlocal
 
 set DIRNAME=%~dp0
-if "%DIRNAME%" == "" set DIRNAME=.
+if "%DIRNAME%"=="" set DIRNAME=.
 set APP_BASE_NAME=%~n0
 set APP_HOME=%DIRNAME%
 
+@rem Resolve any "." and ".." in APP_HOME to make it shorter.
+for %%i in ("%APP_HOME%") do set APP_HOME=%%~fi
+
 @rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
 set DEFAULT_JVM_OPTS="-Xmx64m" "-Xms64m"
 
@@ -37,7 +40,7 @@ if defined JAVA_HOME goto findJavaFromJavaHome
 
 set JAVA_EXE=java.exe
 %JAVA_EXE% -version >NUL 2>&1
-if "%ERRORLEVEL%" == "0" goto init
+if %ERRORLEVEL% equ 0 goto execute
 
 echo.
 echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
@@ -51,7 +54,7 @@ goto fail
 set JAVA_HOME=%JAVA_HOME:"=%
 set JAVA_EXE=%JAVA_HOME%/bin/java.exe
 
-if exist "%JAVA_EXE%" goto init
+if exist "%JAVA_EXE%" goto execute
 
 echo.
 echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%
@@ -61,38 +64,26 @@ echo location of your Java installation.
 
 goto fail
 
-:init
-@rem Get command-line arguments, handling Windows variants
-
-if not "%OS%" == "Windows_NT" goto win9xME_args
-
-:win9xME_args
-@rem Slurp the command line arguments.
-set CMD_LINE_ARGS=
-set _SKIP=2
-
-:win9xME_args_slurp
-if "x%~1" == "x" goto execute
-
-set CMD_LINE_ARGS=%*
-
 :execute
 @rem Setup the command line
 
 set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
 
+
 @rem Execute Gradle
-"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS%
+"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %*
 
 :end
 @rem End local scope for the variables with windows NT shell
-if "%ERRORLEVEL%"=="0" goto mainEnd
+if %ERRORLEVEL% equ 0 goto mainEnd
 
 :fail
 rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
 rem the _cmd.exe /c_ return code!
-if  not "" == "%GRADLE_EXIT_CONSOLE%" exit 1
-exit /b 1
+set EXIT_CODE=%ERRORLEVEL%
+if %EXIT_CODE% equ 0 set EXIT_CODE=1
+if not ""=="%GRADLE_EXIT_CONSOLE%" exit %EXIT_CODE%
+exit /b %EXIT_CODE%
 
 :mainEnd
 if "%OS%"=="Windows_NT" endlocal
diff --git a/libwallet/go.mod b/libwallet/go.mod
index 5b88265f..0bd19427 100644
--- a/libwallet/go.mod
+++ b/libwallet/go.mod
@@ -3,11 +3,9 @@ module github.com/muun/libwallet
 go 1.14
 
 require (
-	github.com/aead/chacha20 v0.0.0-20180709150244-8b13a72661da // indirect
 	github.com/btcsuite/btcd v0.20.1-beta.0.20200515232429-9f0179fd2c46
 	github.com/btcsuite/btcutil v1.0.2
 	github.com/fiatjaf/go-lnurl v1.3.1
-	github.com/google/uuid v1.1.1
 	github.com/jinzhu/gorm v1.9.16
 	github.com/lightningnetwork/lightning-onion v1.0.1
 	github.com/lightningnetwork/lnd v0.10.4-beta
@@ -15,14 +13,13 @@ require (
 	github.com/pdfcpu/pdfcpu v0.3.11
 	github.com/pkg/errors v0.9.1
 	github.com/shopspring/decimal v1.2.0
-	golang.org/x/crypto v0.0.0-20210921155107-089bfa567519
+	golang.org/x/crypto v0.25.0
+	golang.org/x/image v0.18.0 // indirect
 	golang.org/x/mobile v0.0.0-20220414153400-ce6a79cf6a13 // indirect
-	golang.org/x/sys v0.0.0-20220503163025-988cb79eb6c6 // indirect
-	golang.org/x/tools v0.1.10 // indirect
-	golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1 // indirect
+	golang.org/x/net v0.27.0 // indirect
 	google.golang.org/protobuf v1.25.0
 	gopkg.in/gormigrate.v1 v1.6.0
 )
 
 // Fork that includes the -cache flag for quicker builds
-replace golang.org/x/mobile => github.com/muun/mobile v0.0.0-20220913162405-8cc629edd37b
+replace golang.org/x/mobile => github.com/muun/mobile v0.0.0-20240709203120-049ae58602a0
diff --git a/libwallet/go.sum b/libwallet/go.sum
index 92e1994a..f7420546 100644
--- a/libwallet/go.sum
+++ b/libwallet/go.sum
@@ -1,36 +1,22 @@
 cloud.google.com/go v0.26.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw=
-cloud.google.com/go v0.33.1 h1:fmJQWZ1w9PGkHR1YL/P7HloDvqlmKQ4Vpb7PC2e+aCk=
 cloud.google.com/go v0.33.1/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw=
-git.schwanenlied.me/yawning/bsaes.git v0.0.0-20180720073208-c0276d75487e h1:F2x1bq7RaNCIuqYpswggh1+c1JmwdnkHNC9wy1KDip0=
+dmitri.shuralyov.com/gpu/mtl v0.0.0-20221208032759-85de2813cf6b/go.mod h1:H6x//7gZCb22OMCxBHrMx7a5I7Hp++hsVxbQ4BYO7hU=
 git.schwanenlied.me/yawning/bsaes.git v0.0.0-20180720073208-c0276d75487e/go.mod h1:BWqTsj8PgcPriQJGl7el20J/7TuT1d/hSyFDXMEpoEo=
-github.com/BurntSushi/toml v0.3.1 h1:WXkYYl6Yr3qBf1K79EBnL4mak0OimBfB0XUf9Vl28OQ=
 github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU=
-github.com/BurntSushi/xgb v0.0.0-20160522181843-27f122750802 h1:1BDTz0u9nC3//pOCMdNH+CiXJVYJh5UQNCOBG7jbELc=
-github.com/BurntSushi/xgb v0.0.0-20160522181843-27f122750802/go.mod h1:IVnqGOEym/WlBOVXweHU+Q+/VP0lqqI8lqeDx9IjBqo=
-github.com/NebulousLabs/fastrand v0.0.0-20181203155948-6fb6489aac4e h1:n+DcnTNkQnHlwpsrHoQtkrJIO7CBx029fw6oR4vIob4=
 github.com/NebulousLabs/fastrand v0.0.0-20181203155948-6fb6489aac4e/go.mod h1:Bdzq+51GR4/0DIhaICZEOm+OHvXGwwB2trKZ8B4Y6eQ=
-github.com/NebulousLabs/go-upnp v0.0.0-20180202185039-29b680b06c82 h1:MG93+PZYs9PyEsj/n5/haQu2gK0h4tUtSy9ejtMwWa0=
 github.com/NebulousLabs/go-upnp v0.0.0-20180202185039-29b680b06c82/go.mod h1:GbuBk21JqF+driLX3XtJYNZjGa45YDoa9IqCTzNSfEc=
-github.com/OneOfOne/xxhash v1.2.2 h1:KMrpdQIwFcEqXDklaen+P1axHaj9BSKzvpUUfnHldSE=
 github.com/OneOfOne/xxhash v1.2.2/go.mod h1:HSdplMjZKSmBqAxg5vPj2TmRDmfkzw+cTzAElWljhcU=
-github.com/PuerkitoBio/goquery v1.5.1 h1:PSPBGne8NIUWw+/7vFBV+kG2J/5MOjbzc7154OaKCSE=
 github.com/PuerkitoBio/goquery v1.5.1/go.mod h1:GsLWisAFVj4WgDibEWF4pvYnkVQBpKBKeU+7zCJoLcc=
-github.com/Yawning/aez v0.0.0-20180114000226-4dad034d9db2 h1:2be4ykKKov3M1yISM2E8gnGXZ/N2SsPawfnGiXxaYEU=
 github.com/Yawning/aez v0.0.0-20180114000226-4dad034d9db2/go.mod h1:9pIqrY6SXNL8vjRQE5Hd/OL5GyK/9MrGUWs87z/eFfk=
 github.com/aead/chacha20 v0.0.0-20180709150244-8b13a72661da h1:KjTM2ks9d14ZYCvmHS9iAKVt9AyzRSqNU1qabPih5BY=
 github.com/aead/chacha20 v0.0.0-20180709150244-8b13a72661da/go.mod h1:eHEWzANqSiWQsof+nXEI9bUVUyV6F53Fp89EuCh2EAA=
 github.com/aead/siphash v1.0.1 h1:FwHfE/T45KPKYuuSAKyyvE+oPWcaQ+CUmFW0bPlM+kg=
 github.com/aead/siphash v1.0.1/go.mod h1:Nywa3cDsYNNK3gaciGTWPwHt0wlpNV15vwmswBAUSII=
-github.com/alecthomas/template v0.0.0-20160405071501-a0175ee3bccc h1:cAKDfWh5VpdgMhJosfJnn5/FoN2SRZ4p7fJNX58YPaU=
 github.com/alecthomas/template v0.0.0-20160405071501-a0175ee3bccc/go.mod h1:LOuyumcjzFXgccqObfd/Ljyb9UuFJ6TxHnclSeseNhc=
-github.com/alecthomas/units v0.0.0-20151022065526-2efee857e7cf h1:qet1QNfXsQxTZqLG4oE62mJzwPIB8+Tee4RNCL9ulrY=
 github.com/alecthomas/units v0.0.0-20151022065526-2efee857e7cf/go.mod h1:ybxpYRFXyAe+OPACYpWeL0wqObRcbAqCMya13uyzqw0=
-github.com/andybalholm/cascadia v1.1.0 h1:BuuO6sSfQNFRu1LppgbD25Hr2vLYW25JvxHs5zzsLTo=
 github.com/andybalholm/cascadia v1.1.0/go.mod h1:GsXiBklL0woXo1j/WYWtSYYC4ouU9PqHO0sqidkEA4Y=
-github.com/asaskevich/govalidator v0.0.0-20190424111038-f61b66f89f4a h1:idn718Q4B6AGu/h5Sxe66HYVdqdGu2l9Iebqhi/AEoA=
 github.com/asaskevich/govalidator v0.0.0-20190424111038-f61b66f89f4a/go.mod h1:lB+ZfQJz7igIIfQNfa7Ml4HSf2uFQQRzpGGRXenZAgY=
 github.com/beorn7/perks v0.0.0-20180321164747-3a771d992973/go.mod h1:Dwedo/Wpr24TaqPxmxbtue+5NUziq4I4S80YR8gNf3Q=
-github.com/beorn7/perks v1.0.0 h1:HWo1m869IqiPhD389kmkxeTalrjNbbJTC8LXupb+sl0=
 github.com/beorn7/perks v1.0.0/go.mod h1:KWe93zE9D1o94FZ5RNwFwVgaQK1VOXiVxmqh+CedLV8=
 github.com/btcsuite/btcd v0.0.0-20190629003639-c26ffa870fd8/go.mod h1:3J08xEfcugPacsc34/LKRU2yO7YmuT8yt28J8k2+rrI=
 github.com/btcsuite/btcd v0.0.0-20190824003749-130ea5bddde3/go.mod h1:3J08xEfcugPacsc34/LKRU2yO7YmuT8yt28J8k2+rrI=
@@ -64,7 +50,6 @@ github.com/btcsuite/btcwallet/wtxmgr v1.2.0 h1:ZUYPsSv8GjF9KK7lboB2OVHF0uYEcHxgr
 github.com/btcsuite/btcwallet/wtxmgr v1.2.0/go.mod h1:h8hkcKUE3X7lMPzTUoGnNiw5g7VhGrKEW3KpR2r0VnY=
 github.com/btcsuite/go-socks v0.0.0-20170105172521-4720035b7bfd h1:R/opQEbFEy9JGkIguV40SvRY1uliPX8ifOvi6ICsFCw=
 github.com/btcsuite/go-socks v0.0.0-20170105172521-4720035b7bfd/go.mod h1:HHNXQzUsZCxOoE+CPiyCTO6x34Zs86zZUiwtpXoGdtg=
-github.com/btcsuite/golangcrypto v0.0.0-20150304025918-53f62d9b43e8 h1:nOsAWScwueMVk/VLm/dvQQD7DuanyvAUb6B3P3eT274=
 github.com/btcsuite/golangcrypto v0.0.0-20150304025918-53f62d9b43e8/go.mod h1:tYvUd8KLhm/oXvUeSEs2VlLghFjQt9+ZaF9ghH0JNjc=
 github.com/btcsuite/goleveldb v0.0.0-20160330041536-7834afc9e8cd/go.mod h1:F+uVaaLLH7j4eDXPRvw78tMflu7Ie2bzYOH4Y8rRKBY=
 github.com/btcsuite/goleveldb v1.0.0 h1:Tvd0BfvqX9o823q1j2UZ/epQo09eJh6dTcRp79ilIN4=
@@ -74,23 +59,10 @@ github.com/btcsuite/snappy-go v1.0.0 h1:ZxaA6lo2EpxGddsA8JwWOcxlzRybb444sgmeJQMJ
 github.com/btcsuite/snappy-go v1.0.0/go.mod h1:8woku9dyThutzjeg+3xrA5iCpBRH8XEEg3lh6TiUghc=
 github.com/btcsuite/websocket v0.0.0-20150119174127-31079b680792 h1:R8vQdOQdZ9Y3SkEwmHoWBmX1DNXhXZqlTpq6s4tyJGc=
 github.com/btcsuite/websocket v0.0.0-20150119174127-31079b680792/go.mod h1:ghJtEyQwv5/p4Mg4C0fgbePVuGr935/5ddU9Z3TmDRY=
-github.com/btcsuite/winsvc v1.0.0 h1:J9B4L7e3oqhXOcm+2IuNApwzQec85lE+QaikUcCs+dk=
 github.com/btcsuite/winsvc v1.0.0/go.mod h1:jsenWakMcC0zFBFurPLEAyrnc/teJEM1O46fmI40EZs=
-github.com/census-instrumentation/opencensus-proto v0.2.1 h1:glEXhBS5PSLLv4IXzLA5yPRVX4bilULVyxxbrfOtDAk=
 github.com/census-instrumentation/opencensus-proto v0.2.1/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU=
-github.com/cespare/xxhash v1.1.0 h1:a6HrQnmkObjyL+Gs60czilIUGqrzKutQD6XZog3p+ko=
 github.com/cespare/xxhash v1.1.0/go.mod h1:XrSqR1VqqWfGrhpAt58auRo0WTKS1nRRg3ghfAqPWnc=
-github.com/champo/mobile v0.0.0-20210412201235-a784c99e2a62 h1:6CturfaAc1IXi5udu7IMLekMFx6uB81XE7w9AGOqpyc=
-github.com/champo/mobile v0.0.0-20210412201235-a784c99e2a62/go.mod h1:skQtrUTUwhdJvXM/2KKJzY8pDgNr9I/FOMqDVRPBUS4=
-github.com/champo/mobile v0.0.0-20220503145505-51a7737dc434 h1:7KHSIWZ0Lc70SI4dTuF/8ZDBZWUKJfewCi3FpYHaqwk=
-github.com/champo/mobile v0.0.0-20220503145505-51a7737dc434/go.mod h1:pe2sM7Uk+2Su1y7u/6Z8KJ24D7lepUjFZbhFOrmDfuQ=
-github.com/champo/mobile v0.0.0-20220505154254-6a5f99bae305 h1:YgqwiwLKFqs1/d9BNXUduBA7YZ+uzfrjsKPzXBYAHsw=
-github.com/champo/mobile v0.0.0-20220505154254-6a5f99bae305/go.mod h1:pe2sM7Uk+2Su1y7u/6Z8KJ24D7lepUjFZbhFOrmDfuQ=
-github.com/champo/mobile v0.0.0-20220913162405-8cc629edd37b h1:lBk5LxUbwRPdx8jikAiwae6Z7Z9qupNlgJC2QZXJpVg=
-github.com/champo/mobile v0.0.0-20220913162405-8cc629edd37b/go.mod h1:pe2sM7Uk+2Su1y7u/6Z8KJ24D7lepUjFZbhFOrmDfuQ=
-github.com/client9/misspell v0.3.4 h1:ta993UF76GwbvJcIo3Y68y/M3WxlpEHPWIGDkJYwzJI=
 github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDkc90ppPyw=
-github.com/coreos/bbolt v1.3.3 h1:n6AiVyVRKQFNb6mJlwESEvvLoDyiTzXX7ORAUlkeBdY=
 github.com/coreos/bbolt v1.3.3/go.mod h1:iRUV2dpdMOn7Bo10OQBFzIJO9kkE559Wcmn+qkEiiKk=
 github.com/davecgh/go-spew v0.0.0-20171005155431-ecdeabc65495/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
 github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
@@ -99,49 +71,35 @@ github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSs
 github.com/denisenkom/go-mssqldb v0.0.0-20181014144952-4e0d7dc8888f/go.mod h1:xN/JuLBIz4bjkxNmByTiV1IbhfnYb6oo99phBn4Eqhc=
 github.com/denisenkom/go-mssqldb v0.0.0-20191124224453-732737034ffd h1:83Wprp6ROGeiHFAP8WJdI2RoxALQYgdllERc3N5N2DM=
 github.com/denisenkom/go-mssqldb v0.0.0-20191124224453-732737034ffd/go.mod h1:xbL0rPBG9cCiLr28tMa8zpbdarY27NDyej4t/EjAShU=
-github.com/dgryski/go-sip13 v0.0.0-20181026042036-e10d5fee7954 h1:RMLoZVzv4GliuWafOuPuQDKSm1SJph7uCRnnS61JAn4=
 github.com/dgryski/go-sip13 v0.0.0-20181026042036-e10d5fee7954/go.mod h1:vAd38F8PWV+bWy6jNmig1y/TA+kYO4g3RSRF0IAv0no=
-github.com/envoyproxy/go-control-plane v0.9.1-0.20191026205805-5f8ba28d4473 h1:4cmBvAEBNJaGARUEs3/suWRyfyBfhf7I60WBZq+bv2w=
 github.com/envoyproxy/go-control-plane v0.9.1-0.20191026205805-5f8ba28d4473/go.mod h1:YTl/9mNaCwkRvm6d1a2C3ymFceY/DCBVvsKhRF0iEA4=
-github.com/envoyproxy/protoc-gen-validate v0.1.0 h1:EQciDnbrYxy13PgWoY8AqoxGiPrpgBZ1R8UNe3ddc+A=
 github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c=
 github.com/erikstmartin/go-testdb v0.0.0-20160219214506-8d10e4a1bae5 h1:Yzb9+7DPaBjB8zlTR87/ElzFsnQfuHnVUVqpZZIcV5Y=
 github.com/erikstmartin/go-testdb v0.0.0-20160219214506-8d10e4a1bae5/go.mod h1:a2zkGnVExMxdzMo3M0Hi/3sEU+cWnZpSni0O6/Yb/P0=
 github.com/fiatjaf/go-lnurl v1.3.1 h1:9Qn4n1ZyzTMW/YuVX2Wr9cE+LEAzpE1hrCbxVK/yBKE=
 github.com/fiatjaf/go-lnurl v1.3.1/go.mod h1:BqA8WXAOzntF7Z3EkVO7DfP4y5rhWUmJ/Bu9KBke+rs=
-github.com/frankban/quicktest v1.2.2 h1:xfmOhhoH5fGPgbEAlhLpJH9p0z/0Qizio9osmvn9IUY=
 github.com/frankban/quicktest v1.2.2/go.mod h1:Qh/WofXFeiAFII1aEBu529AtJo6Zg2VHscnEsbBnJ20=
 github.com/fsnotify/fsnotify v1.4.7 h1:IXs+QLmnXW2CcXuY+8Mzv/fWEsPGWxqefPtCP5CnV9I=
 github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo=
-github.com/ghodss/yaml v1.0.0 h1:wQHKEahhL6wmXdzwWG11gIVCkOv05bNOh+Rxn0yngAk=
 github.com/ghodss/yaml v1.0.0/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04=
 github.com/go-errors/errors v1.0.1 h1:LUHzmkK3GUKUrL/1gfBUxAHzcev3apQlezX/+O7ma6w=
 github.com/go-errors/errors v1.0.1/go.mod h1:f4zRHt4oKfwPJE5k8C9vpYG+aDHdBFUsgrm6/TyX73Q=
-github.com/go-kit/kit v0.8.0 h1:Wz+5lgoB0kkuqLEc6NVmwRknTKP6dTGbSqvhZtBI/j0=
+github.com/go-gl/glfw/v3.3/glfw v0.0.0-20200222043503-6f7a984d4dc4/go.mod h1:tQ2UAYgL5IevRw8kRxooKSPJfGvJ9fJQFa0TUsXzTg8=
 github.com/go-kit/kit v0.8.0/go.mod h1:xBxKIO96dXMWWy0MnWVtmwkA9/13aqxPnvrjFYMA2as=
 github.com/go-logfmt/logfmt v0.3.0/go.mod h1:Qt1PoO58o5twSAckw1HlFXLmHsOX5/0LbT9GBnD5lWE=
-github.com/go-logfmt/logfmt v0.4.0 h1:MP4Eh7ZCb31lleYCFuwm0oe4/YGak+5l1vA2NOE80nA=
 github.com/go-logfmt/logfmt v0.4.0/go.mod h1:3RMwSq7FuexP4Kalkev3ejPJsZTpXXBr9+V4qmtdjCk=
-github.com/go-openapi/errors v0.19.2 h1:a2kIyV3w+OS3S97zxUndRVD46+FhGOUBDFY7nmu4CsY=
 github.com/go-openapi/errors v0.19.2/go.mod h1:qX0BLWsyaKfvhluLejVpVNwNRdXZhEbTA4kxxpKBC94=
-github.com/go-openapi/strfmt v0.19.5 h1:0utjKrw+BAh8s57XE9Xz8DUBsVvPmRUB6styvl9wWIM=
 github.com/go-openapi/strfmt v0.19.5/go.mod h1:eftuHTlB/dI8Uq8JJOyRlieZf+WkkxUuk0dgdHXr2Qk=
 github.com/go-sql-driver/mysql v1.4.1/go.mod h1:zAC/RDZ24gD3HViQzih4MyKcchzm+sOG5ZlKdlhCg5w=
 github.com/go-sql-driver/mysql v1.5.0 h1:ozyZYNQW3x3HtqT1jira07DN2PArx2v7/mN66gGcHOs=
 github.com/go-sql-driver/mysql v1.5.0/go.mod h1:DCzpHaOWr8IXmIStZouvnhqoel9Qv2LBy8hT2VhHyBg=
-github.com/go-stack/stack v1.8.0 h1:5SgMzNM5HxrEjV0ww2lTmX6E2Izsfxas4+YHWRs3Lsk=
 github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY=
-github.com/gofrs/uuid v3.2.0+incompatible h1:y12jRkkFxsd7GpqdSZ+/KCs/fJbqpEXSGd4+jfEaewE=
 github.com/gofrs/uuid v3.2.0+incompatible/go.mod h1:b2aQJv3Z4Fp6yNu3cdSllBxTCLRxnplIgP/c0N/04lM=
-github.com/gogo/protobuf v1.1.1 h1:72R+M5VuhED/KujmZVcIquuo8mBgX4oVda//DQb3PXo=
 github.com/gogo/protobuf v1.1.1/go.mod h1:r8qH/GZQm5c6nD/R0oafs1akxWv10x8SbQlK7atdtwQ=
 github.com/golang-sql/civil v0.0.0-20190719163853-cb61b32ac6fe h1:lXe2qZdvpiX5WZkZR4hgp4KJVfY3nMkvmwbVkpv1rVY=
 github.com/golang-sql/civil v0.0.0-20190719163853-cb61b32ac6fe/go.mod h1:8vg3r2VgvsThLBIFL93Qb5yWzgyZWhEmBwUJWevAkK0=
-github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b h1:VKtxabqXZkF25pY9ekfRL6a582T4P37/31XEstQ5p58=
 github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b/go.mod h1:SBH7ygxi8pfUlaOkMMuAQtPIUF8ecWP5IEl/CR7VP2Q=
-github.com/golang/lint v0.0.0-20180702182130-06c8688daad7 h1:2hRPrmiwPrp3fQX967rNJIhQPtiGXdlQWAxKbKw3VHA=
 github.com/golang/lint v0.0.0-20180702182130-06c8688daad7/go.mod h1:tluoj9z5200jBnyusfRPU2LqT6J+DAorxEvtC7LHB+E=
-github.com/golang/mock v1.1.1 h1:G5FRp8JnTd7RQH5kemVNlMeyXQAztQ3mOWV95KxsXH8=
 github.com/golang/mock v1.1.1/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A=
 github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U=
 github.com/golang/protobuf v1.3.1/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U=
@@ -151,23 +109,19 @@ github.com/golang/protobuf v1.4.0-rc.1.0.20200221234624-67d41d38c208/go.mod h1:x
 github.com/golang/protobuf v1.4.0-rc.2/go.mod h1:LlEzMj4AhA7rCAGe4KMBDvJI+AwstrUpVNzEA03Pprs=
 github.com/golang/protobuf v1.4.0-rc.4.0.20200313231945-b860323f09d0/go.mod h1:WU3c8KckQ9AFe+yFwt9sWVRKCVIyN9cPHBJSNnbL67w=
 github.com/golang/protobuf v1.4.0/go.mod h1:jodUvKwWbYaEsadDk5Fwe5c77LiNKVO9IDvqG2KuDX0=
+github.com/golang/protobuf v1.4.1 h1:ZFgWrT+bLgsYPirOnRfKLYJLvssAegOj/hgyMFdJZe0=
 github.com/golang/protobuf v1.4.1/go.mod h1:U8fpvMrcmy5pZrNK1lt4xCsGvpyWQ/VVv6QDs8UjoX8=
-github.com/golang/protobuf v1.4.2 h1:+Z5KGCizgyZCbGh1KZqA0fcLLkwbsjIzS4aV2v7wJX0=
-github.com/golang/protobuf v1.4.2/go.mod h1:oDoupMAO8OvCJWAcko0GGGIgR6R6ocIYbsSw735rRwI=
 github.com/google/go-cmp v0.2.0/go.mod h1:oXzfMopK8JAjlY9xF4vHSVASa0yLyX7SntLO5aqRK0M=
 github.com/google/go-cmp v0.2.1-0.20190312032427-6f77996f0c42/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU=
 github.com/google/go-cmp v0.3.0/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU=
 github.com/google/go-cmp v0.3.1/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU=
 github.com/google/go-cmp v0.4.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
-github.com/google/go-cmp v0.5.0 h1:/QaMHBdZ26BB3SSst0Iwl10Epc+xhTquomWX0oZEB6w=
 github.com/google/go-cmp v0.5.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
-github.com/google/uuid v1.1.1 h1:Gkbcsh/GbpXz7lPftLA3P6TYMwjCLYm83jiFQZF/3gY=
+github.com/google/go-cmp v0.6.0 h1:ofyhxvXcZhMsU5ulbFiLKl/XBFqE1GSq7atu8tAmTRI=
+github.com/google/go-cmp v0.6.0/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY=
 github.com/google/uuid v1.1.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo=
-github.com/grpc-ecosystem/go-grpc-middleware v1.0.0 h1:Iju5GlWwrvL6UBg4zJJt3btmonfrMlCDdsejg4CZE7c=
 github.com/grpc-ecosystem/go-grpc-middleware v1.0.0/go.mod h1:FiyG127CGDf3tlThmgyCl78X/SZQqEOJBCDaAfeWzPs=
-github.com/grpc-ecosystem/go-grpc-prometheus v1.2.0 h1:Ovs26xHkKqVztRpIrF/92BcuyuQ/YW4NSIpoGtfXNho=
 github.com/grpc-ecosystem/go-grpc-prometheus v1.2.0/go.mod h1:8NvIoxWQoOIhqOTXgfV/d3M/q6VIi02HzZEHgUlZvzk=
-github.com/grpc-ecosystem/grpc-gateway v1.8.6 h1:XvND7+MPP7Jp+JpqSZ7naSl5nVZf6k0LbL1V3EKh0zc=
 github.com/grpc-ecosystem/grpc-gateway v1.8.6/go.mod h1:vNeuVxBJEsws4ogUvrchl83t/GYV9WGTSLVdBhOQFDY=
 github.com/hhrutter/lzw v0.0.0-20190827003112-58b82c5a41cc/go.mod h1:yJBvOcu1wLQ9q9XZmfiPfur+3dQJuIhYQsMGLYcItZk=
 github.com/hhrutter/lzw v0.0.0-20190829144645-6f07a24e8650 h1:1yY/RQWNSBjJe2GDCIYoLmpWVidrooriUr4QS/zaATQ=
@@ -176,15 +130,12 @@ github.com/hhrutter/tiff v0.0.0-20190829141212-736cae8d0bc7 h1:o1wMw7uTNyA58IlEd
 github.com/hhrutter/tiff v0.0.0-20190829141212-736cae8d0bc7/go.mod h1:WkUxfS2JUu3qPo6tRld7ISb8HiC0gVSU91kooBMDVok=
 github.com/hpcloud/tail v1.0.0 h1:nfCOvKYfkgYP8hkirhJocXT2+zOD8yUNjXaWfTlyFKI=
 github.com/hpcloud/tail v1.0.0/go.mod h1:ab1qPbhIpdTxEkNHXyeSf5vhxWSCs/tWer42PpOxQnU=
-github.com/jackpal/gateway v1.0.5 h1:qzXWUJfuMdlLMtt0a3Dgt+xkWQiA5itDEITVJtuSwMc=
 github.com/jackpal/gateway v1.0.5/go.mod h1:lTpwd4ACLXmpyiCTRtfiNyVnUmqT9RivzCDQetPfnjA=
-github.com/jackpal/go-nat-pmp v0.0.0-20170405195558-28a68d0c24ad h1:heFfj7z0pGsNCekUlsFhO2jstxO4b5iQ665LjwM5mDc=
 github.com/jackpal/go-nat-pmp v0.0.0-20170405195558-28a68d0c24ad/go.mod h1:QPH045xvCAeXUZOxsnwmrtiCoxIr9eob+4orBN1SBKc=
-github.com/jedib0t/go-pretty v4.3.0+incompatible h1:CGs8AVhEKg/n9YbUenWmNStRW2PHJzaeDodcfvRAbIo=
 github.com/jedib0t/go-pretty v4.3.0+incompatible/go.mod h1:XemHduiw8R651AF9Pt4FwCTKeG3oo7hrHJAoznj9nag=
 github.com/jessevdk/go-flags v0.0.0-20141203071132-1679536dcc89/go.mod h1:4FA24M0QyGHXBuZZK/XkWh8h0e1EYbRYJSGM75WSRxI=
-github.com/jessevdk/go-flags v1.4.0 h1:4IU2WS7AumrZ/40jfhf4QVDMsQwqA7VEHozFRrGARJA=
 github.com/jessevdk/go-flags v1.4.0/go.mod h1:4FA24M0QyGHXBuZZK/XkWh8h0e1EYbRYJSGM75WSRxI=
+github.com/jezek/xgb v1.0.0/go.mod h1:nrhwO0FX/enq75I7Y7G8iN1ubpSGZEiA3v9e9GyRFlk=
 github.com/jinzhu/gorm v1.9.2/go.mod h1:Vla75njaFJ8clLU1W44h34PjIkijhjHIYnZxMqCdxqo=
 github.com/jinzhu/gorm v1.9.16 h1:+IyIjPEABKRpsu/F8OvDPy9fyQlgsg2luMV2ZIH5i5o=
 github.com/jinzhu/gorm v1.9.16/go.mod h1:G3LB3wezTOWM2ITLzPxEXgSkOXAntiLHS7UdBefADcs=
@@ -198,34 +149,22 @@ github.com/joho/godotenv v1.3.0 h1:Zjp+RcGpHhGlrMbJzXTrZZPrWj+1vfm90La1wgB6Bhc=
 github.com/joho/godotenv v1.3.0/go.mod h1:7hK45KPybAkOC6peb+G5yklZfMxEjkZhHbwpqxOKXbg=
 github.com/jrick/logrotate v1.0.0 h1:lQ1bL/n9mBNeIXoTUoYRlK4dHuNJVofX9oWqBtPnSzI=
 github.com/jrick/logrotate v1.0.0/go.mod h1:LNinyqDIJnpAur+b8yyulnQw/wDuN1+BYKlTRt3OuAQ=
-github.com/juju/clock v0.0.0-20190205081909-9c5c9712527c h1:3UvYABOQRhJAApj9MdCN+Ydv841ETSoy6xLzdmmr/9A=
 github.com/juju/clock v0.0.0-20190205081909-9c5c9712527c/go.mod h1:nD0vlnrUjcjJhqN5WuCWZyzfd5AHZAC9/ajvbSx69xA=
-github.com/juju/errors v0.0.0-20190806202954-0232dcc7464d h1:hJXjZMxj0SWlMoQkzeZDLi2cmeiWKa7y1B8Rg+qaoEc=
 github.com/juju/errors v0.0.0-20190806202954-0232dcc7464d/go.mod h1:W54LbzXuIE0boCoNJfwqpmkKJ1O4TCTZMetAt6jGk7Q=
-github.com/juju/loggo v0.0.0-20190526231331-6e530bcce5d8 h1:UUHMLvzt/31azWTN/ifGWef4WUqvXk0iRqdhdy/2uzI=
 github.com/juju/loggo v0.0.0-20190526231331-6e530bcce5d8/go.mod h1:vgyd7OREkbtVEN/8IXZe5Ooef3LQePvuBm9UWj6ZL8U=
-github.com/juju/retry v0.0.0-20180821225755-9058e192b216 h1:/eQL7EJQKFHByJe3DeE8Z36yqManj9UY5zppDoQi4FU=
 github.com/juju/retry v0.0.0-20180821225755-9058e192b216/go.mod h1:OohPQGsr4pnxwD5YljhQ+TZnuVRYpa5irjugL1Yuif4=
-github.com/juju/testing v0.0.0-20190723135506-ce30eb24acd2 h1:Pp8RxiF4rSoXP9SED26WCfNB28/dwTDpPXS8XMJR8rc=
 github.com/juju/testing v0.0.0-20190723135506-ce30eb24acd2/go.mod h1:63prj8cnj0tU0S9OHjGJn+b1h0ZghCndfnbQolrYTwA=
-github.com/juju/utils v0.0.0-20180820210520-bf9cc5bdd62d h1:irPlN9z5VCe6BTsqVsxheCZH99OFSmqSVyTigW4mEoY=
 github.com/juju/utils v0.0.0-20180820210520-bf9cc5bdd62d/go.mod h1:6/KLg8Wz/y2KVGWEpkK9vMNGkOnu4k/cqs8Z1fKjTOk=
-github.com/juju/version v0.0.0-20180108022336-b64dbd566305 h1:lQxPJ1URr2fjsKnJRt/BxiIxjLt9IKGvS+0injMHbag=
 github.com/juju/version v0.0.0-20180108022336-b64dbd566305/go.mod h1:kE8gK5X0CImdr7qpSKl3xB2PmpySSmfj7zVbkZFs81U=
-github.com/julienschmidt/httprouter v1.2.0 h1:TDTW5Yz1mjftljbcKqRcrYhd4XeOoI98t+9HbQbYf7g=
 github.com/julienschmidt/httprouter v1.2.0/go.mod h1:SYymIcj16QtmaHHD7aYtjjsJG7VTCxuUUipMqKk8s4w=
-github.com/kisielk/gotool v1.0.0 h1:AV2c/EiW3KqPNT9ZKl07ehoAGi4C5/01Cfbblndcapg=
 github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck=
 github.com/kkdai/bstream v0.0.0-20161212061736-f391b8402d23/go.mod h1:J+Gs4SYgM6CZQHDETBtE9HaSEkGmuNXF86RwHhHUvq4=
 github.com/kkdai/bstream v0.0.0-20181106074824-b3251f7901ec h1:n1NeQ3SgUHyISrjFFoO5dR748Is8dBL9qpaTNfphQrs=
 github.com/kkdai/bstream v0.0.0-20181106074824-b3251f7901ec/go.mod h1:J+Gs4SYgM6CZQHDETBtE9HaSEkGmuNXF86RwHhHUvq4=
-github.com/konsorten/go-windows-terminal-sequences v1.0.1 h1:mweAR1A6xJ3oS2pRaGiHgQ4OO8tzTaLawm8vnODuwDk=
 github.com/konsorten/go-windows-terminal-sequences v1.0.1/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ=
-github.com/kr/logfmt v0.0.0-20140226030751-b84e30acd515 h1:T+h1c/A9Gawja4Y9mFVWj2vyii2bbUNDw3kt9VxK2EY=
 github.com/kr/logfmt v0.0.0-20140226030751-b84e30acd515/go.mod h1:+0opPa2QZZtGFBFZlji/RkVcI2GknAs/DXo4wKdlNEc=
 github.com/kr/pretty v0.1.0 h1:L/CwN0zerZDmRFUapSPitk6f+Q3+0za1rQkzVuMiMFI=
 github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo=
-github.com/kr/pty v1.1.1 h1:VkoXIwSboBpnk99O/KFauAEILuNHv5DVFKZMBN/gUgw=
 github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ=
 github.com/kr/text v0.1.0 h1:45sCR5RtlFHMR4UwH9sdQ5TC8v0qDQCHnXt+kaKSTVE=
 github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI=
@@ -237,13 +176,11 @@ github.com/lightninglabs/gozmq v0.0.0-20191113021534-d20a764486bf/go.mod h1:vxmQ
 github.com/lightninglabs/neutrino v0.11.0/go.mod h1:CuhF0iuzg9Sp2HO6ZgXgayviFTn1QHdSTJlMncK80wg=
 github.com/lightninglabs/neutrino v0.11.1-0.20200316235139-bffc52e8f200 h1:j4iZ1XlUAPQmW6oSzMcJGILYsRHNs+4O3Gk+2Ms5Dww=
 github.com/lightninglabs/neutrino v0.11.1-0.20200316235139-bffc52e8f200/go.mod h1:MlZmoKa7CJP3eR1s5yB7Rm5aSyadpKkxqAwLQmog7N0=
-github.com/lightninglabs/protobuf-hex-display v1.3.3-0.20191212020323-b444784ce75d h1:QWD/5MPnaZfUVP7P8wLa4M8Td2DI7XXHXt2vhVtUgGI=
 github.com/lightninglabs/protobuf-hex-display v1.3.3-0.20191212020323-b444784ce75d/go.mod h1:KDb67YMzoh4eudnzClmvs2FbiLG9vxISmLApUkCa4uI=
 github.com/lightningnetwork/lightning-onion v1.0.1 h1:qChGgS5+aPxFeR6JiUsGvanei1bn6WJpYbvosw/1604=
 github.com/lightningnetwork/lightning-onion v1.0.1/go.mod h1:rigfi6Af/KqsF7Za0hOgcyq2PNH4AN70AaMRxcJkff4=
 github.com/lightningnetwork/lnd v0.10.4-beta h1:Af2zOCPePeaU8Tkl8IqtTjr4BP3zYfi+hAtQYcCMM58=
 github.com/lightningnetwork/lnd v0.10.4-beta/go.mod h1:4d02pduRVtZwgTJ+EimKJTsEAY0jDwi0SPE9h5aRneM=
-github.com/lightningnetwork/lnd/cert v1.0.2 h1:g2rEu+sM2Uyz0bpfuvwri/ks6R/26H5iY1NcGbpDJ+c=
 github.com/lightningnetwork/lnd/cert v1.0.2/go.mod h1:fmtemlSMf5t4hsQmcprSoOykypAPp+9c+0d0iqTScMo=
 github.com/lightningnetwork/lnd/clock v1.0.1 h1:QQod8+m3KgqHdvVMV+2DRNNZS1GRFir8mHZYA+Z2hFo=
 github.com/lightningnetwork/lnd/clock v1.0.1/go.mod h1:KnQudQ6w0IAMZi1SgvecLZQZ43ra2vpDNj7H/aasemg=
@@ -254,25 +191,19 @@ github.com/lightningnetwork/lnd/ticker v1.0.0 h1:S1b60TEGoTtCe2A0yeB+ecoj/kkS4qp
 github.com/lightningnetwork/lnd/ticker v1.0.0/go.mod h1:iaLXJiVgI1sPANIF2qYYUJXjoksPNvGNYowB8aRbpX0=
 github.com/ltcsuite/ltcd v0.0.0-20190101042124-f37f8bf35796 h1:sjOGyegMIhvgfq5oaue6Td+hxZuf3tDC8lAPrFldqFw=
 github.com/ltcsuite/ltcd v0.0.0-20190101042124-f37f8bf35796/go.mod h1:3p7ZTf9V1sNPI5H8P3NkTFF4LuwMdPl2DodF60qAKqY=
-github.com/ltcsuite/ltcutil v0.0.0-20181217130922-17f3b04680b6 h1:b/Op1jKdoE6tzGyjzFx8gc7ZyW3hVFs1jUCQfM/Z2Jo=
 github.com/ltcsuite/ltcutil v0.0.0-20181217130922-17f3b04680b6/go.mod h1:8Vg/LTOO0KYa/vlHWJ6XZAevPQThGH5sufO0Hrou/lA=
-github.com/mattn/go-runewidth v0.0.9 h1:Lm995f3rfxdpd6TSmuVCHVb/QhupuXlYr8sCI/QdE+0=
 github.com/mattn/go-runewidth v0.0.9/go.mod h1:H031xJmbD/WCDINGzjvQ9THkh0rPKHF+m2gUSrubnMI=
 github.com/mattn/go-sqlite3 v1.10.0/go.mod h1:FPy6KqzDD04eiIsT53CuJW3U88zkxoIYsOqkbpncsNc=
 github.com/mattn/go-sqlite3 v1.14.0 h1:mLyGNKR8+Vv9CAU7PphKa2hkEqxxhn8i32J6FPj1/QA=
 github.com/mattn/go-sqlite3 v1.14.0/go.mod h1:JIl7NbARA7phWnGvh0LKTyg7S9BA+6gx71ShQilpsus=
-github.com/matttproud/golang_protobuf_extensions v1.0.1 h1:4hp9jkHxhMHkqkrB3Ix0jegS5sx/RkqARlsWZ6pIwiU=
 github.com/matttproud/golang_protobuf_extensions v1.0.1/go.mod h1:D8He9yQNgCq6Z5Ld7szi9bcBfOoFv/3dc6xSMkL2PC0=
 github.com/miekg/dns v0.0.0-20171125082028-79bfde677fa8/go.mod h1:W1PPwlIAgtquWBMBEV9nkV9Cazfe8ScdGz/Lj7v3Nrg=
 github.com/miekg/dns v1.1.29 h1:xHBEhR+t5RzcFJjBLJlax2daXOrTYtr9z4WdKEfWFzg=
 github.com/miekg/dns v1.1.29/go.mod h1:KNUDUusw/aVsxyTYZM1oqvCicbwhgbNgztCETuNZ7xM=
-github.com/mitchellh/mapstructure v1.1.2 h1:fmNYVwqnSfB9mZU6OS2O6GsXM+wcskZDuKQzvN1EDeE=
 github.com/mitchellh/mapstructure v1.1.2/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y=
-github.com/muun/mobile v0.0.0-20220913162405-8cc629edd37b h1:vAbL/T5aP3yNt1TAhukQvsnxLR4pAf1+EmVWecDMr+Q=
-github.com/muun/mobile v0.0.0-20220913162405-8cc629edd37b/go.mod h1:pe2sM7Uk+2Su1y7u/6Z8KJ24D7lepUjFZbhFOrmDfuQ=
-github.com/mwitkow/go-conntrack v0.0.0-20161129095857-cc309e4a2223 h1:F9x/1yl3T2AeKLr2AMdilSD8+f9bvMnNN8VS5iDtovc=
+github.com/muun/mobile v0.0.0-20240709203120-049ae58602a0 h1:1Wc7cbXYLR73MAFL8ztWyYiVAKj6JspMNEjrbFE2Y1w=
+github.com/muun/mobile v0.0.0-20240709203120-049ae58602a0/go.mod h1:TCsc78+c4cqb8IKEosz2LwJ6YRNkIjMuAYeHYjchGDE=
 github.com/mwitkow/go-conntrack v0.0.0-20161129095857-cc309e4a2223/go.mod h1:qRWi+5nqEBWmkhHvq77mSJWrCKwh8bxhgT7d/eI7P4U=
-github.com/oklog/ulid v1.3.1 h1:EGfNDEx6MqHz8B3uNV6QAib1UR2Lm97sHi3ocA6ESJ4=
 github.com/oklog/ulid v1.3.1/go.mod h1:CirwcVhetQ6Lv90oh/F+FBtV6XMibvdAFo93nm5qn4U=
 github.com/onsi/ginkgo v1.6.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE=
 github.com/onsi/ginkgo v1.7.0 h1:WSHQ+IS43OoUrWtD1/bbclrwK8TTH5hzp+umCiuxHgs=
@@ -288,32 +219,23 @@ github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINE
 github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
 github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
 github.com/prometheus/client_golang v0.9.1/go.mod h1:7SWBe2y4D6OKWSNQJUaRYU/AaXPKyh/dDVn+NZz0KFw=
-github.com/prometheus/client_golang v0.9.3 h1:9iH4JKXLzFbOAdtqv/a+j8aewx2Y8lAjAydhbaScPF8=
 github.com/prometheus/client_golang v0.9.3/go.mod h1:/TN21ttK/J9q6uSwhBd54HahCDft0ttaMvbicHlPoso=
 github.com/prometheus/client_model v0.0.0-20180712105110-5c3871d89910/go.mod h1:MbSGuTsp3dbXC40dX6PRTWyKYBIrTGTE9sqQNg2J8bo=
 github.com/prometheus/client_model v0.0.0-20190129233127-fd36f4220a90/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA=
-github.com/prometheus/client_model v0.0.0-20190812154241-14fe0d1b01d4 h1:gQz4mCbXsO+nc9n1hCxHcGA3Zx3Eo+UHZoInFGUIXNM=
 github.com/prometheus/client_model v0.0.0-20190812154241-14fe0d1b01d4/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA=
 github.com/prometheus/common v0.0.0-20181113130724-41aa239b4cce/go.mod h1:daVV7qP5qjZbuso7PdcryaAu0sAZbrN9i7WWcTMWvro=
-github.com/prometheus/common v0.4.0 h1:7etb9YClo3a6HjLzfl6rIQaU+FDfi0VSX39io3aQ+DM=
 github.com/prometheus/common v0.4.0/go.mod h1:TNfzLD0ON7rHzMJeJkieUDPYmFC7Snx/y86RQel1bk4=
 github.com/prometheus/procfs v0.0.0-20181005140218-185b4288413d/go.mod h1:c3At6R/oaqEKCNdg8wHV1ftS6bRYblBhIjjI8uT2IGk=
-github.com/prometheus/procfs v0.0.0-20190507164030-5867b95ac084 h1:sofwID9zm4tzrgykg80hfFph1mryUeLRsUfoocVVmRY=
 github.com/prometheus/procfs v0.0.0-20190507164030-5867b95ac084/go.mod h1:TjEm7ze935MbeOT/UhFTIMYKhuLP4wbCsTZCD3I8kEA=
-github.com/prometheus/tsdb v0.7.1 h1:YZcsG11NqnK4czYLrWd9mpEuAJIHVQLwdrleYfszMAA=
 github.com/prometheus/tsdb v0.7.1/go.mod h1:qhTCs0VvXwvX/y3TZrWD7rabWM+ijKTux40TwIPHuXU=
 github.com/rogpeppe/fastuuid v0.0.0-20150106093220-6724a57986af/go.mod h1:XWv6SoW27p1b0cqNHllgS5HIMJraePCO15w5zCzIWYg=
-github.com/rogpeppe/fastuuid v1.2.0 h1:Ppwyp6VYCF1nvBTXL3trRso7mXMlRrw9ooo375wvi2s=
 github.com/rogpeppe/fastuuid v1.2.0/go.mod h1:jVj6XXZzXRy/MSR5jhDC/2q6DgLz+nrA6LYCDYWNEvQ=
 github.com/shopspring/decimal v1.2.0 h1:abSATXmQEYyShuxI4/vyW3tV1MrKAJzCZ/0zLUXYbsQ=
 github.com/shopspring/decimal v1.2.0/go.mod h1:DKyhrW/HYNuLGql+MJL6WCR6knT2jwCFRcu2hWCYk4o=
-github.com/sirupsen/logrus v1.2.0 h1:juTguoYk5qI21pwyTXY3B3Y5cOTH3ZUyZCg1v/mihuo=
 github.com/sirupsen/logrus v1.2.0/go.mod h1:LxeOpSwHxABJmUn/MG1IvRgCAasNZTLOkJPxbbu5VWo=
-github.com/spaolacci/murmur3 v0.0.0-20180118202830-f09979ecbc72 h1:qLC7fQah7D6K1B0ujays3HV9gkFtllcxhzImRR7ArPQ=
 github.com/spaolacci/murmur3 v0.0.0-20180118202830-f09979ecbc72/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA=
 github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
 github.com/stretchr/objx v0.1.1/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
-github.com/stretchr/objx v0.2.0 h1:Hbg2NidpLE8veEBkEZTL3CvlkUIVzuU9jDplZO54c48=
 github.com/stretchr/objx v0.2.0/go.mod h1:qt09Ya8vawLte6SNmTgCsAVtYtaKzEcn8ATUoHMkEqE=
 github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs=
 github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI=
@@ -325,17 +247,12 @@ github.com/tidwall/match v1.0.1 h1:PnKP62LPNxHKTwvHHZZzdOAOCtsJTjo6dZLCwpKm5xc=
 github.com/tidwall/match v1.0.1/go.mod h1:LujAq0jyVjBy028G1WhWfIzbpQfMO8bBZ6Tyb0+pL9E=
 github.com/tidwall/pretty v1.0.0 h1:HsD+QiTn7sK6flMKIvNmpqz1qrpP3Ps6jOKIKMooyg4=
 github.com/tidwall/pretty v1.0.0/go.mod h1:XNkn88O1ChpSDQmQeStsy+sBenx6DDtFZJxhVysOjyk=
-github.com/tv42/zbase32 v0.0.0-20160707012821-501572607d02 h1:tcJ6OjwOMvExLlzrAVZute09ocAGa7KqOON60++Gz4E=
 github.com/tv42/zbase32 v0.0.0-20160707012821-501572607d02/go.mod h1:tHlrkM198S068ZqfrO6S8HsoJq2bF3ETfTL+kt4tInY=
-github.com/urfave/cli v1.18.0 h1:m9MfmZWX7bwr9kUcs/Asr95j0IVXzGNNc+/5ku2m26Q=
 github.com/urfave/cli v1.18.0/go.mod h1:70zkFmudgCuE/ngEzBv17Jvp/497gISqfk5gWijbERA=
-github.com/yuin/goldmark v1.3.5/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1Zlc8k=
-github.com/yuin/goldmark v1.4.0/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1Zlc8k=
-github.com/yuin/goldmark v1.4.1/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1Zlc8k=
+github.com/yuin/goldmark v1.4.13/go.mod h1:6yULJ656Px+3vBD8DxQVa3kxgyrAnzto9xy5taEt/CY=
 go.etcd.io/bbolt v1.3.3/go.mod h1:IbVyRI1SCnLcuJnV2u8VeU0CEYM7e686BmAb1XKL+uU=
 go.etcd.io/bbolt v1.3.5-0.20200615073812-232d8fc87f50 h1:ASw9n1EHMftwnP3Az4XW6e308+gNsrHzmdhd0Olz9Hs=
 go.etcd.io/bbolt v1.3.5-0.20200615073812-232d8fc87f50/go.mod h1:G5EMThwa9y8QZGBClrRx5EY+Yw9kAhnjy3bSjsnlVTQ=
-go.mongodb.org/mongo-driver v1.0.3 h1:GKoji1ld3tw2aC+GX1wbr/J2fX13yNacEYoJ8Nhr0yU=
 go.mongodb.org/mongo-driver v1.0.3/go.mod h1:u7ryQJ+DOzQmeO7zB6MHyr8jkEQvC8vH7qLUO4lqsUM=
 golang.org/x/crypto v0.0.0-20170930174604-9419663f5a44/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
 golang.org/x/crypto v0.0.0-20180904163835-0709b304e793/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
@@ -343,36 +260,35 @@ golang.org/x/crypto v0.0.0-20181112202954-3d3f9f413869/go.mod h1:6SG95UA2DQfeDnf
 golang.org/x/crypto v0.0.0-20190211182817-74369b46fc67/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
 golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
 golang.org/x/crypto v0.0.0-20190325154230-a5d413f7728c/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
-golang.org/x/crypto v0.0.0-20190510104115-cbcb75029529/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
 golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
 golang.org/x/crypto v0.0.0-20191205180655-e7c4368fe9dd/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
 golang.org/x/crypto v0.0.0-20200115085410-6d4e4cb37c7d/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
 golang.org/x/crypto v0.0.0-20200510223506-06a226fb4e37/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
-golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9 h1:psW17arqaxU48Z5kZ0CQnkZWQJsqcURM6tKiBApRjXI=
-golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
-golang.org/x/crypto v0.0.0-20210921155107-089bfa567519 h1:7I4JAnoQBe7ZtJcBaYHi5UtiO8tQHbUSXxL+pnGRANg=
 golang.org/x/crypto v0.0.0-20210921155107-089bfa567519/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc=
+golang.org/x/crypto v0.13.0/go.mod h1:y6Z2r+Rw4iayiXXAIxJIDAJ1zMW4yaTpebo8fPOliYc=
+golang.org/x/crypto v0.19.0/go.mod h1:Iy9bg/ha4yyC70EfRS8jz+B6ybOBKMaSxLj6P6oBDfU=
+golang.org/x/crypto v0.23.0/go.mod h1:CKFgDieR+mRhux2Lsu27y0fO304Db0wZe70UKqHu0v8=
+golang.org/x/crypto v0.25.0 h1:ypSNr+bnYL2YhwoMt2zPxHFmbAN1KZs/njMG3hxUp30=
+golang.org/x/crypto v0.25.0/go.mod h1:T+wALwcMOSE0kXgUAnPAHqTLW+XHgcELELW8VaDgm/M=
 golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA=
-golang.org/x/exp v0.0.0-20190731235908-ec7cb31e5a56 h1:estk1glOnSVeJ9tdEZZc5mAMDZk5lNJNyJ6DvrBkTEU=
-golang.org/x/exp v0.0.0-20190731235908-ec7cb31e5a56/go.mod h1:JhuoJpWY28nO4Vef9tZUw9qufEGTyX1+7lmHxV5q5G4=
-golang.org/x/image v0.0.0-20190227222117-0694c2d4d067/go.mod h1:kZ7UVZpmo3dzQBMxlp+ypCbDeSB+sBbTgSJuh5dn5js=
+golang.org/x/exp/shiny v0.0.0-20230817173708-d852ddb80c63/go.mod h1:UH99kUObWAZkDnWqppdQe5ZhPYESUw8I0zVV1uWBR+0=
 golang.org/x/image v0.0.0-20190802002840-cff245a6509b/go.mod h1:FeLwcggjj3mMvU+oOTbSwawSJRM1uh48EjtB4UJZlP0=
 golang.org/x/image v0.0.0-20190823064033-3a9bac650e44/go.mod h1:FeLwcggjj3mMvU+oOTbSwawSJRM1uh48EjtB4UJZlP0=
-golang.org/x/image v0.0.0-20210220032944-ac19c3e999fb h1:fqpd0EBDzlHRCjiphRR5Zo/RSWWQlWv34418dnEixWk=
 golang.org/x/image v0.0.0-20210220032944-ac19c3e999fb/go.mod h1:FeLwcggjj3mMvU+oOTbSwawSJRM1uh48EjtB4UJZlP0=
+golang.org/x/image v0.18.0 h1:jGzIakQa/ZXI1I0Fxvaa9W7yP25TqT6cHIHn+6CqvSQ=
+golang.org/x/image v0.18.0/go.mod h1:4yyo5vMFQjVjUcVk4jEQcU9MGy/rulF5WvUILseCM2E=
 golang.org/x/lint v0.0.0-20180702182130-06c8688daad7/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE=
 golang.org/x/lint v0.0.0-20181026193005-c67002cb31c3/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE=
 golang.org/x/lint v0.0.0-20190227174305-5b3e6a55c961/go.mod h1:wehouNa3lNwaWXcvxsM5YxQ5yQlVC4a0KAMCusXpPoU=
-golang.org/x/lint v0.0.0-20190313153728-d0100b6bd8b3 h1:XQyxROzUlZH+WIQwySDgnISgOivlhjIEwaQaJEJrrN0=
 golang.org/x/lint v0.0.0-20190313153728-d0100b6bd8b3/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc=
-golang.org/x/mod v0.1.0/go.mod h1:0QHyrYULN0/3qlju5TqG8bIK38QM8yzMo5ekMj3DlcY=
 golang.org/x/mod v0.1.1-0.20191105210325-c90efee705ee/go.mod h1:QqPTAvyqsEbceGzBzNggFXnrqF1CaUcvgkdR5Ot7KZg=
-golang.org/x/mod v0.1.1-0.20191209134235-331c550502dd h1:ePuNC7PZ6O5BzgPn9bZayERXBdfZjUYoXEf5BTfDfh8=
-golang.org/x/mod v0.1.1-0.20191209134235-331c550502dd/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
-golang.org/x/mod v0.4.2 h1:Gz96sIWK3OalVv/I/qNygP42zyoKp3xptRVCWRFEBvo=
-golang.org/x/mod v0.4.2/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
-golang.org/x/mod v0.6.0-dev.0.20220106191415-9b9b3d81d5e3 h1:kQgndtyPBW/JIYERgdxfwMYh3AVStj88WQTlNDi2a+o=
-golang.org/x/mod v0.6.0-dev.0.20220106191415-9b9b3d81d5e3/go.mod h1:3p9vT2HGsQu2K1YbXdKPJLVgG5VJdoTa1poYQBtP1AY=
+golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4/go.mod h1:jJ57K6gSWd91VN4djpZkiMVwK6gcyfeH4XE8wZrZaV4=
+golang.org/x/mod v0.8.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs=
+golang.org/x/mod v0.12.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs=
+golang.org/x/mod v0.15.0/go.mod h1:hTbmBsO62+eylJbnUtE2MGJUyE7QWk4xUqPFrRgJ+7c=
+golang.org/x/mod v0.17.0/go.mod h1:hTbmBsO62+eylJbnUtE2MGJUyE7QWk4xUqPFrRgJ+7c=
+golang.org/x/mod v0.19.0 h1:fEdghXQSo20giMthA7cd28ZC+jts4amQ3YMXiP5oMQ8=
+golang.org/x/mod v0.19.0/go.mod h1:hTbmBsO62+eylJbnUtE2MGJUyE7QWk4xUqPFrRgJ+7c=
 golang.org/x/net v0.0.0-20180218175443-cbe0f9307d01/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
 golang.org/x/net v0.0.0-20180719180050-a680a1efc54d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
 golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
@@ -388,27 +304,28 @@ golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn
 golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
 golang.org/x/net v0.0.0-20190923162816-aa69164e4478/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
 golang.org/x/net v0.0.0-20200202094626-16171245cfb2/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
-golang.org/x/net v0.0.0-20200324143707-d3edc9973b7e h1:3G+cUijn7XD+S4eJFddp53Pv7+slrESplyjG25HgL+k=
 golang.org/x/net v0.0.0-20200324143707-d3edc9973b7e/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A=
-golang.org/x/net v0.0.0-20201021035429-f5854403a974 h1:IX6qOQeG5uLjB/hjjwjedwfjND0hgjPMMyO1RoIXQNI=
-golang.org/x/net v0.0.0-20201021035429-f5854403a974/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU=
 golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg=
-golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4 h1:4nGaVu0QrbjT/AK2PRLuQfQuh6DJve+pELhqTdAj3x0=
-golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4/go.mod h1:p54w0d4576C0XHj96bSt6lcn1PtDYWL6XObtHCRCNQM=
-golang.org/x/net v0.0.0-20210805182204-aaa1db679c0d h1:20cMwl2fHAzkJMEA+8J4JgqBQcQGzbisXo31MIeenXI=
-golang.org/x/net v0.0.0-20210805182204-aaa1db679c0d/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
-golang.org/x/net v0.0.0-20211015210444-4f30a5c0130f h1:OfiFi4JbukWwe3lzw+xunroH1mnC1e2Gy5cxNJApiSY=
-golang.org/x/net v0.0.0-20211015210444-4f30a5c0130f/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
-golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be h1:vEDujvNQGv4jgYKudGeI/+DAX4Jffq6hpD55MmoEvKs=
+golang.org/x/net v0.0.0-20220722155237-a158d28d115b/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c=
+golang.org/x/net v0.6.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs=
+golang.org/x/net v0.10.0/go.mod h1:0qNGK6F8kojg2nk9dLZ2mShWaEBan6FAoqfSigmmuDg=
+golang.org/x/net v0.15.0/go.mod h1:idbUs1IY1+zTqbi8yxTbhexhEEk5ur9LInksu6HrEpk=
+golang.org/x/net v0.21.0/go.mod h1:bIjVDfnllIU7BJ2DNgfnXvpSvtn8VRwhlsaeUTyUS44=
+golang.org/x/net v0.25.0/go.mod h1:JkAGAh7GEvH74S6FOH42FLoXpXbE/aqXSrIQjXgsiwM=
+golang.org/x/net v0.27.0 h1:5K3Njcw06/l2y9vpGCSdcxWOYHOUk3dVNGDXN+FvAys=
+golang.org/x/net v0.27.0/go.mod h1:dDi0PyhWNoiUOrAS8uXv/vnScO4wnHQO4mj9fn/RytE=
 golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
 golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
 golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
 golang.org/x/sync v0.0.0-20181221193216-37e7f081c4d4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
 golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
 golang.org/x/sync v0.0.0-20190911185100-cd5d95a43a6e/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
-golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9 h1:SQFwaSi55rU7vdNs9Yr0Z324VNlrF+0wMqRXT4St8ck=
-golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
-golang.org/x/sync v0.0.0-20210220032951-036812b2e83c/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
+golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
+golang.org/x/sync v0.1.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
+golang.org/x/sync v0.3.0/go.mod h1:FU7BRWz2tNW+3quACPkgCx/L+uEAv1htQ0V83Z9Rj+Y=
+golang.org/x/sync v0.6.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk=
+golang.org/x/sync v0.7.0 h1:YsImfSBoP9QPYL0xyKJPq0gcaJdG3rInoqxTWbfQu9M=
+golang.org/x/sync v0.7.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk=
 golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
 golang.org/x/sys v0.0.0-20180905080454-ebe1bf3edb33/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
 golang.org/x/sys v0.0.0-20180909124046-d0be0721c37e/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
@@ -420,68 +337,71 @@ golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7w
 golang.org/x/sys v0.0.0-20190904154756-749cb33beabd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
 golang.org/x/sys v0.0.0-20190924154521-2837fb4f24fe/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
 golang.org/x/sys v0.0.0-20200202164722-d101bd2416d5/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
-golang.org/x/sys v0.0.0-20200323222414-85ca7c5b95cd h1:xhmwyvizuTgC2qz7ZlMluP20uW+C3Rm0FD/WLDX8884=
 golang.org/x/sys v0.0.0-20200323222414-85ca7c5b95cd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
-golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
 golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
-golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
-golang.org/x/sys v0.0.0-20210412220455-f1c623a9e750 h1:ZBu6861dZq7xBnG1bn5SRU0vA8nx42at4+kP07FMTog=
-golang.org/x/sys v0.0.0-20210412220455-f1c623a9e750/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
-golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
-golang.org/x/sys v0.0.0-20210510120138-977fb7262007 h1:gG67DSER+11cZvqIMb8S8bt0vZtiN6xWYARwirrOSfE=
-golang.org/x/sys v0.0.0-20210510120138-977fb7262007/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
 golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
-golang.org/x/sys v0.0.0-20210809222454-d867a43fc93e h1:WUoyKPm6nCo1BnNUvPGnFG3T5DUVem42yDJZZ4CNxMA=
-golang.org/x/sys v0.0.0-20210809222454-d867a43fc93e/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
-golang.org/x/sys v0.0.0-20211019181941-9d821ace8654 h1:id054HUawV2/6IGm2IV8KZQjqtwAOo2CYlOToYqa0d0=
 golang.org/x/sys v0.0.0-20211019181941-9d821ace8654/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
-golang.org/x/sys v0.0.0-20220503163025-988cb79eb6c6 h1:nonptSpoQ4vQjyraW20DXPAglgQfVnM9ZC6MmNLMR60=
-golang.org/x/sys v0.0.0-20220503163025-988cb79eb6c6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
-golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1 h1:v+OssWQX+hTHEmOBgwxdZxK4zHq3yOs8F9J7mk0PY8E=
+golang.org/x/sys v0.0.0-20220520151302-bc2c85ada10a/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
+golang.org/x/sys v0.0.0-20220722155257-8c9f86f7a55f/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
+golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
+golang.org/x/sys v0.8.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
+golang.org/x/sys v0.12.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
+golang.org/x/sys v0.17.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
+golang.org/x/sys v0.20.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
+golang.org/x/sys v0.22.0 h1:RI27ohtqKCnwULzJLqkv897zojh5/DwS/ENaMzUOaWI=
+golang.org/x/sys v0.22.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
+golang.org/x/telemetry v0.0.0-20240228155512-f48c80bd79b2/go.mod h1:TeRTkGYfJXctD9OcfyVLyj2J3IxLnKwHJR8f4D8a3YE=
+golang.org/x/telemetry v0.0.0-20240521205824-bda55230c457/go.mod h1:pRgIJT+bRLFKnoM1ldnzKoxTIn14Yxz928LQRYYgIN0=
 golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
+golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8=
+golang.org/x/term v0.5.0/go.mod h1:jMB1sMXY+tzblOD4FWmEbocvup2/aLOaQEp7JmGp78k=
+golang.org/x/term v0.8.0/go.mod h1:xPskH00ivmX89bAKVGSKKtLOWNx2+17Eiy94tnKShWo=
+golang.org/x/term v0.12.0/go.mod h1:owVbMEjm3cBLCHdkQu9b1opXd4ETQWc3BhuQGKgXgvU=
+golang.org/x/term v0.17.0/go.mod h1:lLRBjIVuehSbZlaOtGMbcMncT+aqLLLmKrsjNrUguwk=
+golang.org/x/term v0.20.0/go.mod h1:8UkIAJTvZgivsXaD6/pH6U9ecQzZ45awqEOzuCvwpFY=
+golang.org/x/term v0.22.0 h1:BbsgPEJULsl2fV/AT3v15Mjva5yXKQDyKf+TbDz7QJk=
+golang.org/x/term v0.22.0/go.mod h1:F3qCibpT5AMpCRfhfT53vVJwhLtIVHhB9XDjfFvnMI4=
 golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
 golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
 golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
-golang.org/x/text v0.3.6 h1:aRYxNxv6iGQlyVaZmk6ZgYEDa+Jg18DxebPSrd6bg1M=
 golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
-golang.org/x/text v0.3.7 h1:olpwvP2KacW1ZWvsR7uQhoyTYvKAupfQrRGBFM352Gk=
 golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ=
-golang.org/x/time v0.0.0-20180412165947-fbb02b2291d2 h1:+DCIGbF/swA92ohVg0//6X2IVY3KZs6p9mix0ziNYJM=
+golang.org/x/text v0.7.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8=
+golang.org/x/text v0.9.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8=
+golang.org/x/text v0.13.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE=
+golang.org/x/text v0.14.0/go.mod h1:18ZOQIKpY8NJVqYksKHtTdi31H5itFRjB5/qKTNYzSU=
+golang.org/x/text v0.15.0/go.mod h1:18ZOQIKpY8NJVqYksKHtTdi31H5itFRjB5/qKTNYzSU=
+golang.org/x/text v0.16.0 h1:a94ExnEXNtEwYLGJSIUxnWoxoRz/ZcCsV63ROupILh4=
+golang.org/x/text v0.16.0/go.mod h1:GhwF1Be+LQoKShO3cGOHzqOgRrGaYc9AvblQOmPVHnI=
 golang.org/x/time v0.0.0-20180412165947-fbb02b2291d2/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
 golang.org/x/tools v0.0.0-20180828015842-6cd1fcedba52/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
 golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
 golang.org/x/tools v0.0.0-20190114222345-bf090417da8b/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
 golang.org/x/tools v0.0.0-20190226205152-f727befe758c/go.mod h1:9Yl7xja0Znq3iFh3HoIrodX9oNMXvdceNzlUR8zjMvY=
 golang.org/x/tools v0.0.0-20190311212946-11955173bddd/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
-golang.org/x/tools v0.0.0-20190312151545-0bb0c0a6e846/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
 golang.org/x/tools v0.0.0-20190524140312-2c0ae7006135/go.mod h1:RgjU9mgBXZiqYHBnxXauZ1Gv1EHHAz9KjViQ78xBX0Q=
 golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo=
 golang.org/x/tools v0.0.0-20191216052735-49a3e744a425/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28=
-golang.org/x/tools v0.0.0-20200117012304-6edc0a871e69 h1:yBHHx+XZqXJBm6Exke3N7V9gnlsyXxoCPEb1yVenjfk=
-golang.org/x/tools v0.0.0-20200117012304-6edc0a871e69/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28=
-golang.org/x/tools v0.1.2/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk=
-golang.org/x/tools v0.1.8-0.20211022200916-316ba0b74098/go.mod h1:LGqMHiF4EqQNHR1JncWGqT5BVaXmza+X+BDGol+dOxo=
-golang.org/x/tools v0.1.10 h1:QjFRCZxdOhBJ/UNgnBZLbNV13DlbnK0quyivTnXJM20=
-golang.org/x/tools v0.1.10/go.mod h1:Uh6Zz+xoGYZom868N8YTex3t7RhtHDBrE8Gzo9bV56E=
+golang.org/x/tools v0.1.12/go.mod h1:hNGJHUnrk76NpqgfD5Aqm5Crs+Hm0VOH/i9J2+nxYbc=
+golang.org/x/tools v0.6.0/go.mod h1:Xwgl3UAJ/d3gWutnCtw505GrjyAbvKui8lOU390QaIU=
+golang.org/x/tools v0.13.0/go.mod h1:HvlwmtVNQAhOuCjW7xxvovg8wbNq7LwfXh/k7wXUl58=
+golang.org/x/tools v0.21.1-0.20240508182429-e35e4ccd0d2d/go.mod h1:aiJjzUbINMkxbQROHiO6hDPo2LHcIPhhQsa9DLh0yGk=
+golang.org/x/tools v0.23.0 h1:SGsXPZ+2l4JsgaCKkx+FQ9YZ5XEtA1GZYuoDjenLjvg=
+golang.org/x/tools v0.23.0/go.mod h1:pnu6ufv6vQkll6szChhK3C3L/ruaIv5eBeztNG8wtsI=
 golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
 golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
 golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
-golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1 h1:go1bK/D/BFZV2I8cIQd1NKEZ+0owSTG1fDTci4IqFcE=
-golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
 google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM=
 google.golang.org/appengine v1.3.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4=
-google.golang.org/appengine v1.4.0 h1:/wp5JvzpHIxhs/dumFmF7BXTf3Z+dd4uXta4kVyO508=
 google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4=
 google.golang.org/genproto v0.0.0-20180817151627-c66870c02cf8/go.mod h1:JiN7NxoALGmiZfu7CAH4rXhgtRTLTxftemlI0sWmxmc=
 google.golang.org/genproto v0.0.0-20190201180003-4b09977fb922/go.mod h1:L3J43x8/uS+qIUoksaLKe6OS3nUKxOKuIFz1sl2/jx4=
 google.golang.org/genproto v0.0.0-20190819201941-24fa4b261c55/go.mod h1:DMBHOl98Agz4BDEuKkezgsaosCRResVns1a3J2ZsMNc=
-google.golang.org/genproto v0.0.0-20200526211855-cb27e3aa2013 h1:+kGHl1aib/qcwaRi1CbqBZ1rk19r85MNUf8HaBghugY=
 google.golang.org/genproto v0.0.0-20200526211855-cb27e3aa2013/go.mod h1:NbSheEEYHJ7i3ixzK3sjbqSGDJWnxyFXZblF3eUsNvo=
 google.golang.org/grpc v1.16.0/go.mod h1:0JHn/cJsOMiMfNA9+DeHDlAU7KAAB5GDlYFpa9MZMio=
 google.golang.org/grpc v1.18.0/go.mod h1:6QZJwpn2B+Zp71q/5VxRsJ6NXXVCE5NRUHRo+f3cWCs=
 google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c=
 google.golang.org/grpc v1.23.0/go.mod h1:Y5yQAOtifL1yxbo5wqy6BxZv8vAUGQwXBOALyacEbxg=
-google.golang.org/grpc v1.27.0 h1:rRYRFMVgRv6E0D70Skyfsr28tDXIuuPZyWGMPdMcnXg=
 google.golang.org/grpc v1.27.0/go.mod h1:qbnxyOmOxrQa7FizSgH+ReBfzJrCY1pSN7KXBS8abTk=
 google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8=
 google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0=
@@ -489,28 +409,21 @@ google.golang.org/protobuf v0.0.0-20200228230310-ab0ca4ff8a60/go.mod h1:cfTl7dwQ
 google.golang.org/protobuf v1.20.1-0.20200309200217-e05f789c0967/go.mod h1:A+miEFZTKqfCUM6K7xSMQL9OKL/b6hQv+e19PK+JZNE=
 google.golang.org/protobuf v1.21.0/go.mod h1:47Nbq4nVaFHyn7ilMalzfO3qCViNmqZ2kzikPIcrTAo=
 google.golang.org/protobuf v1.22.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU=
-google.golang.org/protobuf v1.23.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU=
 google.golang.org/protobuf v1.23.1-0.20200526195155-81db48ad09cc/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU=
 google.golang.org/protobuf v1.25.0 h1:Ejskq+SyPohKW+1uil0JJMtmHCgJPJ/qWTxr8qp+R4c=
 google.golang.org/protobuf v1.25.0/go.mod h1:9JNX74DMeImyA3h4bdi1ymwjUzf21/xIlbajtzgsN7c=
-gopkg.in/alecthomas/kingpin.v2 v2.2.6 h1:jMFz6MfLP0/4fUyZle81rXUoxOBFi19VUFKVDOQfozc=
 gopkg.in/alecthomas/kingpin.v2 v2.2.6/go.mod h1:FMv+mEhP44yOT+4EoQTLFTRgOQ1FBLkstjWtayDeSgw=
 gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
 gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127 h1:qIbj1fsPNlZgppZ+VLlY7N33q108Sa+fhmuc+sWQYwY=
 gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
-gopkg.in/errgo.v1 v1.0.1 h1:oQFRXzZ7CkBGdm1XZm/EbQYaYNNEElNBOd09M6cqNso=
 gopkg.in/errgo.v1 v1.0.1/go.mod h1:3NjfXwocQRYAPTq4/fzX+CwUhPRcR/azYRhj8G+LqMo=
 gopkg.in/fsnotify.v1 v1.4.7 h1:xOHLXZwVvI9hhs+cLKq5+I5onOuwQLhQwiu63xxlHs4=
 gopkg.in/fsnotify.v1 v1.4.7/go.mod h1:Tz8NjZHkW78fSQdbUxIjBTcgA1z1m8ZHf0WmKUhAMys=
 gopkg.in/gormigrate.v1 v1.6.0 h1:XpYM6RHQPmzwY7Uyu+t+xxMXc86JYFJn4nEc9HzQjsI=
 gopkg.in/gormigrate.v1 v1.6.0/go.mod h1:Lf00lQrHqfSYWiTtPcyQabsDdM6ejZaMgV0OU6JMSlw=
-gopkg.in/macaroon-bakery.v2 v2.0.1 h1:0N1TlEdfLP4HXNCg7MQUMp5XwvOoxk+oe9Owr2cpvsc=
 gopkg.in/macaroon-bakery.v2 v2.0.1/go.mod h1:B4/T17l+ZWGwxFSZQmlBwp25x+og7OkhETfr3S9MbIA=
-gopkg.in/macaroon.v2 v2.0.0 h1:LVWycAfeJBUjCIqfR9gqlo7I8vmiXRr51YEOZ1suop8=
 gopkg.in/macaroon.v2 v2.0.0/go.mod h1:+I6LnTMkm/uV5ew/0nsulNjL16SK4+C8yDmRUzHR17I=
-gopkg.in/mgo.v2 v2.0.0-20190816093944-a6b53ec6cb22 h1:VpOs+IwYnYBaFnrNAeB8UUWtL3vEUnzSCL1nVjPhqrw=
 gopkg.in/mgo.v2 v2.0.0-20190816093944-a6b53ec6cb22/go.mod h1:yeKp02qBN3iKW1OzL3MGk2IdtZzaj7SFntXj72NppTA=
-gopkg.in/resty.v1 v1.12.0 h1:CuXP0Pjfw9rOuY6EP+UvtNvt5DSqHpIxILZKT/quCZI=
 gopkg.in/resty.v1 v1.12.0/go.mod h1:mDo4pnntr5jdWRML875a/NmxYqAlA73dVijT2AXvQQo=
 gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7 h1:uRGJdciOHaEIrze2W8Q3AKkepLTh2hOroT7a+7czfdQ=
 gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7/go.mod h1:dt/ZhP58zS4L8KSrWDmTeBkI65Dw0HsyUHuEVlX15mw=
@@ -521,5 +434,4 @@ gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY=
 gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ=
 honnef.co/go/tools v0.0.0-20180728063816-88497007e858/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4=
 honnef.co/go/tools v0.0.0-20190102054323-c2f93a96b099/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4=
-honnef.co/go/tools v0.0.0-20190523083050-ea95bdfd59fc h1:/hemPrYIhOhy8zYrNj+069zDB68us2sMGsfkFJO0iZs=
 honnef.co/go/tools v0.0.0-20190523083050-ea95bdfd59fc/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4=
diff --git a/libwallet/newop/state.go b/libwallet/newop/state.go
index 5e072d0f..6241c803 100644
--- a/libwallet/newop/state.go
+++ b/libwallet/newop/state.go
@@ -918,18 +918,11 @@ type ConfirmState struct {
 
 func (s *ConfirmState) OpenFeeEditor() error {
 
-	maxFeeRate := newPaymentAnalyzer(s.PaymentContext).MaxFeeRateToAddress(&operation.PaymentToAddress{
-		TakeFeeFromAmount:     s.TakeFeeFromAmount,
-		AmountInSat:           s.Amount.InSat,
-		FeeRateInSatsPerVByte: s.FeeRateInSatsPerVByte,
-	})
-
 	next := &EditFeeState{
-		Resolved:                 s.Resolved,
-		AmountInfo:               s.AmountInfo,
-		Validated:                s.Validated,
-		Note:                     s.Note,
-		MaxFeeRateInSatsPerVByte: maxFeeRate,
+		Resolved:   s.Resolved,
+		AmountInfo: s.AmountInfo,
+		Validated:  s.Validated,
+		Note:       s.Note,
 	}
 
 	next.emit()
diff --git a/libwallet/operation/payment_analyzer.go b/libwallet/operation/payment_analyzer.go
index 142dcef5..7d18cd7b 100644
--- a/libwallet/operation/payment_analyzer.go
+++ b/libwallet/operation/payment_analyzer.go
@@ -580,30 +580,3 @@ func (a *PaymentAnalyzer) computeFeeForTFFASwap(payment *PaymentToInvoice, feeRa
 
 	return a.feeCalculator.Fee(onChainAmount, feeRate, true)
 }
-
-// MaxFeeRateToAddress computes the maximum fee rate that can be used when
-// paying a given amount. This does not imply that the payment _can be made_.
-// When given invalid parameters, it's likely to still obtain a value here and
-// the resulting analysis would be Unpayable. It's up to the caller to first
-// verify the amount is payable, and only then call this method.
-func (a *PaymentAnalyzer) MaxFeeRateToAddress(payment *PaymentToAddress) float64 {
-
-	if payment.AmountInSat > a.totalBalance() {
-		return 0
-	}
-
-	var restInSat int64
-	if payment.TakeFeeFromAmount {
-		restInSat = payment.AmountInSat
-	} else {
-		restInSat = a.totalBalance() - payment.AmountInSat
-	}
-
-	for _, sizeForAmount := range a.nextTransactionSize.SizeProgression {
-		if sizeForAmount.AmountInSat >= payment.AmountInSat {
-			return float64(restInSat) / float64(sizeForAmount.SizeInVByte)
-		}
-	}
-
-	return 0
-}
diff --git a/libwallet/operation/payment_analyzer_test.go b/libwallet/operation/payment_analyzer_test.go
index 419d4296..34d5d163 100644
--- a/libwallet/operation/payment_analyzer_test.go
+++ b/libwallet/operation/payment_analyzer_test.go
@@ -2239,170 +2239,3 @@ func TestAnalyzeOffChain(t *testing.T) {
 		})
 	}
 }
-
-func TestMaxFeeRate(t *testing.T) {
-	testCases := []struct {
-		desc     string
-		nts      *NextTransactionSize
-		payment  *PaymentToAddress
-		expected float64
-	}{
-		{
-			desc: "small amount with one coin",
-			payment: &PaymentToAddress{
-				TakeFeeFromAmount: false,
-				AmountInSat:       10_000,
-			},
-			expected: 9_900,
-		},
-		{
-			desc: "take fee from amount one coin",
-			payment: &PaymentToAddress{
-				AmountInSat:       1_000_000,
-				TakeFeeFromAmount: true,
-			},
-			expected: 10_000,
-		},
-		{
-			desc: "zero amount",
-			payment: &PaymentToAddress{
-				TakeFeeFromAmount: false,
-				AmountInSat:       0,
-			},
-			expected: 10_000,
-		},
-		{
-			desc: "zero amount using TFFA",
-			payment: &PaymentToAddress{
-				TakeFeeFromAmount: true,
-				AmountInSat:       0,
-			},
-			expected: 0,
-		},
-		{
-			desc: "amount greater than balance",
-			payment: &PaymentToAddress{
-				TakeFeeFromAmount: false,
-				AmountInSat:       1_000_000_000,
-			},
-			expected: 0,
-		},
-		{
-			desc: "small amount with one coin and debt > 0",
-			nts: &NextTransactionSize{
-				SizeProgression:   defaultNTS.SizeProgression,
-				ExpectedDebtInSat: 10_000,
-			},
-			payment: &PaymentToAddress{
-				TakeFeeFromAmount: false,
-				AmountInSat:       10_000,
-			},
-			expected: 9_800,
-		},
-		{
-			desc: "take fee from amount success with debt > 0",
-			nts: &NextTransactionSize{
-				SizeProgression:   defaultNTS.SizeProgression,
-				ExpectedDebtInSat: 10_000,
-			},
-			payment: &PaymentToAddress{
-				AmountInSat:       990_000,
-				TakeFeeFromAmount: true,
-			},
-			expected: 9_900,
-		},
-		{
-			desc: "amount greater than balance because debt > 0",
-			nts: &NextTransactionSize{
-				SizeProgression:   defaultNTS.SizeProgression,
-				ExpectedDebtInSat: 10_000,
-			},
-			payment: &PaymentToAddress{
-				TakeFeeFromAmount: false,
-				AmountInSat:       999_900,
-			},
-			expected: 0,
-		},
-		{
-			desc: "needs 2 coins to spend",
-			nts: &NextTransactionSize{
-				SizeProgression: []SizeForAmount{
-					{
-						AmountInSat: 10_000,
-						SizeInVByte: 240,
-					},
-					{
-						AmountInSat: 20_000,
-						SizeInVByte: 450,
-					},
-				},
-				ExpectedDebtInSat: 0,
-			},
-			payment: &PaymentToAddress{
-				TakeFeeFromAmount: false,
-				AmountInSat:       11_000,
-			},
-			expected: 20,
-		},
-		{
-			desc: "needs 2 coins to spend with debt",
-			nts: &NextTransactionSize{
-				SizeProgression: []SizeForAmount{
-					{
-						AmountInSat: 10_000,
-						SizeInVByte: 240,
-					},
-					{
-						AmountInSat: 20_000,
-						SizeInVByte: 400,
-					},
-				},
-				ExpectedDebtInSat: 8_000,
-			},
-			payment: &PaymentToAddress{
-				TakeFeeFromAmount:     false,
-				AmountInSat:           11_000,
-				FeeRateInSatsPerVByte: 0,
-			},
-			expected: 2.5,
-		},
-		{
-			desc: "TFFA needs 2 coins to spend with debt",
-			nts: &NextTransactionSize{
-				SizeProgression: []SizeForAmount{
-					{
-						AmountInSat: 10_000,
-						SizeInVByte: 240,
-					},
-					{
-						AmountInSat: 20_000,
-						SizeInVByte: 400,
-					},
-				},
-				ExpectedDebtInSat: 8_000,
-			},
-			payment: &PaymentToAddress{
-				TakeFeeFromAmount: true,
-				AmountInSat:       12_000,
-			},
-			expected: 30,
-		},
-	}
-
-	for _, tC := range testCases {
-		t.Run(tC.desc, func(t *testing.T) {
-
-			var analyzer *PaymentAnalyzer
-			if tC.nts != nil {
-				analyzer = NewPaymentAnalyzer(defaultFeeWindow, tC.nts)
-			} else {
-				analyzer = NewPaymentAnalyzer(defaultFeeWindow, defaultNTS)
-			}
-
-			maxFeeRate := analyzer.MaxFeeRateToAddress(tC.payment)
-			if maxFeeRate != tC.expected {
-				t.Fatalf("Max fee rate %v != %v", maxFeeRate, tC.expected)
-			}
-		})
-	}
-}
diff --git a/tools/bootstrap-gomobile.sh b/tools/bootstrap-gomobile.sh
index c5f8dd16..afef6846 100755
--- a/tools/bootstrap-gomobile.sh
+++ b/tools/bootstrap-gomobile.sh
@@ -11,4 +11,4 @@ mkdir -p "$build_dir/pkg"
 
 GOMODCACHE="$build_dir/pkg" \
     go install golang.org/x/mobile/cmd/gomobile && \
-    go install golang.org/x/mobile/cmd/gobind
\ No newline at end of file
+    go install golang.org/x/mobile/cmd/gobind
diff --git a/tools/libwallet-android.sh b/tools/libwallet-android.sh
index f348a99c..e835ae72 100755
--- a/tools/libwallet-android.sh
+++ b/tools/libwallet-android.sh
@@ -5,16 +5,18 @@ set -e
 repo_root=$(git rev-parse --show-toplevel)
 build_dir="$repo_root/libwallet/.build"
 
+# Install and setup gomobile on demand (no-op if already installed and up-to-date)
+. "$repo_root/tools/bootstrap-gomobile.sh"
+
 # OSS project has a different folder libwallet aar, so we receive it as param
 libwallet="$1"
 if [[ ! -s "$1" ]]; then
     libwallet="$repo_root/android/libwallet/libs/libwallet.aar"
 fi
 
-
 cd "$repo_root/libwallet"
 
-mkdir -p "$(dirname $libwallet)"
+mkdir -p "$(dirname "$libwallet")"
 
 # Create the cache folders
 mkdir -p "$build_dir/android"
@@ -35,10 +37,17 @@ if [[ -z $GOCACHE ]]; then
     GOCACHE="$build_dir/android"
 fi
 
+# gomobile bind generates the src-android-* directories several times, leading to fail with:
+# /tmp/go-build3034672677/b001/exe/gomobile: mkdir $GOCACHE/src-android-arm64: file exists
+# exit status 1
+# There is no significant change in build times without these folders.
+rm -rf "$GOCACHE"/src-android-* 2>/dev/null \
+  || echo "No src-android-* directories found in GOCACHE."
+
 GOMODCACHE="$GOMODCACHE" \
     go run golang.org/x/mobile/cmd/gomobile bind \
     -target="android" -o "$libwallet" \
-    -cache  "$GOCACHE"\
+    -androidapi 19 \
     -trimpath -ldflags="-buildid=. -v" \
     . ./newop