diff --git a/app/build.gradle.kts b/app/build.gradle.kts index ea2b9cd..e218a50 100644 --- a/app/build.gradle.kts +++ b/app/build.gradle.kts @@ -5,16 +5,16 @@ import org.jetbrains.kotlin.gradle.dsl.JvmTarget plugins { id("com.android.application") id("kotlin-android") - id("org.jmailen.kotlinter") version "4.4.1" + id("org.jmailen.kotlinter") version "5.1.1" } android { namespace = "com.github.gotify" - compileSdk = 35 + compileSdk = 36 defaultConfig { applicationId = "com.github.gotify" minSdk = 23 - targetSdk = 35 + targetSdk = 36 versionCode = 33 versionName = "2.8.2" testInstrumentationRunner = "androidx.test.runner.AndroidJUnitRunner" @@ -79,15 +79,15 @@ dependencies { val markwonVersion = "4.6.2" val tinylogVersion = "2.7.0" implementation(project(":client")) - implementation("androidx.appcompat:appcompat:1.7.0") + implementation("androidx.appcompat:appcompat:1.7.1") implementation("androidx.core:core-splashscreen:1.0.1") implementation("com.google.android.material:material:1.12.0") - implementation("androidx.constraintlayout:constraintlayout:2.1.4") + implementation("androidx.constraintlayout:constraintlayout:2.2.1") implementation("androidx.swiperefreshlayout:swiperefreshlayout:1.1.0") implementation("androidx.vectordrawable:vectordrawable:1.2.0") implementation("androidx.preference:preference-ktx:1.2.1") - implementation("com.github.cyb3rko:QuickPermissions-Kotlin:1.1.5") + implementation("com.github.cyb3rko:QuickPermissions-Kotlin:1.1.6") implementation("io.coil-kt:coil:$coilVersion") implementation("io.coil-kt:coil-svg:$coilVersion") implementation("io.noties.markwon:core:$markwonVersion") @@ -99,9 +99,9 @@ dependencies { implementation("org.tinylog:tinylog-api-kotlin:$tinylogVersion") implementation("org.tinylog:tinylog-impl:$tinylogVersion") - implementation("com.google.code.gson:gson:2.11.0") - implementation("com.squareup.retrofit2:retrofit:2.11.0") - implementation("org.threeten:threetenbp:1.7.0") + implementation("com.google.code.gson:gson:2.13.1") + implementation("com.squareup.retrofit2:retrofit:3.0.0") + implementation("org.threeten:threetenbp:1.7.1") } configurations { diff --git a/app/src/main/kotlin/com/github/gotify/CoilInstance.kt b/app/src/main/kotlin/com/github/gotify/CoilInstance.kt index ca50977..53e2c1c 100644 --- a/app/src/main/kotlin/com/github/gotify/CoilInstance.kt +++ b/app/src/main/kotlin/com/github/gotify/CoilInstance.kt @@ -3,12 +3,12 @@ package com.github.gotify import android.content.Context import android.graphics.Bitmap import android.graphics.BitmapFactory -import android.graphics.drawable.BitmapDrawable import android.net.Uri import android.util.Base64 import androidx.annotation.DrawableRes import androidx.appcompat.content.res.AppCompatResources import androidx.core.graphics.drawable.toBitmap +import androidx.core.graphics.drawable.toDrawable import coil.ImageLoader import coil.annotation.ExperimentalCoilApi import coil.decode.DataSource @@ -148,7 +148,7 @@ class DataDecoderFactory : Fetcher.Factory { return Fetcher { DrawableResult( - drawable = BitmapDrawable(options.context.resources, bitmap), + drawable = bitmap.toDrawable(options.context.resources), isSampled = false, dataSource = DataSource.MEMORY ) diff --git a/app/src/main/kotlin/com/github/gotify/MissedMessageUtil.kt b/app/src/main/kotlin/com/github/gotify/MissedMessageUtil.kt index 52e1a0f..5597ec9 100644 --- a/app/src/main/kotlin/com/github/gotify/MissedMessageUtil.kt +++ b/app/src/main/kotlin/com/github/gotify/MissedMessageUtil.kt @@ -33,7 +33,7 @@ internal class MissedMessageUtil(private val api: MessageApi) { val filtered = filter(messages, till) result.addAll(filtered) if (messages.size != filtered.size || - messages.size == 0 || + messages.isEmpty() || pagedMessages.paging.next == null ) { break diff --git a/app/src/main/kotlin/com/github/gotify/Settings.kt b/app/src/main/kotlin/com/github/gotify/Settings.kt index 0592a3c..243c6c7 100644 --- a/app/src/main/kotlin/com/github/gotify/Settings.kt +++ b/app/src/main/kotlin/com/github/gotify/Settings.kt @@ -2,6 +2,7 @@ package com.github.gotify import android.content.Context import android.content.SharedPreferences +import androidx.core.content.edit import com.github.gotify.client.model.User internal class Settings(context: Context) { @@ -9,10 +10,10 @@ internal class Settings(context: Context) { val filesDir: String var url: String get() = sharedPreferences.getString("url", "")!! - set(value) = sharedPreferences.edit().putString("url", value).apply() + set(value) = sharedPreferences.edit { putString("url", value) } var token: String? get() = sharedPreferences.getString("token", null) - set(value) = sharedPreferences.edit().putString("token", value).apply() + set(value) = sharedPreferences.edit { putString("token", value) } var user: User? = null get() { val username = sharedPreferences.getString("username", null) @@ -26,22 +27,24 @@ internal class Settings(context: Context) { private set var serverVersion: String get() = sharedPreferences.getString("version", "UNKNOWN")!! - set(value) = sharedPreferences.edit().putString("version", value).apply() + set(value) = sharedPreferences.edit { putString("version", value) } var legacyCert: String? get() = sharedPreferences.getString("cert", null) - set(value) = sharedPreferences.edit().putString("cert", value).commit().toUnit() + set(value) = sharedPreferences.edit(commit = true) { putString("cert", value) }.toUnit() var caCertPath: String? get() = sharedPreferences.getString("caCertPath", null) - set(value) = sharedPreferences.edit().putString("caCertPath", value).commit().toUnit() + set(value) = sharedPreferences + .edit(commit = true) { putString("caCertPath", value) } + .toUnit() var validateSSL: Boolean get() = sharedPreferences.getBoolean("validateSSL", true) - set(value) = sharedPreferences.edit().putBoolean("validateSSL", value).apply() + set(value) = sharedPreferences.edit { putBoolean("validateSSL", value) } var clientCertPath: String? get() = sharedPreferences.getString("clientCertPath", null) - set(value) = sharedPreferences.edit().putString("clientCertPath", value).apply() + set(value) = sharedPreferences.edit { putString("clientCertPath", value) } var clientCertPassword: String? get() = sharedPreferences.getString("clientCertPass", null) - set(value) = sharedPreferences.edit().putString("clientCertPass", value).apply() + set(value) = sharedPreferences.edit { putString("clientCertPass", value) } init { sharedPreferences = context.getSharedPreferences("gotify", Context.MODE_PRIVATE) @@ -61,7 +64,7 @@ internal class Settings(context: Context) { } fun setUser(name: String?, admin: Boolean) { - sharedPreferences.edit().putString("username", name).putBoolean("admin", admin).apply() + sharedPreferences.edit { putString("username", name).putBoolean("admin", admin) } } fun sslSettings(): SSLSettings { diff --git a/app/src/main/kotlin/com/github/gotify/api/Callback.kt b/app/src/main/kotlin/com/github/gotify/api/Callback.kt index 5b0d0f1..15c2b7b 100644 --- a/app/src/main/kotlin/com/github/gotify/api/Callback.kt +++ b/app/src/main/kotlin/com/github/gotify/api/Callback.kt @@ -1,8 +1,6 @@ package com.github.gotify.api import android.app.Activity -import com.github.gotify.api.Callback.ErrorCallback -import com.github.gotify.api.Callback.SuccessCallback import org.tinylog.kotlin.Logger import retrofit2.Call import retrofit2.Response diff --git a/app/src/main/kotlin/com/github/gotify/init/InitializationActivity.kt b/app/src/main/kotlin/com/github/gotify/init/InitializationActivity.kt index ea42ef7..534d477 100644 --- a/app/src/main/kotlin/com/github/gotify/init/InitializationActivity.kt +++ b/app/src/main/kotlin/com/github/gotify/init/InitializationActivity.kt @@ -3,13 +3,13 @@ package com.github.gotify.init import android.Manifest import android.app.AlarmManager import android.content.Intent -import android.net.Uri import android.os.Build import android.os.Bundle import androidx.activity.result.contract.ActivityResultContracts.StartActivityForResult import androidx.annotation.RequiresApi import androidx.appcompat.app.AppCompatActivity import androidx.core.content.ContextCompat +import androidx.core.net.toUri import androidx.core.splashscreen.SplashScreen.Companion.installSplashScreen import com.github.gotify.R import com.github.gotify.Settings @@ -126,7 +126,7 @@ internal class InitializationActivity : AppCompatActivity() { .setPositiveButton(getString(R.string.permissions_dialog_grant)) { _, _ -> Intent( android.provider.Settings.ACTION_REQUEST_SCHEDULE_EXACT_ALARM, - Uri.parse("package:$packageName") + "package:$packageName".toUri() ).apply { activityResultLauncher.launch(this) } diff --git a/app/src/main/kotlin/com/github/gotify/log/LogsActivity.kt b/app/src/main/kotlin/com/github/gotify/log/LogsActivity.kt index 4fc0610..90198dc 100644 --- a/app/src/main/kotlin/com/github/gotify/log/LogsActivity.kt +++ b/app/src/main/kotlin/com/github/gotify/log/LogsActivity.kt @@ -2,7 +2,6 @@ package com.github.gotify.log import android.content.ClipData import android.content.ClipboardManager -import android.content.Context import android.os.Bundle import android.os.Handler import android.os.Looper @@ -73,7 +72,7 @@ internal class LogsActivity : AppCompatActivity() { R.id.action_copy_logs -> { val content = binding.logContent val clipboardManager = - getSystemService(Context.CLIPBOARD_SERVICE) as ClipboardManager + getSystemService(CLIPBOARD_SERVICE) as ClipboardManager val clipData = ClipData.newPlainText("GotifyLog", content.text.toString()) clipboardManager.setPrimaryClip(clipData) Utils.showSnackBar(this, getString(R.string.logs_copied)) diff --git a/app/src/main/kotlin/com/github/gotify/login/LoginActivity.kt b/app/src/main/kotlin/com/github/gotify/login/LoginActivity.kt index e874c49..df31e7c 100644 --- a/app/src/main/kotlin/com/github/gotify/login/LoginActivity.kt +++ b/app/src/main/kotlin/com/github/gotify/login/LoginActivity.kt @@ -215,7 +215,7 @@ internal class LoginActivity : AppCompatActivity() { try { resultLauncher.launch(Intent.createChooser(intent, getString(descriptionId))) - } catch (e: ActivityNotFoundException) { + } catch (_: ActivityNotFoundException) { // case for user not having a file browser installed Utils.showSnackBar(this, getString(R.string.please_install_file_browser)) } diff --git a/app/src/main/kotlin/com/github/gotify/messages/IntentUrlDialogActivity.kt b/app/src/main/kotlin/com/github/gotify/messages/IntentUrlDialogActivity.kt index a2bebcc..1dc5e68 100644 --- a/app/src/main/kotlin/com/github/gotify/messages/IntentUrlDialogActivity.kt +++ b/app/src/main/kotlin/com/github/gotify/messages/IntentUrlDialogActivity.kt @@ -1,9 +1,9 @@ package com.github.gotify.messages import android.content.Intent -import android.net.Uri import android.os.Bundle import androidx.appcompat.app.AppCompatActivity +import androidx.core.net.toUri import com.github.gotify.databinding.ActivityDialogIntentUrlBinding internal class IntentUrlDialogActivity : AppCompatActivity() { @@ -18,7 +18,7 @@ internal class IntentUrlDialogActivity : AppCompatActivity() { binding.openButton.setOnClickListener { finish() Intent(Intent.ACTION_VIEW).apply { - data = Uri.parse(intentUrl) + data = intentUrl?.toUri() flags = Intent.FLAG_ACTIVITY_NEW_TASK startActivity(this) } diff --git a/app/src/main/kotlin/com/github/gotify/messages/MessagesActivity.kt b/app/src/main/kotlin/com/github/gotify/messages/MessagesActivity.kt index 1e211cc..145928d 100644 --- a/app/src/main/kotlin/com/github/gotify/messages/MessagesActivity.kt +++ b/app/src/main/kotlin/com/github/gotify/messages/MessagesActivity.kt @@ -1,5 +1,6 @@ package com.github.gotify.messages +import android.annotation.SuppressLint import android.app.NotificationManager import android.content.BroadcastReceiver import android.content.Context @@ -8,7 +9,6 @@ import android.content.IntentFilter import android.graphics.Canvas import android.graphics.drawable.ColorDrawable import android.graphics.drawable.Drawable -import android.net.Uri import android.os.Build import android.os.Bundle import android.view.Menu @@ -21,6 +21,8 @@ import androidx.appcompat.app.ActionBarDrawerToggle import androidx.appcompat.app.AppCompatActivity import androidx.core.content.ContextCompat import androidx.core.graphics.drawable.DrawableCompat +import androidx.core.graphics.drawable.toDrawable +import androidx.core.net.toUri import androidx.core.view.GravityCompat import androidx.drawerlayout.widget.DrawerLayout.SimpleDrawerListener import androidx.lifecycle.ViewModelProvider @@ -188,7 +190,7 @@ internal class MessagesActivity : } private fun openDocumentation() { - val browserIntent = Intent(Intent.ACTION_VIEW, Uri.parse("https://gotify.net/docs/pushmsg")) + val browserIntent = Intent(Intent.ACTION_VIEW, "https://gotify.net/docs/pushmsg".toUri()) startActivity(browserIntent) } @@ -317,6 +319,7 @@ internal class MessagesActivity : if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.TIRAMISU) { registerReceiver(receiver, filter, RECEIVER_EXPORTED) } else { + @SuppressLint("UnspecifiedRegisterReceiverFlag") registerReceiver(receiver, filter) } launchCoroutine { @@ -409,7 +412,7 @@ internal class MessagesActivity : icon = DrawableCompat.wrap(drawable.mutate()) DrawableCompat.setTint(icon!!, iconColorId) } - background = ColorDrawable(backgroundColorId) + background = backgroundColorId.toDrawable() } override fun onMove( diff --git a/app/src/main/kotlin/com/github/gotify/service/WebSocketService.kt b/app/src/main/kotlin/com/github/gotify/service/WebSocketService.kt index 60a37dd..719d7c9 100644 --- a/app/src/main/kotlin/com/github/gotify/service/WebSocketService.kt +++ b/app/src/main/kotlin/com/github/gotify/service/WebSocketService.kt @@ -10,12 +10,12 @@ import android.content.pm.ServiceInfo import android.graphics.Color import android.net.ConnectivityManager import android.net.Network -import android.net.Uri import android.os.Build import android.os.IBinder import androidx.annotation.RequiresApi import androidx.core.app.NotificationCompat import androidx.core.content.ContextCompat +import androidx.core.net.toUri import com.github.gotify.BuildConfig import com.github.gotify.CoilInstance import com.github.gotify.MarkwonFactory @@ -331,7 +331,7 @@ internal class WebSocketService : Service() { if (url != null) { intent = Intent(Intent.ACTION_VIEW) - intent.data = Uri.parse(url) + intent.data = url.toUri() } else { intent = Intent(this, MessagesActivity::class.java) } diff --git a/app/src/main/kotlin/com/github/gotify/settings/SettingsActivity.kt b/app/src/main/kotlin/com/github/gotify/settings/SettingsActivity.kt index a4d32ce..f341270 100644 --- a/app/src/main/kotlin/com/github/gotify/settings/SettingsActivity.kt +++ b/app/src/main/kotlin/com/github/gotify/settings/SettingsActivity.kt @@ -5,13 +5,13 @@ import android.content.DialogInterface import android.content.Intent import android.content.SharedPreferences import android.content.SharedPreferences.OnSharedPreferenceChangeListener -import android.net.Uri import android.os.Build import android.os.Bundle import android.provider.Settings import android.view.MenuItem import android.view.View import androidx.appcompat.app.AppCompatActivity +import androidx.core.net.toUri import androidx.preference.ListPreference import androidx.preference.ListPreferenceDialogFragmentCompat import androidx.preference.Preference @@ -128,7 +128,7 @@ internal class SettingsActivity : private fun openSystemAlertWindowPermissionPage(): Boolean { Intent( Settings.ACTION_MANAGE_OVERLAY_PERMISSION, - Uri.parse("package:${requireContext().packageName}") + "package:${requireContext().packageName}".toUri() ).apply { startActivity(this) } diff --git a/build.gradle.kts b/build.gradle.kts index 306ac65..bb26ca7 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -3,8 +3,8 @@ import java.io.File import java.net.URI plugins { - id("com.android.application") version "8.7.1" apply false - id("org.jetbrains.kotlin.android") version "2.0.20" apply false + id("com.android.application") version "8.11.0" apply false + id("org.jetbrains.kotlin.android") version "2.2.0" apply false id("org.hidetake.swagger.generator") version "2.19.2" } diff --git a/gradle/wrapper/gradle-wrapper.jar b/gradle/wrapper/gradle-wrapper.jar index a4b76b9..1b33c55 100644 Binary files a/gradle/wrapper/gradle-wrapper.jar and b/gradle/wrapper/gradle-wrapper.jar differ diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties index fb602ee..3735f26 100644 --- a/gradle/wrapper/gradle-wrapper.properties +++ b/gradle/wrapper/gradle-wrapper.properties @@ -1,7 +1,7 @@ distributionBase=GRADLE_USER_HOME distributionPath=wrapper/dists -distributionSha256Sum=31c55713e40233a8303827ceb42ca48a47267a0ad4bab9177123121e71524c26 -distributionUrl=https\://services.gradle.org/distributions/gradle-8.10.2-bin.zip +distributionSha256Sum=7197a12f450794931532469d4ff21a59ea2c1cd59a3ec3f89c035c3c420a6999 +distributionUrl=https\://services.gradle.org/distributions/gradle-8.14.2-bin.zip networkTimeout=10000 validateDistributionUrl=true zipStoreBase=GRADLE_USER_HOME diff --git a/gradlew b/gradlew index f5feea6..23d15a9 100755 --- a/gradlew +++ b/gradlew @@ -86,8 +86,7 @@ done # shellcheck disable=SC2034 APP_BASE_NAME=${0##*/} # Discard cd standard output in case $CDPATH is set (https://github.com/gradle/gradle/issues/25036) -APP_HOME=$( cd -P "${APP_HOME:-./}" > /dev/null && printf '%s -' "$PWD" ) || exit +APP_HOME=$( cd -P "${APP_HOME:-./}" > /dev/null && printf '%s\n' "$PWD" ) || exit # Use the maximum available, or set MAX_FD != -1 to use that value. MAX_FD=maximum @@ -115,7 +114,7 @@ case "$( uname )" in #( NONSTOP* ) nonstop=true ;; esac -CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar +CLASSPATH="\\\"\\\"" # Determine the Java command to use to start the JVM. @@ -206,7 +205,7 @@ fi DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"' # Collect all arguments for the java command: -# * DEFAULT_JVM_OPTS, JAVA_OPTS, JAVA_OPTS, and optsEnvironmentVar are not allowed to contain shell fragments, +# * DEFAULT_JVM_OPTS, JAVA_OPTS, and optsEnvironmentVar are not allowed to contain shell fragments, # and any embedded shellness will be escaped. # * For example: A user cannot expect ${Hostname} to be expanded, as it is an environment variable and will be # treated as '${Hostname}' itself on the command line. @@ -214,7 +213,7 @@ DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"' set -- \ "-Dorg.gradle.appname=$APP_BASE_NAME" \ -classpath "$CLASSPATH" \ - org.gradle.wrapper.GradleWrapperMain \ + -jar "$APP_HOME/gradle/wrapper/gradle-wrapper.jar" \ "$@" # Stop when "xargs" is not available. diff --git a/gradlew.bat b/gradlew.bat index 9d21a21..db3a6ac 100644 --- a/gradlew.bat +++ b/gradlew.bat @@ -70,11 +70,11 @@ goto fail :execute @rem Setup the command line -set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar +set CLASSPATH= @rem Execute Gradle -"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %* +"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" -jar "%APP_HOME%\gradle\wrapper\gradle-wrapper.jar" %* :end @rem End local scope for the variables with windows NT shell