diff --git a/Navigation.ts b/Navigation.ts index aca216691c..153dcf3d61 100644 --- a/Navigation.ts +++ b/Navigation.ts @@ -127,6 +127,8 @@ import RestoreChannelBackups from './views/Settings/EmbeddedNode/RestoreChannelB import RawTxHex from './views/RawTxHex'; +import CustodialWalletWarning from './views/Settings/CustodialWalletWarning'; + const AppScenes = { Wallet: { screen: Wallet @@ -445,6 +447,9 @@ const AppScenes = { }, SetNodePicture: { screen: SetNodePicture + }, + CustodialWalletWarning: { + screen: CustodialWalletWarning } }; diff --git a/android/app/build.gradle b/android/app/build.gradle index 0ae04d1a2b..729711d734 100644 --- a/android/app/build.gradle +++ b/android/app/build.gradle @@ -1,10 +1,10 @@ apply plugin: "com.android.application" +apply plugin: "org.jetbrains.kotlin.android" apply plugin: "com.facebook.react" apply plugin: "com.google.protobuf" apply plugin: "kotlin-android" -apply plugin: "kotlin-android-extensions" // LN address notifications apply plugin: "com.google.gms.google-services" @@ -94,13 +94,14 @@ def enableSeparateBuildPerCPUArchitecture = true def nativeArchitectures = project.getProperties().get("reactNativeDebugArchitectures") android { + namespace "app.zeusln.zeus" defaultConfig { compileSdk rootProject.ext.compileSdkVersion applicationId "app.zeusln.zeus" minSdkVersion rootProject.ext.minSdkVersion targetSdkVersion rootProject.ext.targetSdkVersion versionCode 84 - versionName "0.8.3-alpha" + versionName "0.8.3-beta1" multiDexEnabled true missingDimensionStrategy 'react-native-camera', 'general' } @@ -179,10 +180,12 @@ android { } dependencies { + // The version of react-native is set by the React Native Gradle Plugin + implementation("com.facebook.react:react-android") + implementation fileTree(dir: "libs", include: ["*.jar"]) implementation 'androidx.multidex:multidex:2.0.1' implementation project(':react-native-randombytes') - implementation "com.facebook.react:react-native:0.70.6!!" // From node_modules implementation 'androidx.core:core-ktx:1.9.0' implementation 'androidx.appcompat:appcompat:1.6.1' implementation 'androidx.swiperefreshlayout:swiperefreshlayout:1.2.0-alpha01' diff --git a/android/app/src/main/java/com/zeus/LndMobileScheduledSyncWorker.java b/android/app/src/main/java/com/zeus/LndMobileScheduledSyncWorker.java index 68a121270e..53d88a90f0 100644 --- a/android/app/src/main/java/com/zeus/LndMobileScheduledSyncWorker.java +++ b/android/app/src/main/java/com/zeus/LndMobileScheduledSyncWorker.java @@ -87,7 +87,7 @@ public ListenableFuture startWork() { writeLastScheduledSyncAttemptToDb(); // Hyperlog.i(TAG, "MainActivity.started = " + MainActivity.started); - if (persistentServicesEnabled || MainActivity.started) { + if (persistentServicesEnabled || MainActivity.Companion.getStarted()) { // Hyperlog.i(TAG, "MainActivity is started or persistentServicesEnabled = " + persistentServicesEnabled + ", quitting job"); completer.set(Result.success()); return null; diff --git a/android/app/src/main/java/com/zeus/LndMobileTools.java b/android/app/src/main/java/com/zeus/LndMobileTools.java index 9a092c293f..c04d4f9e4c 100644 --- a/android/app/src/main/java/com/zeus/LndMobileTools.java +++ b/android/app/src/main/java/com/zeus/LndMobileTools.java @@ -134,9 +134,9 @@ public void copyLndLog(String network, Promise promise) { intent.setType("text/plain"); intent.putExtra(Intent.EXTRA_TITLE, "lnd.log"); if (network == "testnet") { - getReactApplicationContext().getCurrentActivity().startActivityForResult(intent, MainActivity.INTENT_COPYLNDLOGTESTNET); + getReactApplicationContext().getCurrentActivity().startActivityForResult(intent, MainActivity.Companion.getINTENT_COPYLNDLOGTESTNET()); } else { - getReactApplicationContext().getCurrentActivity().startActivityForResult(intent, MainActivity.INTENT_COPYLNDLOG); + getReactApplicationContext().getCurrentActivity().startActivityForResult(intent, MainActivity.Companion.getINTENT_COPYLNDLOG()); } promise.resolve(true); } @@ -268,14 +268,14 @@ private void readToEnd(BufferedReader buf, boolean emit) throws IOException { @ReactMethod public void saveChannelsBackup(String base64Backups, Promise promise) { - MainActivity.tmpChanBackup = Base64.decode(base64Backups, Base64.NO_WRAP); + MainActivity.Companion.setTmpChanBackup(Base64.decode(base64Backups, Base64.NO_WRAP)); SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd_HH-mm-ss"); Intent intent = new Intent(Intent.ACTION_CREATE_DOCUMENT); intent.addCategory(Intent.CATEGORY_OPENABLE); intent.setType("text/plain"); intent.putExtra(Intent.EXTRA_TITLE, "zeus-channels-backup-" + dateFormat.format(new Date()) + ".bin"); - getReactApplicationContext().getCurrentActivity().startActivityForResult(intent, MainActivity.INTENT_EXPORTCHANBACKUP); + getReactApplicationContext().getCurrentActivity().startActivityForResult(intent, MainActivity.Companion.getINTENT_EXPORTCHANBACKUP()); promise.resolve(true); } @@ -288,9 +288,9 @@ public void saveChannelBackupFile(String network, Promise promise) { intent.setType("text/plain"); intent.putExtra(Intent.EXTRA_TITLE, "zeus-channels-backup-" + dateFormat.format(new Date()) + ".bin"); if (network == "testnet") { - getReactApplicationContext().getCurrentActivity().startActivityForResult(intent, MainActivity.INTENT_EXPORTCHANBACKUPFILETESTNET); + getReactApplicationContext().getCurrentActivity().startActivityForResult(intent, MainActivity.Companion.getINTENT_EXPORTCHANBACKUPFILETESTNET()); } else { - getReactApplicationContext().getCurrentActivity().startActivityForResult(intent, MainActivity.INTENT_EXPORTCHANBACKUPFILE); + getReactApplicationContext().getCurrentActivity().startActivityForResult(intent, MainActivity.Companion.getINTENT_EXPORTCHANBACKUPFILE()); } promise.resolve(true); } diff --git a/android/app/src/main/java/com/zeus/MainActivity.java b/android/app/src/main/java/com/zeus/MainActivity.java deleted file mode 100644 index b0ae336531..0000000000 --- a/android/app/src/main/java/com/zeus/MainActivity.java +++ /dev/null @@ -1,159 +0,0 @@ -package app.zeusln.zeus; - -import com.facebook.react.ReactActivity; -import com.facebook.react.ReactActivityDelegate; -import com.facebook.react.defaults.DefaultNewArchitectureEntryPoint; -import com.facebook.react.defaults.DefaultReactActivityDelegate; - -import android.os.Bundle; -import androidx.core.content.ContextCompat; - -import android.content.Intent; -import android.app.Activity; -import android.net.Uri; -import android.widget.Toast; -import java.io.ByteArrayInputStream; -import java.io.File; -import java.io.FileInputStream; -import java.io.IOException; -import java.io.InputStream; -import java.io.OutputStream; -import java.lang.ref.WeakReference; - -import dev.doubledot.doki.ui.DokiActivity; - -public class MainActivity extends ReactActivity { - /** - * Returns the name of the main component registered from JavaScript. This is used to schedule - * rendering of the component. - */ - @Override - protected String getMainComponentName() { - return "zeus"; - } - - /** - * Returns the instance of the {@link ReactActivityDelegate}. Here we use a util class {@link - * DefaultReactActivityDelegate} which allows you to easily enable Fabric and Concurrent React - * (aka React 18) with two boolean flags. - */ - @Override - protected ReactActivityDelegate createReactActivityDelegate() { - return new DefaultReactActivityDelegate( - this, - getMainComponentName(), - // If you opted-in for the New Architecture, we enable the Fabric Renderer. - DefaultNewArchitectureEntryPoint.getFabricEnabled()); - } - - static String TAG = "MainActivity"; - static boolean started = false; - - static int INTENT_COPYLNDLOG = 100; - static int INTENT_EXPORTCHANBACKUP = 101; - static int INTENT_EXPORTCHANBACKUPFILE = 102; - - static int INTENT_COPYLNDLOGTESTNET = 200; - static int INTENT_EXPORTCHANBACKUPFILETESTNET = 202; - - static byte[] tmpChanBackup; - - public static WeakReference currentActivity; - - @Override - protected void onCreate(Bundle savedInstanceState) { - super.onCreate(null); - currentActivity = new WeakReference<>(MainActivity.this); - started = true; - } - - @Override - public void onNewIntent(Intent intent) { - super.onNewIntent(intent); - setIntent(intent); - } - - @Override - public void onActivityResult(int requestCode, int resultCode, Intent data) { - super.onActivityResult(requestCode, resultCode, data); - if (requestCode == INTENT_COPYLNDLOG && resultCode == Activity.RESULT_OK) { - Uri destUri = data.getData(); - File sourceLocation = new File(getFilesDir().toString() + "/logs/bitcoin/mainnet/lnd.log"); - try { - InputStream in = new FileInputStream(sourceLocation); - OutputStream out = getContentResolver().openOutputStream(destUri); - - byte[] buf = new byte[1024]; - int len; - while ((len = in.read(buf)) > 0) { - out.write(buf, 0, len); - } - in.close(); - out.close(); - } - catch(IOException e) { - Toast.makeText(this, "Error " + e.getMessage(), Toast.LENGTH_LONG).show(); - } - } else if (requestCode == INTENT_EXPORTCHANBACKUP && resultCode == Activity.RESULT_OK) { - Uri destUri = data.getData(); - try { - ByteArrayInputStream in = new ByteArrayInputStream(MainActivity.tmpChanBackup); - OutputStream out = getContentResolver().openOutputStream(destUri); - byte[] buf = new byte[1024]; - int len; - while ((len = in.read(buf)) > 0) { - out.write(buf, 0, len); - } - in.close(); - out.close(); - MainActivity.tmpChanBackup = new byte[0]; - } catch (IOException e) { - e.printStackTrace(); - } - } else if (requestCode == INTENT_EXPORTCHANBACKUPFILE && resultCode == Activity.RESULT_OK) { - Uri destUri = data.getData(); - File sourceLocation = new File(getFilesDir().toString() + "/data/chain/bitcoin/mainnet/channel.backup"); - try { - InputStream in = new FileInputStream(sourceLocation); - OutputStream out = getContentResolver().openOutputStream(destUri); - - byte[] buf = new byte[1024]; - int len; - while ((len = in.read(buf)) > 0) { - out.write(buf, 0, len); - } - in.close(); - out.close(); - } - catch(IOException e) { - Toast.makeText(this, "Error " + e.getMessage(), Toast.LENGTH_LONG).show(); - } - } else if (requestCode == INTENT_EXPORTCHANBACKUPFILETESTNET && resultCode == Activity.RESULT_OK) { - Uri destUri = data.getData(); - File sourceLocation = new File(getFilesDir().toString() + "/data/chain/bitcoin/testnet/channel.backup"); - try { - InputStream in = new FileInputStream(sourceLocation); - OutputStream out = getContentResolver().openOutputStream(destUri); - - byte[] buf = new byte[1024]; - int len; - while ((len = in.read(buf)) > 0) { - out.write(buf, 0, len); - } - in.close(); - out.close(); - } - catch(IOException e) { - Toast.makeText(this, "Error " + e.getMessage(), Toast.LENGTH_LONG).show(); - } - } - } - - public void showMsg() { - startActivity(new Intent(MainActivity.this, DokiActivity.class)); - } - - public static MainActivity getActivity() { - return currentActivity.get(); - } -} \ No newline at end of file diff --git a/android/app/src/main/java/com/zeus/MainActivity.kt b/android/app/src/main/java/com/zeus/MainActivity.kt new file mode 100644 index 0000000000..e51435f9ef --- /dev/null +++ b/android/app/src/main/java/com/zeus/MainActivity.kt @@ -0,0 +1,129 @@ +package app.zeusln.zeus + +import android.content.Intent +import android.os.Bundle +import android.widget.Toast +import com.facebook.react.ReactActivity +import com.facebook.react.ReactActivityDelegate +import com.facebook.react.defaults.DefaultNewArchitectureEntryPoint.fabricEnabled +import com.facebook.react.defaults.DefaultReactActivityDelegate +import dev.doubledot.doki.ui.DokiActivity +import java.io.ByteArrayInputStream +import java.io.File +import java.io.FileInputStream +import java.io.IOException +import java.io.InputStream +import java.lang.ref.WeakReference + +class MainActivity : ReactActivity() { + /** + * Returns the name of the main component registered from JavaScript. This is used to schedule + * rendering of the component. + */ + override fun getMainComponentName(): String = "zeus" + + /** + * Returns the instance of the [ReactActivityDelegate]. We use [DefaultReactActivityDelegate] + * which allows you to enable New Architecture with a single boolean flags [fabricEnabled] + */ + override fun createReactActivityDelegate(): ReactActivityDelegate = + DefaultReactActivityDelegate(this, mainComponentName, fabricEnabled) + + override fun onCreate(savedInstanceState: Bundle?) { + super.onCreate(null) + currentActivity = WeakReference(this@MainActivity) + started = true + } + + override fun onNewIntent(intent: Intent) { + super.onNewIntent(intent) + setIntent(intent) + } + + override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) { + super.onActivityResult(requestCode, resultCode, data) + if (requestCode == INTENT_COPYLNDLOG && resultCode == RESULT_OK) { + val destUri = data!!.data + val sourceLocation = File("$filesDir/logs/bitcoin/mainnet/lnd.log") + try { + val `in`: InputStream = FileInputStream(sourceLocation) + val out = contentResolver.openOutputStream(destUri!!) + val buf = ByteArray(1024) + var len: Int + while (`in`.read(buf).also { len = it } > 0) { + out!!.write(buf, 0, len) + } + `in`.close() + out!!.close() + } catch (e: IOException) { + Toast.makeText(this, "Error " + e.message, Toast.LENGTH_LONG).show() + } + } else if (requestCode == INTENT_EXPORTCHANBACKUP && resultCode == RESULT_OK) { + val destUri = data!!.data + try { + val `in` = ByteArrayInputStream(tmpChanBackup) + val out = contentResolver.openOutputStream(destUri!!) + val buf = ByteArray(1024) + var len: Int + while (`in`.read(buf).also { len = it } > 0) { + out!!.write(buf, 0, len) + } + `in`.close() + out!!.close() + tmpChanBackup = ByteArray(0) + } catch (e: IOException) { + e.printStackTrace() + } + } else if (requestCode == INTENT_EXPORTCHANBACKUPFILE && resultCode == RESULT_OK) { + val destUri = data!!.data + val sourceLocation = File("$filesDir/data/chain/bitcoin/mainnet/channel.backup") + try { + val `in`: InputStream = FileInputStream(sourceLocation) + val out = contentResolver.openOutputStream(destUri!!) + val buf = ByteArray(1024) + var len: Int + while (`in`.read(buf).also { len = it } > 0) { + out!!.write(buf, 0, len) + } + `in`.close() + out!!.close() + } catch (e: IOException) { + Toast.makeText(this, "Error " + e.message, Toast.LENGTH_LONG).show() + } + } else if (requestCode == INTENT_EXPORTCHANBACKUPFILETESTNET && resultCode == RESULT_OK) { + val destUri = data!!.data + val sourceLocation = File("$filesDir/data/chain/bitcoin/testnet/channel.backup") + try { + val `in`: InputStream = FileInputStream(sourceLocation) + val out = contentResolver.openOutputStream(destUri!!) + val buf = ByteArray(1024) + var len: Int + while (`in`.read(buf).also { len = it } > 0) { + out!!.write(buf, 0, len) + } + `in`.close() + out!!.close() + } catch (e: IOException) { + Toast.makeText(this, "Error " + e.message, Toast.LENGTH_LONG).show() + } + } + } + + fun showMsg() { + startActivity(Intent(this@MainActivity, DokiActivity::class.java)) + } + + companion object { + var TAG = "MainActivity" + var started = false + var INTENT_COPYLNDLOG = 100 + var INTENT_EXPORTCHANBACKUP = 101 + var INTENT_EXPORTCHANBACKUPFILE = 102 + var INTENT_COPYLNDLOGTESTNET = 200 + var INTENT_EXPORTCHANBACKUPFILETESTNET = 202 + var tmpChanBackup: ByteArray = ByteArray(0) + var currentActivity: WeakReference? = null + val activity: MainActivity? + get() = currentActivity!!.get() + } +} \ No newline at end of file diff --git a/android/app/src/main/java/com/zeus/MainApplication.java b/android/app/src/main/java/com/zeus/MainApplication.java deleted file mode 100644 index 05b1e01e13..0000000000 --- a/android/app/src/main/java/com/zeus/MainApplication.java +++ /dev/null @@ -1,102 +0,0 @@ -package app.zeusln.zeus; - -import android.app.Application; -import android.util.Log; -import com.facebook.react.PackageList; -//import com.facebook.hermes.reactexecutor.HermesExecutorFactory; -import com.facebook.react.bridge.JavaScriptExecutorFactory; -import com.facebook.react.shell.MainReactPackage; - -import com.facebook.react.bridge.JSIModulePackage; - -import com.facebook.react.ReactApplication; -// import com.swmansion.gesturehandler.react.RNGestureHandlerPackage; -import com.oblador.vectoricons.VectorIconsPackage; -import com.facebook.react.ReactNativeHost; -import com.facebook.react.ReactPackage; -import com.remobile.qrcodeLocalImage.RCTQRCodeLocalImagePackage; -import android.content.Context; - -import com.facebook.react.defaults.DefaultNewArchitectureEntryPoint; -import com.facebook.react.defaults.DefaultReactNativeHost; -import com.facebook.soloader.SoLoader; - -import java.lang.reflect.InvocationTargetException; -import java.util.List; -import javax.net.ssl.X509TrustManager; - -import com.ReactNativeBlobUtil.ReactNativeBlobUtilUtils; - -public class MainApplication extends Application implements ReactApplication { - - private final ReactNativeHost mReactNativeHost = - new DefaultReactNativeHost(this) { - @Override - public boolean getUseDeveloperSupport() { - return BuildConfig.DEBUG; - } - - @Override - protected List getPackages() { - @SuppressWarnings("UnnecessaryLocalVariable") - List packages = new PackageList(this).getPackages(); - // Packages that cannot be autolinked yet can be added manually here, for example: - // packages.add(new MyReactNativePackage()); - - // ZEUS - packages.add(new MobileToolsPackage()); - packages.add(new LndMobilePackage()); - packages.add(new LndMobileToolsPackage()); - packages.add(new LndMobileScheduledSyncPackage()); - packages.add(new LncPackage()); - // packages.add(new ZeusTorPackage()); - - return packages; - } - - @Override - protected String getJSMainModuleName() { - return "index"; - } - - @Override - protected boolean isNewArchEnabled() { - return BuildConfig.IS_NEW_ARCHITECTURE_ENABLED; - } - - @Override - protected Boolean isHermesEnabled() { - return BuildConfig.IS_HERMES_ENABLED; - } - }; - - @Override - public ReactNativeHost getReactNativeHost() { - return mReactNativeHost; - } - - @Override - public void onCreate() { - super.onCreate(); - SoLoader.init(this, /* native exopackage */ false); - if (BuildConfig.IS_NEW_ARCHITECTURE_ENABLED) { - // If you opted-in for the New Architecture, we load the native entry point for this app. - DefaultNewArchitectureEntryPoint.load(); - } - - ReactNativeBlobUtilUtils.sharedTrustManager = new X509TrustManager() { - @Override - public void checkClientTrusted(java.security.cert.X509Certificate[] chain, String authType) { - } - - @Override - public void checkServerTrusted(java.security.cert.X509Certificate[] chain, String authType) { - } - - @Override - public java.security.cert.X509Certificate[] getAcceptedIssuers() { - return new java.security.cert.X509Certificate[]{}; - } - }; - } -} diff --git a/android/app/src/main/java/com/zeus/MainApplication.kt b/android/app/src/main/java/com/zeus/MainApplication.kt new file mode 100644 index 0000000000..16bfe69cbe --- /dev/null +++ b/android/app/src/main/java/com/zeus/MainApplication.kt @@ -0,0 +1,61 @@ +package app.zeusln.zeus + +import android.app.Application +import com.ReactNativeBlobUtil.ReactNativeBlobUtilUtils +import com.facebook.react.PackageList +import com.facebook.react.ReactApplication +import com.facebook.react.ReactHost +import com.facebook.react.ReactNativeHost +import com.facebook.react.ReactPackage +import com.facebook.react.defaults.DefaultNewArchitectureEntryPoint.load +import com.facebook.react.defaults.DefaultReactHost.getDefaultReactHost +import com.facebook.react.defaults.DefaultReactNativeHost +import com.facebook.soloader.SoLoader +import java.security.cert.X509Certificate +import javax.net.ssl.X509TrustManager + +//import com.facebook.hermes.reactexecutor.HermesExecutorFactory; +// import com.swmansion.gesturehandler.react.RNGestureHandlerPackage; +class MainApplication : Application(), ReactApplication { + override public val reactNativeHost: ReactNativeHost = object : DefaultReactNativeHost(this) { + override fun getPackages(): List = + PackageList(this).packages.apply { + // Packages that cannot be autolinked yet can be added manually here, for example: + // add(MyReactNativePackage()) + + // ZEUS + add(MobileToolsPackage()) + add(LndMobilePackage()) + add(LndMobileToolsPackage()) + add(LndMobileScheduledSyncPackage()) + add(LncPackage()) + // add(new ZeusTorPackage()); + } + + override fun getJSMainModuleName(): String = "index" + + override fun getUseDeveloperSupport(): Boolean = BuildConfig.DEBUG + + override val isNewArchEnabled: Boolean = BuildConfig.IS_NEW_ARCHITECTURE_ENABLED + override val isHermesEnabled: Boolean = BuildConfig.IS_HERMES_ENABLED + } + + override val reactHost: ReactHost + get() = getDefaultReactHost(this.applicationContext, reactNativeHost) + + override fun onCreate() { + super.onCreate() + SoLoader.init(this, false) + if (BuildConfig.IS_NEW_ARCHITECTURE_ENABLED) { + // If you opted-in for the New Architecture, we load the native entry point for this app. + load() + } + ReactNativeBlobUtilUtils.sharedTrustManager = object : X509TrustManager { + override fun checkClientTrusted(chain: Array, authType: String) {} + override fun checkServerTrusted(chain: Array, authType: String) {} + override fun getAcceptedIssuers(): Array { + return arrayOf() + } + } + } +} diff --git a/android/build.gradle b/android/build.gradle index 9c724a0323..f89ca88f0e 100644 --- a/android/build.gradle +++ b/android/build.gradle @@ -1,12 +1,11 @@ -// Top-level build file where you can add configuration options common to all sub-projects/modules. - buildscript { ext { buildToolsVersion = "34.0.0" minSdkVersion = 28 compileSdkVersion = 34 targetSdkVersion = 34 - ndkVersion = "23.1.7779620" + ndkVersion = "25.1.8937393" + kotlinVersion = "1.8.0" } subprojects { subproject -> afterEvaluate{ @@ -25,9 +24,9 @@ buildscript { dependencies { classpath("com.android.tools.build:gradle") classpath("com.facebook.react:react-native-gradle-plugin") + classpath("org.jetbrains.kotlin:kotlin-gradle-plugin") // Needed for react-native-camera-kit - classpath("org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version") classpath("com.google.protobuf:protobuf-gradle-plugin:0.9.3") // LN address notifications @@ -46,3 +45,5 @@ allprojects { } } } + +apply plugin: "com.facebook.react.rootproject" \ No newline at end of file diff --git a/android/gradle.properties b/android/gradle.properties index f76ed896eb..9682d43c54 100755 --- a/android/gradle.properties +++ b/android/gradle.properties @@ -26,9 +26,6 @@ android.useAndroidX=true # Automatically convert third-party libraries to use AndroidX android.enableJetifier=true -# Version of flipper SDK to use with React Native -FLIPPER_VERSION=0.182.0 - # Use this property to specify which architecture you want to build. # You can also override it from the CLI using # ./gradlew -PreactNativeArchitectures=x86_64 @@ -45,6 +42,5 @@ newArchEnabled=false # If set to false, you will be using JSC instead. hermesEnabled=true -# We don't use Kotlin, but we'll mandate this version for all react-native libs -kotlinVersion=1.7.21 -kotlin_version=1.7.21 +# Necessary for react-native-camera-kit +kotlin_version=1.8.0 diff --git a/android/gradle/wrapper/gradle-wrapper.properties b/android/gradle/wrapper/gradle-wrapper.properties index 6ec1567a0f..d11cdd907d 100644 --- a/android/gradle/wrapper/gradle-wrapper.properties +++ b/android/gradle/wrapper/gradle-wrapper.properties @@ -1,6 +1,7 @@ distributionBase=GRADLE_USER_HOME distributionPath=wrapper/dists -distributionUrl=https\://services.gradle.org/distributions/gradle-8.0.1-all.zip +distributionUrl=https\://services.gradle.org/distributions/gradle-8.3-all.zip networkTimeout=10000 +validateDistributionUrl=true zipStoreBase=GRADLE_USER_HOME zipStorePath=wrapper/dists diff --git a/android/gradlew b/android/gradlew index 65dcd68d65..f0fd109853 100755 --- a/android/gradlew +++ b/android/gradlew @@ -83,10 +83,8 @@ done # This is normally unused # shellcheck disable=SC2034 APP_BASE_NAME=${0##*/} -APP_HOME=$( cd "${APP_HOME:-./}" && pwd -P ) || exit - -# 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"' +# Discard cd standard output in case $CDPATH is set (https://github.com/gradle/gradle/issues/25036) +APP_HOME=$( cd "${APP_HOME:-./}" > /dev/null && pwd -P ) || exit # Use the maximum available, or set MAX_FD != -1 to use that value. MAX_FD=maximum @@ -133,10 +131,13 @@ location of your Java installation." fi else 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. + if ! command -v java >/dev/null 2>&1 + then + 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 location of your Java installation." + fi fi # Increase the maximum file descriptors if we can. @@ -197,6 +198,10 @@ if "$cygwin" || "$msys" ; then done fi + +# 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"' + # 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 diff --git a/backends/EmbeddedLND.ts b/backends/EmbeddedLND.ts index bbde2a6f7f..2d6102b69e 100644 --- a/backends/EmbeddedLND.ts +++ b/backends/EmbeddedLND.ts @@ -30,8 +30,14 @@ const { closeChannel, openChannel } = lndMobile.channel; -const { signMessageNodePubkey, verifyMessageNodePubkey, bumpFee } = - lndMobile.wallet; +const { + signMessageNodePubkey, + verifyMessageNodePubkey, + bumpFee, + fundPsbt, + finalizePsbt, + publishTransaction +} = lndMobile.wallet; const { walletBalance, newAddress, getTransactions, sendCoins } = lndMobile.onchain; @@ -151,10 +157,21 @@ export default class EmbeddedLND extends LND { urlParams && (await queryRoutes(urlParams[0], urlParams[1])); // getForwardingHistory = () => N/A // // Coin Control - // fundPsbt = (data: any) => this.postRequest('/v2/wallet/psbt/fund', data); - // finalizePsbt = (data: any) => - // this.postRequest('/v2/wallet/psbt/finalize', data); - // publishTransaction = (data: any) => this.postRequest('/v2/wallet/tx', data); + fundPsbt = async (data: any) => + await fundPsbt({ + raw: data.raw, + spend_unconfirmed: data.spend_unconfirmed, + sat_per_vbyte: data.sat_per_vbyte + }); + finalizePsbt = async (data: any) => + await finalizePsbt({ + funded_psbt: data.funded_psbt + }); + publishTransaction = async (data: any) => + await publishTransaction({ + tx_hex: data.tx_hex + }); + getUTXOs = async () => await listUnspent(); bumpFee = async (data: any) => await bumpFee(data); lookupInvoice = async (data: any) => await lookupInvoice(data.r_hash); diff --git a/backends/LightningNodeConnect.ts b/backends/LightningNodeConnect.ts index bfd21006b1..3c94453a42 100644 --- a/backends/LightningNodeConnect.ts +++ b/backends/LightningNodeConnect.ts @@ -237,9 +237,8 @@ export default class LightningNodeConnect { }, force: urlParams && urlParams[2] }; - return await this.lnc.lnd.lightning - .closeChannel(params) - .then((data: lnrpc.CloseStatusUpdate) => snakeize(data)); + + return this.lnc.lnd.lightning.closeChannel(params); }; getNodeInfo = async (urlParams?: Array) => await this.lnc.lnd.lightning diff --git a/components/Button.tsx b/components/Button.tsx index 5c03f69eb0..1a2a5e124b 100644 --- a/components/Button.tsx +++ b/components/Button.tsx @@ -12,7 +12,6 @@ interface ButtonProps { tertiary?: boolean; quaternary?: boolean; warning?: boolean; - quinary?: boolean; iconOnly?: boolean; adaptiveWidth?: boolean; containerStyle?: any; @@ -32,7 +31,6 @@ function Button(props: ButtonProps) { tertiary, quaternary, warning, - quinary, iconOnly, adaptiveWidth, containerStyle, @@ -83,10 +81,8 @@ function Button(props: ButtonProps) { buttonStyle={{ backgroundColor: iconOnly ? 'transparent' - : quinary - ? themeColor('buttonBackground') || themeColor('secondary') : quaternary - ? themeColor('background') + ? themeColor('buttonBackground') || themeColor('secondary') : tertiary ? themeColor('highlight') : secondary @@ -104,10 +100,6 @@ function Button(props: ButtonProps) { : { color: iconOnly ? textColor - : quinary - ? warning - ? themeColor('warning') - : textColor : quaternary ? warning ? themeColor('warning') diff --git a/components/Channels/SortButton.tsx b/components/Channels/SortButton.tsx index dd8e70cb31..2e7abd91ce 100644 --- a/components/Channels/SortButton.tsx +++ b/components/Channels/SortButton.tsx @@ -72,7 +72,7 @@ export default class SortButton extends React.Component { }} adaptiveWidth buttonStyle={{ width: 50 }} - quinary + quaternary onPress={() => ActionSheetIOS.showActionSheetWithOptions( { diff --git a/components/UTXOPicker.tsx b/components/UTXOPicker.tsx index 5e703b9e79..556e2ca018 100644 --- a/components/UTXOPicker.tsx +++ b/components/UTXOPicker.tsx @@ -12,13 +12,14 @@ import remove from 'lodash/remove'; import { inject, observer } from 'mobx-react'; import Amount from './Amount'; -import Button from './../components/Button'; +import Button from '../components/Button'; +import LoadingIndicator from './LoadingIndicator'; -import { localeString } from './../utils/LocaleUtils'; -import { themeColor } from './../utils/ThemeUtils'; +import { localeString } from '../utils/LocaleUtils'; +import { themeColor } from '../utils/ThemeUtils'; -import stores from './../stores/Stores'; -import UTXOsStore from './../stores/UTXOsStore'; +import stores from '../stores/Stores'; +import UTXOsStore from '../stores/UTXOsStore'; interface UTXOPickerProps { title?: string; @@ -67,6 +68,7 @@ export default class UTXOPicker extends React.Component< selectedBalance: 0, setBalance: 0 }); + this.props.onValueChange([], 0); } displayValues(): string { @@ -161,100 +163,142 @@ export default class UTXOPicker extends React.Component< /> - ( - } + + {!loading && utxos.length === 0 && ( + + - this.toggleItem(item) - } > - - {item.getOutpoint} - - + + )} + + {!loading && utxos.length > 0 && ( + ( + + this.toggleItem(item) + } > - - - - )} - keyExtractor={( - item: any, - index: number - ) => `${item.txid}-${index}`} - onEndReachedThreshold={50} - refreshing={loading} - onRefresh={() => getUTXOs()} - /> - - -