diff --git a/android/app/build.gradle.kts b/android/app/build.gradle.kts index 979eb466e2f0..4d5ab430caf2 100644 --- a/android/app/build.gradle.kts +++ b/android/app/build.gradle.kts @@ -47,9 +47,9 @@ android { lint { lintConfig = file("${rootProject.projectDir}/config/lint.xml") - baseline = file("lint-baseline.xml") abortOnError = true warningsAsErrors = true + checkDependencies = true } } diff --git a/android/app/lint-baseline.xml b/android/app/lint-baseline.xml deleted file mode 100644 index 9f67e68efad6..000000000000 --- a/android/app/lint-baseline.xml +++ /dev/null @@ -1,37 +0,0 @@ - - - - - - - - - - - - - - - - diff --git a/android/app/src/debug/AndroidManifest.xml b/android/app/src/debug/AndroidManifest.xml index cfe2c7c4dfdb..f428b876c743 100644 --- a/android/app/src/debug/AndroidManifest.xml +++ b/android/app/src/debug/AndroidManifest.xml @@ -11,7 +11,7 @@ android:theme="@style/Theme.App.Starting" android:extractNativeLibs="true" android:allowBackup="false" - android:banner="@drawable/banner" + android:banner="@mipmap/ic_banner" android:name=".MullvadApplication" tools:ignore="DataExtractionRules,GoogleAppIndexingWarning"/> diff --git a/android/app/src/main/AndroidManifest.xml b/android/app/src/main/AndroidManifest.xml index 8dc3c4e38551..24c430f44457 100644 --- a/android/app/src/main/AndroidManifest.xml +++ b/android/app/src/main/AndroidManifest.xml @@ -3,7 +3,10 @@ - + + @@ -20,9 +23,12 @@ android:required="false" /> + MaterialTheme.colorScheme.error - StatusLevel.Warning -> MaterialTheme.colorScheme.warning - StatusLevel.Info -> MaterialTheme.colorScheme.surfaceContainer - }, - shape = CircleShape, - ) - .size(Dimens.notificationStatusIconSize) - .constrainAs(status) { - top.linkTo(textTitle.top) - start.linkTo(parent.start) - bottom.linkTo(textTitle.bottom) - } + NotificationDot( + statusLevel, + Modifier.constrainAs(status) { + top.linkTo(textTitle.top) + start.linkTo(parent.start) + bottom.linkTo(textTitle.bottom) + }, ) Text( text = title.uppercase(), @@ -173,24 +164,58 @@ private fun Notification(notificationBannerData: NotificationData) { ) } action?.let { - IconButton( + NotificationAction( + it.icon, + onClick = it.onClick, + contentDescription = it.contentDescription, modifier = Modifier.constrainAs(actionIcon) { - top.linkTo(parent.top) - end.linkTo(parent.end) - bottom.linkTo(parent.bottom) - } - .testTag(NOTIFICATION_BANNER_ACTION) - .padding(all = Dimens.notificationEndIconPadding), - onClick = it.onClick, - ) { - Icon( - modifier = Modifier.padding(Dimens.notificationIconPadding), - imageVector = it.icon, - contentDescription = it.contentDescription, - tint = MaterialTheme.colorScheme.onSurface, - ) - } + top.linkTo(parent.top) + end.linkTo(parent.end) + bottom.linkTo(parent.bottom) + }, + ) } } } + +@Composable +private fun NotificationDot(statusLevel: StatusLevel, modifier: Modifier) { + Box( + modifier = + modifier + .background( + color = + when (statusLevel) { + StatusLevel.Error -> MaterialTheme.colorScheme.error + StatusLevel.Warning -> MaterialTheme.colorScheme.warning + StatusLevel.Info -> MaterialTheme.colorScheme.surfaceContainer + }, + shape = CircleShape, + ) + .size(Dimens.notificationStatusIconSize) + ) +} + +@Composable +private fun NotificationAction( + imageVector: ImageVector, + contentDescription: String?, + onClick: () -> Unit, + modifier: Modifier = Modifier, +) { + IconButton( + modifier = + modifier + .testTag(NOTIFICATION_BANNER_ACTION) + .padding(all = Dimens.notificationEndIconPadding), + onClick = onClick, + ) { + Icon( + modifier = Modifier.padding(Dimens.notificationIconPadding), + imageVector = imageVector, + contentDescription = contentDescription, + tint = MaterialTheme.colorScheme.onSurface, + ) + } +} diff --git a/android/app/src/main/kotlin/net/mullvad/mullvadvpn/compose/dialog/RedeemVoucherDialog.kt b/android/app/src/main/kotlin/net/mullvad/mullvadvpn/compose/dialog/RedeemVoucherDialog.kt index 3d49a7afcac9..04f3c05a11e0 100644 --- a/android/app/src/main/kotlin/net/mullvad/mullvadvpn/compose/dialog/RedeemVoucherDialog.kt +++ b/android/app/src/main/kotlin/net/mullvad/mullvadvpn/compose/dialog/RedeemVoucherDialog.kt @@ -41,6 +41,7 @@ import net.mullvad.mullvadvpn.compose.textfield.CustomTextField import net.mullvad.mullvadvpn.compose.util.MAX_VOUCHER_LENGTH import net.mullvad.mullvadvpn.compose.util.vouchersVisualTransformation import net.mullvad.mullvadvpn.constant.VOUCHER_LENGTH +import net.mullvad.mullvadvpn.lib.model.DAYS_PER_VOUCHER_MONTH import net.mullvad.mullvadvpn.lib.model.RedeemVoucherError import net.mullvad.mullvadvpn.lib.theme.AppTheme import net.mullvad.mullvadvpn.lib.theme.Dimens @@ -162,18 +163,18 @@ fun RedeemVoucherDialog( val message = stringResource( R.string.added_to_your_account, - when (days) { - 0 -> { + when { + days == 0 -> { stringResource(R.string.less_than_one_day) } - in 1..59 -> { + days < 2 * DAYS_PER_VOUCHER_MONTH -> { pluralStringResource(id = R.plurals.days, count = days, days) } else -> { pluralStringResource( id = R.plurals.months, - count = days / 30, - days / 30, + count = days / DAYS_PER_VOUCHER_MONTH, + days / DAYS_PER_VOUCHER_MONTH, ) } }, diff --git a/android/app/src/main/kotlin/net/mullvad/mullvadvpn/compose/extensions/ResourcesExtensions.kt b/android/app/src/main/kotlin/net/mullvad/mullvadvpn/compose/extensions/ResourcesExtensions.kt index 11b41dd27a61..9611897e766c 100644 --- a/android/app/src/main/kotlin/net/mullvad/mullvadvpn/compose/extensions/ResourcesExtensions.kt +++ b/android/app/src/main/kotlin/net/mullvad/mullvadvpn/compose/extensions/ResourcesExtensions.kt @@ -2,20 +2,20 @@ package net.mullvad.mullvadvpn.compose.extensions import android.content.res.Resources import net.mullvad.mullvadvpn.R -import org.joda.time.DateTime import org.joda.time.Duration -import org.joda.time.Period + +private const val DAYS_IN_STANDARD_YEAR = 365 fun Resources.getExpiryQuantityString(accountExpiry: Duration): String { - val expiryPeriod = Period(DateTime.now(), accountExpiry) + val days = accountExpiry.standardDays.toInt() + val years = (accountExpiry.standardDays / DAYS_IN_STANDARD_YEAR).toInt() + return if (accountExpiry.millis <= 0) { getString(R.string.out_of_time) - } else if (expiryPeriod.years > 0) { - getRemainingText(this, R.plurals.years_left, expiryPeriod.years) - } else if (expiryPeriod.months >= 3) { - getRemainingText(this, R.plurals.months_left, expiryPeriod.months) - } else if (expiryPeriod.months > 0 || expiryPeriod.days >= 1) { - getRemainingText(this, R.plurals.days_left, expiryPeriod.days) + } else if (years > 1) { + getRemainingText(this, R.plurals.years_left, years) + } else if (days >= 1) { + getRemainingText(this, R.plurals.days_left, days) } else { getString(R.string.less_than_a_day_left) } diff --git a/android/app/src/main/kotlin/net/mullvad/mullvadvpn/compose/screen/LoginScreen.kt b/android/app/src/main/kotlin/net/mullvad/mullvadvpn/compose/screen/LoginScreen.kt index 9dcd01676760..7a3d3380228a 100644 --- a/android/app/src/main/kotlin/net/mullvad/mullvadvpn/compose/screen/LoginScreen.kt +++ b/android/app/src/main/kotlin/net/mullvad/mullvadvpn/compose/screen/LoginScreen.kt @@ -94,6 +94,9 @@ private fun PreviewLoginScreen( AppTheme { LoginScreen(state = state) } } +private const val TOP_SPACER_WEIGHT = 1f +private const val BOTTOM_SPACER_WEIGHT = 3f + @Destination(style = LoginTransition::class) @Composable fun Login( @@ -177,7 +180,7 @@ private fun LoginScreen( .background(MaterialTheme.colorScheme.primary) .verticalScroll(scrollState) ) { - Spacer(modifier = Modifier.weight(1f)) + Spacer(modifier = Modifier.weight(TOP_SPACER_WEIGHT)) LoginIcon( state.loginState, modifier = @@ -185,7 +188,7 @@ private fun LoginScreen( .padding(bottom = Dimens.largePadding), ) LoginContent(state, onAccountNumberChange, onLoginClick, onDeleteHistoryClick) - Spacer(modifier = Modifier.weight(3f)) + Spacer(modifier = Modifier.weight(BOTTOM_SPACER_WEIGHT)) CreateAccountPanel(onCreateAccountClick, isEnabled = state.loginState is Idle) } } diff --git a/android/app/src/main/kotlin/net/mullvad/mullvadvpn/compose/textfield/CustomTextField.kt b/android/app/src/main/kotlin/net/mullvad/mullvadvpn/compose/textfield/CustomTextField.kt index b64de576eeb9..5bdcc961e77a 100644 --- a/android/app/src/main/kotlin/net/mullvad/mullvadvpn/compose/textfield/CustomTextField.kt +++ b/android/app/src/main/kotlin/net/mullvad/mullvadvpn/compose/textfield/CustomTextField.kt @@ -13,7 +13,6 @@ import androidx.compose.runtime.SideEffect import androidx.compose.runtime.getValue import androidx.compose.runtime.mutableStateOf import androidx.compose.runtime.remember -import androidx.compose.runtime.rememberCoroutineScope import androidx.compose.runtime.setValue import androidx.compose.ui.Modifier import androidx.compose.ui.draw.clip @@ -23,8 +22,6 @@ import androidx.compose.ui.text.input.KeyboardCapitalization import androidx.compose.ui.text.input.KeyboardType import androidx.compose.ui.text.input.TextFieldValue import androidx.compose.ui.text.input.VisualTransformation -import kotlinx.coroutines.delay -import kotlinx.coroutines.launch import net.mullvad.mullvadvpn.constant.EMPTY_STRING import net.mullvad.mullvadvpn.constant.NEWLINE_STRING @@ -53,9 +50,6 @@ fun CustomTextField( imeAction = ImeAction.Done, ), ) { - - val scope = rememberCoroutineScope() - // This is the same implementation as in BasicTextField.kt but with initial selection set at the // end of the text rather than in the beginning. // This is a fix for https://issuetracker.google.com/issues/272693535. @@ -97,16 +91,7 @@ fun CustomTextField( singleLine = true, placeholder = placeholderText?.let { { Text(text = it) } }, keyboardOptions = keyboardOptions, - keyboardActions = - KeyboardActions( - onDone = { - scope.launch { - // https://issuetracker.google.com/issues/305518328 - delay(100) - onSubmit(value) - } - } - ), + keyboardActions = KeyboardActions(onDone = { onSubmit(value) }), visualTransformation = visualTransformation, colors = colors, isError = !isValidValue, diff --git a/android/app/src/main/kotlin/net/mullvad/mullvadvpn/viewmodel/EditApiAccessMethodViewModel.kt b/android/app/src/main/kotlin/net/mullvad/mullvadvpn/viewmodel/EditApiAccessMethodViewModel.kt index 4d85ae986842..48e4ac85acfc 100644 --- a/android/app/src/main/kotlin/net/mullvad/mullvadvpn/viewmodel/EditApiAccessMethodViewModel.kt +++ b/android/app/src/main/kotlin/net/mullvad/mullvadvpn/viewmodel/EditApiAccessMethodViewModel.kt @@ -38,6 +38,7 @@ import net.mullvad.mullvadvpn.repository.ApiAccessRepository import net.mullvad.mullvadvpn.util.delayAtLeast import org.apache.commons.validator.routines.InetAddressValidator +@Suppress("TooManyFunctions") class EditApiAccessMethodViewModel( private val apiAccessRepository: ApiAccessRepository, private val inetAddressValidator: InetAddressValidator, diff --git a/android/app/src/main/kotlin/net/mullvad/mullvadvpn/viewmodel/SelectLocationViewModel.kt b/android/app/src/main/kotlin/net/mullvad/mullvadvpn/viewmodel/SelectLocationViewModel.kt index c34b182aa673..4ddad8477bae 100644 --- a/android/app/src/main/kotlin/net/mullvad/mullvadvpn/viewmodel/SelectLocationViewModel.kt +++ b/android/app/src/main/kotlin/net/mullvad/mullvadvpn/viewmodel/SelectLocationViewModel.kt @@ -43,6 +43,7 @@ import net.mullvad.mullvadvpn.usecase.customlists.CustomListActionUseCase import net.mullvad.mullvadvpn.usecase.customlists.CustomListsRelayItemUseCase import net.mullvad.mullvadvpn.usecase.customlists.FilterCustomListsRelayItemUseCase +@Suppress("TooManyFunctions") class SelectLocationViewModel( private val relayListFilterRepository: RelayListFilterRepository, private val availableProvidersUseCase: AvailableProvidersUseCase, diff --git a/android/app/src/main/kotlin/net/mullvad/mullvadvpn/viewmodel/VpnSettingsViewModel.kt b/android/app/src/main/kotlin/net/mullvad/mullvadvpn/viewmodel/VpnSettingsViewModel.kt index 7829d0ce24cc..5ca136341eed 100644 --- a/android/app/src/main/kotlin/net/mullvad/mullvadvpn/viewmodel/VpnSettingsViewModel.kt +++ b/android/app/src/main/kotlin/net/mullvad/mullvadvpn/viewmodel/VpnSettingsViewModel.kt @@ -43,6 +43,7 @@ sealed interface VpnSettingsSideEffect { data object NavigateToDnsDialog : VpnSettingsSideEffect } +@Suppress("TooManyFunctions") class VpnSettingsViewModel( private val repository: SettingsRepository, private val relayListRepository: RelayListRepository, diff --git a/android/app/src/main/res/xml/data_extraction_rules.xml b/android/app/src/main/res/xml/data_extraction_rules.xml new file mode 100644 index 000000000000..b762ef705c10 --- /dev/null +++ b/android/app/src/main/res/xml/data_extraction_rules.xml @@ -0,0 +1,21 @@ + + + + + + + + + + + + + + + + + diff --git a/android/app/src/main/res/xml/full_backup_content.xml b/android/app/src/main/res/xml/full_backup_content.xml new file mode 100644 index 000000000000..e88e6597d9a6 --- /dev/null +++ b/android/app/src/main/res/xml/full_backup_content.xml @@ -0,0 +1,16 @@ + + + + + + + + + + + + diff --git a/android/app/src/test/kotlin/net/mullvad/mullvadvpn/applist/ApplicationsProviderTest.kt b/android/app/src/test/kotlin/net/mullvad/mullvadvpn/applist/ApplicationsProviderTest.kt index 560dafb24a42..efa97c6ab0f9 100644 --- a/android/app/src/test/kotlin/net/mullvad/mullvadvpn/applist/ApplicationsProviderTest.kt +++ b/android/app/src/test/kotlin/net/mullvad/mullvadvpn/applist/ApplicationsProviderTest.kt @@ -1,6 +1,7 @@ package net.mullvad.mullvadvpn.applist import android.Manifest +import android.annotation.SuppressLint import android.content.pm.ApplicationInfo import android.content.pm.PackageManager import io.mockk.every @@ -22,6 +23,7 @@ class ApplicationsProviderTest { unmockkAll() } + @SuppressLint("UseCheckPermission") @Test fun `fetch all apps should work`() { val launchWithInternetPackageName = "launch_with_internet_package_name" @@ -75,6 +77,7 @@ class ApplicationsProviderTest { verifyAll { mockedPackageManager.getInstalledApplications(PackageManager.GET_META_DATA) + // Ensure checkPermission was invoked on all packages listOf( launchWithInternetPackageName, launchWithoutInternetPackageName, diff --git a/android/build.gradle.kts b/android/build.gradle.kts index f62e00c87eaf..24bcb0e4d0a7 100644 --- a/android/build.gradle.kts +++ b/android/build.gradle.kts @@ -71,7 +71,6 @@ buildscript { } } -val baselineFile = file("$rootDir/config/baseline.xml") val configFile = files("$rootDir/config/detekt.yml") val projectSource = file(projectDir) @@ -82,7 +81,6 @@ detekt { allRules = false config.setFrom(configFile) source.setFrom(projectSource) - baseline = baselineFile parallel = true ignoreFailures = false autoCorrect = true diff --git a/android/config/baseline.xml b/android/config/baseline.xml deleted file mode 100644 index 34abe7b92498..000000000000 --- a/android/config/baseline.xml +++ /dev/null @@ -1,23 +0,0 @@ - - - - - CyclomaticComplexMethod:MockApiDispatcher.kt$MockApiDispatcher$override fun dispatch(request: RecordedRequest): MockResponse - EmptyKtFile:build.gradle.kts$.build.gradle.kts - LongMethod:NotificationBanner.kt$@Composable private fun Notification(notificationBannerData: NotificationData) - MagicNumber:CustomTextField.kt$100 - MagicNumber:LoginScreen.kt$3f - MagicNumber:RedeemVoucherDialog.kt$30 - MagicNumber:RedeemVoucherDialog.kt$59 - MagicNumber:ResourcesExtensions.kt$3 - NestedBlockDepth:MockApiDispatcher.kt$MockApiDispatcher$override fun dispatch(request: RecordedRequest): MockResponse - PrintStackTrace:Extensions.kt$ex - ReturnCount:RelayNameComparator.kt$RelayNameComparator$private infix fun List<String>.compareWith(other: List<String>): Int - ReturnCount:TalpidVpnService.kt$TalpidVpnService$private fun createTun(config: TunConfig): CreateTunResult - TooManyFunctions:EditApiAccessMethodViewModel.kt$EditApiAccessMethodViewModel : ViewModel - TooManyFunctions:SelectLocationViewModel.kt$SelectLocationViewModel : ViewModel - TooManyFunctions:VpnSettingsViewModel.kt$VpnSettingsViewModel : ViewModel - UnusedParameter:SimpleMullvadHttpClient.kt$SimpleMullvadHttpClient$body: JSONArray? = null - UnusedPrivateMember:ConnectivityListener.kt$ConnectivityListener$private fun finalize() - - diff --git a/android/lib/build.gradle.kts b/android/lib/build.gradle.kts deleted file mode 100644 index 8b137891791f..000000000000 --- a/android/lib/build.gradle.kts +++ /dev/null @@ -1 +0,0 @@ - diff --git a/android/lib/common/src/main/AndroidManifest.xml b/android/lib/common/src/main/AndroidManifest.xml index acaad2f3b4fc..cc947c567995 100644 --- a/android/lib/common/src/main/AndroidManifest.xml +++ b/android/lib/common/src/main/AndroidManifest.xml @@ -1,4 +1 @@ - - - + diff --git a/android/lib/daemon-grpc/src/main/kotlin/net/mullvad/mullvadvpn/lib/daemon/grpc/RelayNameComparator.kt b/android/lib/daemon-grpc/src/main/kotlin/net/mullvad/mullvadvpn/lib/daemon/grpc/RelayNameComparator.kt index a1b1d3b09237..4b848dde7b4b 100644 --- a/android/lib/daemon-grpc/src/main/kotlin/net/mullvad/mullvadvpn/lib/daemon/grpc/RelayNameComparator.kt +++ b/android/lib/daemon-grpc/src/main/kotlin/net/mullvad/mullvadvpn/lib/daemon/grpc/RelayNameComparator.kt @@ -6,28 +6,32 @@ internal object RelayNameComparator : Comparator { override fun compare(o1: RelayItem.Location.Relay, o2: RelayItem.Location.Relay): Int { val partitions1 = o1.name.split(regex) val partitions2 = o2.name.split(regex) - return if (partitions1.size > partitions2.size) partitions1 compareWith partitions2 - else -(partitions2 compareWith partitions1) - } - private infix fun List.compareWith(other: List): Int { - this.forEachIndexed { index, s -> - if (other.size <= index) return 1 - val partsCompareResult = compareStringOrInt(other[index], s) - if (partsCompareResult != 0) return partsCompareResult - } - return 0 + partitions1 + .zip(partitions2) + .map { (p1, p2) -> compareStringOrInt(p1, p2) } + .forEach { + if (it != 0) { + // Parts differed, return compare result + return it + } + } + return partitions1.size.compareTo(partitions2.size) } - private fun compareStringOrInt(s1: String, s2: String): Int { - val int1 = s1.toIntOrNull() - val int2 = s2.toIntOrNull() - return if (int1 == null || int2 == null || int1 == int2) { - s2.compareTo(s1) + private fun compareStringOrInt(p1: String, p2: String): Int { + val int1 = p1.toIntOrNull() + val int2 = p2.toIntOrNull() + return if (int1 is Int && int2 is Int && int1 != int2) { + // If both are Int and not equal (they might have leading zeros) we should compare them + // as numbers + int1.compareTo(int2) } else { - int2.compareTo(int1) + p1.compareTo(p2) } } + // Regexp that splits digit and non digit, e.g se-got-wg-101 would be ["se-got-wg-", "101"] so + // that the number later can be sorted, e.g 9 being listed before 10. private val regex = "(?<=\\d)(?=\\D)|(?<=\\D)(?=\\d)".toRegex() } diff --git a/android/lib/model/src/main/kotlin/net/mullvad/mullvadvpn/lib/model/VoucherConstant.kt b/android/lib/model/src/main/kotlin/net/mullvad/mullvadvpn/lib/model/VoucherConstant.kt new file mode 100644 index 000000000000..a27efa6bf3a7 --- /dev/null +++ b/android/lib/model/src/main/kotlin/net/mullvad/mullvadvpn/lib/model/VoucherConstant.kt @@ -0,0 +1,3 @@ +package net.mullvad.mullvadvpn.lib.model + +const val DAYS_PER_VOUCHER_MONTH = 30 diff --git a/android/lib/resource/build.gradle.kts b/android/lib/resource/build.gradle.kts index c162b25a0c57..fa9cd5d63e9b 100644 --- a/android/lib/resource/build.gradle.kts +++ b/android/lib/resource/build.gradle.kts @@ -23,7 +23,6 @@ android { lint { lintConfig = file("lint.xml") - baseline = file("lint-baseline.xml") abortOnError = true warningsAsErrors = true } diff --git a/android/lib/resource/lint-baseline.xml b/android/lib/resource/lint-baseline.xml deleted file mode 100644 index d46970e0dbe1..000000000000 --- a/android/lib/resource/lint-baseline.xml +++ /dev/null @@ -1,76 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/android/lib/resource/src/main/res/drawable-xhdpi/banner.png b/android/lib/resource/src/main/res/drawable-xhdpi/banner.png deleted file mode 100644 index da8eee678dd3..000000000000 Binary files a/android/lib/resource/src/main/res/drawable-xhdpi/banner.png and /dev/null differ diff --git a/android/lib/resource/src/main/res/drawable/ic_banner_foreground.xml b/android/lib/resource/src/main/res/drawable/ic_banner_foreground.xml new file mode 100644 index 000000000000..0e542f5c0d28 --- /dev/null +++ b/android/lib/resource/src/main/res/drawable/ic_banner_foreground.xml @@ -0,0 +1,62 @@ + + + + + + + + + + + + + + + + + + + diff --git a/android/lib/resource/src/main/res/drawable/icon_android_mono.xml b/android/lib/resource/src/main/res/drawable/icon_android_mono.xml index 0d0aa38c1255..45e0acfdd572 100644 --- a/android/lib/resource/src/main/res/drawable/icon_android_mono.xml +++ b/android/lib/resource/src/main/res/drawable/icon_android_mono.xml @@ -1,9 +1,11 @@ + android:fillType="evenOdd" + tools:ignore="VectorPath" /> diff --git a/android/lib/resource/src/main/res/mipmap-hdpi/ic_launcher.png b/android/lib/resource/src/main/res/mipmap-hdpi/ic_launcher.png deleted file mode 100644 index eb38145c3cd3..000000000000 Binary files a/android/lib/resource/src/main/res/mipmap-hdpi/ic_launcher.png and /dev/null differ diff --git a/android/lib/resource/src/main/res/mipmap-mdpi/ic_launcher.png b/android/lib/resource/src/main/res/mipmap-mdpi/ic_launcher.png deleted file mode 100644 index 13f0df6b3685..000000000000 Binary files a/android/lib/resource/src/main/res/mipmap-mdpi/ic_launcher.png and /dev/null differ diff --git a/android/lib/resource/src/main/res/mipmap-xhdpi/ic_launcher.png b/android/lib/resource/src/main/res/mipmap-xhdpi/ic_launcher.png deleted file mode 100644 index 2534ca44e38e..000000000000 Binary files a/android/lib/resource/src/main/res/mipmap-xhdpi/ic_launcher.png and /dev/null differ diff --git a/android/lib/resource/src/main/res/mipmap-xxhdpi/ic_launcher.png b/android/lib/resource/src/main/res/mipmap-xxhdpi/ic_launcher.png deleted file mode 100644 index b01a56476548..000000000000 Binary files a/android/lib/resource/src/main/res/mipmap-xxhdpi/ic_launcher.png and /dev/null differ diff --git a/android/lib/resource/src/main/res/mipmap-xxxhdpi/ic_launcher.png b/android/lib/resource/src/main/res/mipmap-xxxhdpi/ic_launcher.png deleted file mode 100644 index 063b31017eea..000000000000 Binary files a/android/lib/resource/src/main/res/mipmap-xxxhdpi/ic_launcher.png and /dev/null differ diff --git a/android/lib/resource/src/main/res/mipmap/ic_banner.xml b/android/lib/resource/src/main/res/mipmap/ic_banner.xml new file mode 100644 index 000000000000..7a6010ef373f --- /dev/null +++ b/android/lib/resource/src/main/res/mipmap/ic_banner.xml @@ -0,0 +1,5 @@ + + + + + \ No newline at end of file diff --git a/android/lib/resource/src/main/res/mipmap-anydpi-v26/ic_launcher.xml b/android/lib/resource/src/main/res/mipmap/ic_launcher.xml similarity index 100% rename from android/lib/resource/src/main/res/mipmap-anydpi-v26/ic_launcher.xml rename to android/lib/resource/src/main/res/mipmap/ic_launcher.xml diff --git a/android/lib/talpid/src/main/kotlin/net/mullvad/talpid/ConnectivityListener.kt b/android/lib/talpid/src/main/kotlin/net/mullvad/talpid/ConnectivityListener.kt index 905f59f313a4..edeec9a6fe9d 100644 --- a/android/lib/talpid/src/main/kotlin/net/mullvad/talpid/ConnectivityListener.kt +++ b/android/lib/talpid/src/main/kotlin/net/mullvad/talpid/ConnectivityListener.kt @@ -55,6 +55,10 @@ class ConnectivityListener { connectivityManager.unregisterNetworkCallback(callback) } + // DROID-1401 + // This function has never been used and should most likely be merged into unregister(), + // along with ensuring that the lifecycle of it is correct. + @Suppress("UnusedPrivateMember") private fun finalize() { destroySender(senderAddress) senderAddress = 0L diff --git a/android/lib/talpid/src/main/kotlin/net/mullvad/talpid/TalpidVpnService.kt b/android/lib/talpid/src/main/kotlin/net/mullvad/talpid/TalpidVpnService.kt index cf8a775e13f6..9470c88318b6 100644 --- a/android/lib/talpid/src/main/kotlin/net/mullvad/talpid/TalpidVpnService.kt +++ b/android/lib/talpid/src/main/kotlin/net/mullvad/talpid/TalpidVpnService.kt @@ -74,6 +74,9 @@ open class TalpidVpnService : LifecycleVpnService() { synchronized(this) { activeTunStatus = null } } + // DROID-1407 + // Function is to be cleaned up and lint suppression to be removed. + @Suppress("ReturnCount") private fun createTun(config: TunConfig): CreateTunResult { if (prepare(this) != null) { // VPN permission wasn't granted diff --git a/android/test/build.gradle.kts b/android/test/build.gradle.kts deleted file mode 100644 index 8b137891791f..000000000000 --- a/android/test/build.gradle.kts +++ /dev/null @@ -1 +0,0 @@ - diff --git a/android/test/e2e/src/main/kotlin/net/mullvad/mullvadvpn/test/e2e/misc/SimpleMullvadHttpClient.kt b/android/test/e2e/src/main/kotlin/net/mullvad/mullvadvpn/test/e2e/misc/SimpleMullvadHttpClient.kt index 5e702a2d806e..b5dcc1d64790 100644 --- a/android/test/e2e/src/main/kotlin/net/mullvad/mullvadvpn/test/e2e/misc/SimpleMullvadHttpClient.kt +++ b/android/test/e2e/src/main/kotlin/net/mullvad/mullvadvpn/test/e2e/misc/SimpleMullvadHttpClient.kt @@ -167,7 +167,7 @@ class SimpleMullvadHttpClient(context: Context) { ): JSONArray? { val future = RequestFuture.newFuture() val request = - object : JsonArrayRequest(method, url, null, future, onErrorResponse) { + object : JsonArrayRequest(method, url, body, future, onErrorResponse) { override fun getHeaders(): MutableMap { val headers = HashMap() headers.put("Content-Type", "application/json") diff --git a/android/test/mockapi/src/main/kotlin/net/mullvad/mullvadvpn/test/mockapi/Extensions.kt b/android/test/mockapi/src/main/kotlin/net/mullvad/mullvadvpn/test/mockapi/Extensions.kt index 356cacb97e9b..ddb28e3937a2 100644 --- a/android/test/mockapi/src/main/kotlin/net/mullvad/mullvadvpn/test/mockapi/Extensions.kt +++ b/android/test/mockapi/src/main/kotlin/net/mullvad/mullvadvpn/test/mockapi/Extensions.kt @@ -14,8 +14,7 @@ fun Buffer.getAccountNumber(): String? { return try { JSONObject(readUtf8()).getString("account_number") } catch (ex: JSONException) { - Logger.e("Unable to parse account number") - ex.printStackTrace() + Logger.e("Unable to parse account number", ex) null } } diff --git a/android/test/mockapi/src/main/kotlin/net/mullvad/mullvadvpn/test/mockapi/MockApiDispatcher.kt b/android/test/mockapi/src/main/kotlin/net/mullvad/mullvadvpn/test/mockapi/MockApiDispatcher.kt index a2978808d775..e230152efe2e 100644 --- a/android/test/mockapi/src/main/kotlin/net/mullvad/mullvadvpn/test/mockapi/MockApiDispatcher.kt +++ b/android/test/mockapi/src/main/kotlin/net/mullvad/mullvadvpn/test/mockapi/MockApiDispatcher.kt @@ -32,6 +32,7 @@ class MockApiDispatcher : Dispatcher() { private var cachedPubKeyFromAppUnderTest: String? = null + @Suppress("CyclomaticComplexMethod", "NestedBlockDepth") override fun dispatch(request: RecordedRequest): MockResponse { Logger.d("Request: $request (body=${request.body.peek().readUtf8()})") return when (request.path ?: "") {