diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index 9f3d1f0c6b1dfa1a3a926d2d8ffa9ce477787464..aa2dc51012dce0956644a55d1288dc8668adf85e 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -1,105 +1,83 @@ -image: "registry.gitlab.e.foundation/e/os/docker-android-apps-cicd:latest" - stages: - - update - - qa - - build + - lint - test + - build # By default load dev keys. variables: MAPBOX_KEY: $MAPBOX_KEY_DEV SENTRY_DSN: $SENTRY_DSN -workflow: - rules: - - if: '$CI_PIPELINE_SOURCE == "merge_request_event"' - - if: '$CI_COMMIT_BRANCH && $CI_OPEN_MERGE_REQUESTS && $CI_PIPELINE_SOURCE == "push"' - when: never - - if: '$CI_COMMIT_BRANCH' - -before_script: - - export GRADLE_USER_HOME=$(pwd)/.gradle - - chmod +x ./gradlew - -cache: - key: ${CI_PROJECT_ID} - paths: - - .gradle/ - -nightly-tasks: - stage: update - script: - - ./gradlew dependencyUpdates - rules: - - if: '$CI_PIPELINE_SOURCE == "schedule"' - artifacts: +default: + image: "registry.gitlab.e.foundation/e/os/docker-android-apps-cicd:latest" + before_script: + - export GRADLE_USER_HOME=$(pwd)/.gradle + - chmod +x ./gradlew + #tags: + # - android + cache: + key: ${CI_PROJECT_ID} paths: - - build/dependencyUpdates + - .gradle/ -quality-analysis: - stage: qa +lint: + stage: lint script: - - ./gradlew spotlessCheck lint + - ./gradlew spotlessCheck rules: - - if: '$CI_PIPELINE_SOURCE == "schedule"' - when: never - - if: '$CI_COMMIT_BRANCH == "main"' - when: never - - if: '$CI_COMMIT_REF_PROTECTED == "true"' - when: never - - if: '$CI_PIPELINE_SOURCE == "merge_request_event"' - when: never - - when: always + - if: $CI_PIPELINE_SOURCE == "merge_request_event" + when: on_success + - if: $CI_COMMIT_BRANCH == "main" + when: on_success + +# No unit tests yet. +#unit-test: +# stage: test +# script: +# - ./gradlew :testDebugUnitTest +# rules: +# - if: '$CI_PIPELINE_SOURCE == "merge_request_event"' +# when: on_success +# - if: $CI_COMMIT_BRANCH == "main" +# when: on_success +# artifacts: +# paths: +# - ./**/build/reports/tests/testDebugUnitTest build-debug: stage: build script: - - ./gradlew :app:assembleDebug + - ./gradlew :app:assembleEosDebug rules: - - if: '$CI_PIPELINE_SOURCE == "schedule"' - when: never - - if: '$CI_COMMIT_BRANCH == "main"' - when: never - - if: '$CI_COMMIT_REF_PROTECTED == "true"' - when: never - - if: '$CI_PIPELINE_SOURCE == "merge_request_event"' - when: never - - when: on_success + - if: $CI_PIPELINE_SOURCE == "merge_request_event" + when: on_success artifacts: paths: - app/build/outputs/apk -test-debug: +# Check that the release build works, but don't keep the artifacts. +build-release-test: stage: test script: - - ./gradlew test --stacktrace + - ./gradlew :app:assembleEosRelease rules: - - if: '$CI_PIPELINE_SOURCE == "schedule"' - when: never - - if: '$CI_PIPELINE_SOURCE == "merge_request_event" && $CI_MERGE_REQUEST_TARGET_BRANCH_NAME == "main"' - when: always - - if: '$CI_COMMIT_BRANCH == "main"' - when: never - - if: '$CI_COMMIT_REF_PROTECTED == "true"' - when: never - - if: '$CI_PIPELINE_SOURCE == "merge_request_event"' - when: never - - when: on_success - artifacts: - paths: - - ./**/build/reports/tests/testDebugUnitTest + - if: $CI_COMMIT_BRANCH == "main" + variables: + MAPBOX_KEY: $MAPBOX_KEY_PROD + when: on_success build-e-release: stage: build script: - ./gradlew :app:assembleEosRelease rules: - - if: '$CI_COMMIT_REF_PROTECTED == "true" && $CI_COMMIT_TAG =~ /^eOS-/' + - if: $CI_PIPELINE_SOURCE == "merge_request_event" + when: never + - if: $CI_COMMIT_REF_PROTECTED == "true" && $CI_COMMIT_TAG =~ /^eOS-v\d+\.\d+(\.\d+)$/ variables: MAPBOX_KEY: $MAPBOX_KEY_PROD - when: always - - if: '$CI_COMMIT_REF_PROTECTED == "true"' + when: on_success + - if: $CI_COMMIT_REF_PROTECTED == "true" variables: MAPBOX_KEY: $MAPBOX_KEY_PROD when: manual diff --git a/DEVELOPMENT.md b/DEVELOPMENT.md index 88354c646b27dc91f2736940bf133b5777ab7c1c..bdc4507465ce8d5bf260507ce1ab0e48541ec040 100644 --- a/DEVELOPMENT.md +++ b/DEVELOPMENT.md @@ -2,58 +2,73 @@ This guide contains development related information to help a developer in getting better understanding of project structure. ## Architecture -The architecture of AdvancedPrivacy is based on [clean architecture](https://blog.cleancoder.com/uncle-bob/2012/08/13/the-clean-architecture.html). For presentation layer, we use [Model-View-Intent](http://hannesdorfmann.com/android/model-view-intent/) design pattern which is a unidirectional reactive flow pattern. We use it in conjunction to ViewModel to make our features lifecycle aware. Our android app is having single activity multiple fragments. +The architecture of AdvancedPrivacy is based on [clean architecture](https://blog.cleancoder.com/uncle-bob/2012/08/13/the-clean-architecture.html). For presentation layer, we use a MVVM design pattern, +with a unique StateFlow for each screen to simplify coherence. Our android app is having single activity multiple fragments, using Android Navigation component. + +The project has 2 flavors : + - eOS: for /e/OS devices, with OS specific signatures, system priviledges and persistent flag + - standalone: for app's stores, without any priviledges. + +Most of the differences between the 2 flavors are separated in distinct modules like : +- permissioneos / permissionstandalone +- trackersserviceseos / trackersservicesstandalone ### Clean Architecture -Clean architecture is the building block of AdvancedPrivacy. This architecture is based on the following principles: -1. **Independent of Frameworks**. The architecture does not depend on the existence of some library of feature laden software. This allows you to use such frameworks as tools, rather than having to cram your system into their limited constraints. -2. **Testable**. The business rules can be tested without the UI, Database, Web Server, or any other external element. -3. **Independent of UI**. The UI can change easily, without changing the rest of the system. A Web UI could be replaced with a console UI, for example, without changing the business rules. -4. **Independent of Database**. You can swap out Oracle or SQL Server, for Mongo, BigTable, CouchDB, or something else. Your business rules are not bound to the database. -5. **Independent of any external agency**. In fact your business rules simply don’t know anything at all about the outside world. - +Clean architecture is the building block of AdvancedPrivacy. It is now a common way of organizing project, +so it helps newcomers. It gives a framework to apply Single Responsibility Principle, having a testable project +and keep files with a decent length. + + +The detailed file tree: + +**Domain** + +- entities : data classes, with no logic +- usecases : most of the logic, with no external dependencies + +**LocalRepositories** + +Repositories of data, that use local datasources, like sqlite database, sharedpreferences or in memory objects. + +**NetworkRepositories** + +Repositories of data, which fetch and push data to some remote servers. -### Model-View-Intent +**InterfaceAdapters** - +All the glue to abstract Android framework (and also all it's supported versions) from the domain layer. -MVI is used at the presentation layer of clean architecture. It is very much similar to [Redux](https://redux.js.org/) in terms of implementation and working. It has three main components. -- **View**: This is where activities, fragments and other android components live. It is responsible for publishing user intent/actions to the model and rendering the state returned by the model. In AdvancedPrivacy, it is just an interface which is implemented by android components. -- **Intent**: In context of our app, we call them actions. These are simple data classes having any extra payload like inputs, ids etc. -- **Model (data layer at presentation level)**: This is responsible for processing the actions, communicating with domain use-cases and mutating the state of the model. It acts as a Store from redux but for our use case, we call it a **Feature**. +- services: Android Services +- broadcastreceivers: Android Broadcast Receivers +- Android Interfaces : abstraction of framework interfaces, like private and priviledges specific API. -#### Flow-MVI in Privacy Central App -In this app, we have implemented MVI using [Kotlin Flow](https://kotlinlang.org/docs/flow.html). +**UI** +All the UI related code, with MVVM pattern. - +## Good practices -Elements of a feature: -1. **Action**: The exhaustive list of user actions for a feature. -2. **State**: Simple POJO (kotlin data class) representing various UI states of the application. -3. **SingleEventProducer**: This is a function which is invoked by the reducer to publish single events (that can/should only be consumed once like displaying toast, snackbar message or sending an analytics event). This function takes action, effect, current state as input and it returns a `SingleEvent`. By default this function is null for any Feature. +### Use hidden-apis-stubs -### Architecture Overview of AdvancedPrivacy App +Reflexion is avoided. We use an [hidden-apis-stub](./permissionseos/libs/hidden-apis-stub) project to make Android hidden APIs available for development and compilations. +Each stubed API should be documented with link to the source code they stub, for each targeted Android version. -![](art/privacycentral-arch.png) +### Use Coroutines and Flow -Looking at the diagram from right to left: -1. **Database, Preferences and API Helpers**: These are a set of classes with very specific responsibilities for each of them. They can perform some business logic, communicate with the database or make a call to third party API. These classes are implementation of abstract gateways and interfaces (see below). -2. **Abstract Gateways and Interfaces**: An abstraction layer that sits between repositories and framework implementations. The objective of this layer is to keep repositories independent from framework (like databases). -3. **Respositoy Implementation**: These classes provide the implementation of abstract repository defined in the domain. -4. **Repository**: They are the core part of our domain. Each repository is a just an interface whose implementation is provided by the data layer. -5. **Usecase/Interactors/Observers**: The act as the bridge between the presentation layer and data layer. -6. **Entities**: These are business objects for the application. They encapsulate the most general and high-level rules. They are the least likely to change when something external changes. -7. **Features**: MVI specific model (discussed above). -8. **ViewModel**: arch-component lifecycle aware viewmodel. -9. **Views**: Android high level components like activities, fragments, etc. +We use Coroutines and Flow for asynchronous tasks. The previous technologies (RxJava, LiveData) to do that are not welcome :) + +### Use Koin for dependency injection + +The project use Koin for "DI". It's flexibility is helpful to cleanly separate the flavored modules. + + +## OrbotService development and maintenance + +The IpScrambling relies on a fork of OrbotService, which is a module of Orbot, the Tor proxy for Android. It lays as a submodule to help fork upgrade and patching. More here: [orbotservice/README.md](orbotservice/README.md) ## Code Quality and Style -This project integrates a combination of unit tests, functional test and code styling tools. -To run **unit** tests on your machine: -``` -./gradlew test -``` + +It use ktlint through spotless. The specific rules are defined in [.editorconfig](./.editorconfig). To run code style check and formatting tool: ``` @@ -61,14 +76,15 @@ To run code style check and formatting tool: ./gradlew spotlessApply ``` +If spotlessApply fails, let's discuss to relax the ktllint rules. + ## State-of-The-Art -The project currently doesn't have exactly the same mentioned structure as it is just a POC and will be improved. + +This document present the objectives for the project, some area may still have legacy code organizations. ### Todo/Improvements - [ ] Add unit tests and code coverage. -- [ ] Implement Hilt DI. # References 1. [Kotlin Flow](https://kotlinlang.org/docs/flow.html) -2. [MVI](https://hannesdorfmann.com/android/mosby3-mvi-1/) -4. [Clean Architecture](https://blog.cleancoder.com/uncle-bob/2012/08/13/the-clean-architecture.html) \ No newline at end of file +4. [Clean Architecture](https://blog.cleancoder.com/uncle-bob/2012/08/13/the-clean-architecture.html) diff --git a/README.md b/README.md index 57c85a5835ab77aa1b5ee74b5acea6bf0abd8905..a96700c0ae3d8a5a295e0f3e43d1b1486a65dbae 100644 --- a/README.md +++ b/README.md @@ -8,8 +8,7 @@ The following features are currently part of AdvancedPrivacy app. 1. Centralized overview dashboard. 2. Fake location. 3. Hiding IP address. -4. Manage granular permissions. -5. Control trackers across apps. +4. Control trackers across apps. # Technologies - Kotlin as main language @@ -17,16 +16,11 @@ The following features are currently part of AdvancedPrivacy app. - AndroidX (core-ktx, fragment-ktx, and lifecycle etc.) - Google Material Design component for UI elements - Timber for logging -- Room for database (may use datastore too) -- Hilt for DI -- MapBox for map support +- MapLibre for map support - LeakCanary for keeping an eye on memory leaks. -- Junit for unit testing -- Espresso for integration testing. -- # Flavours -This app comes in two flavours, one for /e/OS and second one for other android (where app doesn't have system access). For more information refer to [Architecture Guide](DEVELOPMENT.md) +This app comes in two flavours, one for /e/OS and second one for other android (where app doesn't have system access) # Testing Need to write test and add code coverage. @@ -37,12 +31,12 @@ Need to write test and add code coverage. You can use any latest stable version of android studio to be able to build this app. ## Supported Versions -- Minimum SDK: 24 (Android N) -- Compile SDK: 30 (Android R) -- Target SDK: 30 (Android R) +- Minimum SDK: 26 (Android O) +- Compile SDK: 34 (Android U) +- Target SDK: 33 (Android T) ## API Keys -This project uses [Sentry](https://sentry.io) for telemetry and crash reports, [Mapbox](https://docs.mapbox.com/android/maps/guides/install/) sdk for displaying maps. To download and use the mapbox sdk, you need to supply API key and secret and set them as follows: +This project uses [Sentry](https://sentry.io) for telemetry and crash reports, [Mapbox](https://docs.mapbox.com/android/maps/guides/install/) sdk as maps tiles provider. To compile the project, you need to set keys for them: ### For local build You can set them in local.properties @@ -89,18 +83,6 @@ then run the build as usual This won't include advanced privacy, you still need to build the app. - -This app requires different modules that must be built indivually and pushed to a local maven repository or our gitlab - -modules must be build and deployed in the following order: - -- privacymodule-api : - - ./gradlew :privacymodule-api:assembleRelease - - ./gradlew --console=verbose publishToMavenLocal // To make it available locally for dev. - - ./gradlew --console=verbose publish // To publish it on gitlab for release. -- [privacymodule-tor](../../../e_privacycentral_privacymoduletor) -- [app] - ## Build If you'd like to build AdvancedPrivacy locally, you should be able to just clone and build with no issues. @@ -171,6 +153,7 @@ Please refer to [Development Guide](DEVELOPMENT.md) for detailed instructions ab # License ``` +Copyright (C) 2023 MURENA SAS Copyright (C) 2021 ECORP This program is free software: you can redistribute it and/or modify diff --git a/app/build.gradle b/app/build.gradle index a10ead1cc061f636449224c82c3efc399c7a5502..263e0e70b5b2ca062f8a48c69a876039c3a3a9a5 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -126,8 +126,8 @@ android { } compileOptions { - sourceCompatibility JavaVersion.VERSION_1_8 - targetCompatibility JavaVersion.VERSION_1_8 + sourceCompatibility JavaVersion.VERSION_17 + targetCompatibility JavaVersion.VERSION_17 } buildFeatures { @@ -138,6 +138,7 @@ android { lintOptions { disable 'MissingTranslation' } + namespace 'foundation.e.advancedprivacy' } dependencies { diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index 246b7c0d318a6a3f76057e76d9f75db78ea1cb99..6be3dbc00a2a24b8a15f38d80863c4d18629955c 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -16,9 +16,7 @@ along with this program. If not, see . --> + xmlns:tools="http://schemas.android.com/tools"> diff --git a/app/src/main/java/foundation/e/advancedprivacy/common/NavToolbarFragment.kt b/app/src/main/java/foundation/e/advancedprivacy/common/NavToolbarFragment.kt index cdb6a4c4447f3f2e06745acde2c581dfe27ac2e7..93d77837ec61586dff3fbc2c39ec7ddc9fa476c5 100644 --- a/app/src/main/java/foundation/e/advancedprivacy/common/NavToolbarFragment.kt +++ b/app/src/main/java/foundation/e/advancedprivacy/common/NavToolbarFragment.kt @@ -42,14 +42,16 @@ abstract class NavToolbarFragment(@LayoutRes contentLayoutId: Int) : Fragment(co override fun onViewCreated(view: View, savedInstanceState: Bundle?) { super.onViewCreated(view, savedInstanceState) - setupToolbar(view.findViewById(R.id.toolbar)) + view.findViewById(R.id.toolbar).let { toolbar -> + toolbar.title = getTitle() + toolbar.setNavigationOnClickListener { + onNavigateUp() + } + } } - open fun setupToolbar(toolbar: MaterialToolbar) { - toolbar.title = getTitle() - toolbar.setNavigationOnClickListener { - requireActivity().onBackPressed() - } + open fun onNavigateUp(): Boolean { + return findNavController().navigateUp() } fun getToolbar(): MaterialToolbar? = view?.findViewById(R.id.toolbar) diff --git a/app/src/main/java/foundation/e/advancedprivacy/common/WarningDialog.kt b/app/src/main/java/foundation/e/advancedprivacy/common/WarningDialog.kt index 9dbfea97c3a82a50fcb6e4a65b20f5b066965345..60747e36db34cdca29a5f86ce252b67eb6306eb7 100644 --- a/app/src/main/java/foundation/e/advancedprivacy/common/WarningDialog.kt +++ b/app/src/main/java/foundation/e/advancedprivacy/common/WarningDialog.kt @@ -22,6 +22,7 @@ import android.app.Activity import android.content.Context import android.content.Intent import android.graphics.drawable.ColorDrawable +import android.os.Build import android.os.Bundle import android.view.View import android.widget.CheckBox @@ -77,7 +78,12 @@ class WarningDialog : AppCompatActivity() { window.setBackgroundDrawable(ColorDrawable(0)) feature = try { - intent.getParcelableExtra(PARAM_FEATURE)!! + if (Build.VERSION.SDK_INT > Build.VERSION_CODES.TIRAMISU) { + intent.getParcelableExtra(PARAM_FEATURE, MainFeatures::class.java)!! + } else { + @Suppress("DEPRECATION") + intent.getParcelableExtra(PARAM_FEATURE)!! + } } catch (e: Exception) { Timber.e(e, "Missing mandatory activity parameter") finish() diff --git a/app/src/main/java/foundation/e/advancedprivacy/features/dashboard/DashboardFragment.kt b/app/src/main/java/foundation/e/advancedprivacy/features/dashboard/DashboardFragment.kt index 56cf81f63ed96788a81d95453872a4d3ae1edd2b..b22e67f44cd54bcdf059f2e84465460acc76262c 100644 --- a/app/src/main/java/foundation/e/advancedprivacy/features/dashboard/DashboardFragment.kt +++ b/app/src/main/java/foundation/e/advancedprivacy/features/dashboard/DashboardFragment.kt @@ -138,6 +138,11 @@ class DashboardFragment : NavToolbarFragment(R.layout.fragment_dashboard) { } } + override fun onNavigateUp(): Boolean { + requireActivity().finish() + return true + } + private fun render(state: DashboardState) { binding.stateLabel.text = getString( when (state.quickPrivacyState) { diff --git a/art/AbstractMVI.png b/art/AbstractMVI.png deleted file mode 100644 index eeca62cb35e2af4b60cad6981c2149ae95dd5428..0000000000000000000000000000000000000000 Binary files a/art/AbstractMVI.png and /dev/null differ diff --git a/art/CleanArchitecture.jpg b/art/CleanArchitecture.jpg deleted file mode 100644 index 3cd44fb58d87e5fd2fe1f0a75533f132bb163c61..0000000000000000000000000000000000000000 Binary files a/art/CleanArchitecture.jpg and /dev/null differ diff --git a/art/MVI-Feature.png b/art/MVI-Feature.png deleted file mode 100644 index de85c3db1b6b8721e618515eb8908c5e1cdf10ce..0000000000000000000000000000000000000000 Binary files a/art/MVI-Feature.png and /dev/null differ diff --git a/art/privacycentral-arch.png b/art/privacycentral-arch.png deleted file mode 100644 index 93f26bc2faf657142741bf3a4408875234572c50..0000000000000000000000000000000000000000 Binary files a/art/privacycentral-arch.png and /dev/null differ diff --git a/build.gradle b/build.gradle index 1f0ab1691f2b876e203cefd0249ff1020088f095..50427ef240f1ae0e4e01af1a4e8509b35d4b702b 100644 --- a/build.gradle +++ b/build.gradle @@ -16,15 +16,12 @@ * along with this program. If not, see . */ -import foundation.e.advancedprivacy.buildsrc.DependencyUpdates -import foundation.e.advancedprivacy.buildsrc.ReleaseType - // Top-level build file where you can add configuration options common to all sub-projects/modules. buildscript { ext.buildConfig = [ - 'compileSdk': 31, + 'compileSdk': 34, 'minSdk' : 26, - 'targetSdk' : 31, + 'targetSdk' : 33, 'version' : [ 'major': 1, 'minor': 19, @@ -61,11 +58,13 @@ allprojects { kotlinOptions { freeCompilerArgs = ['-Xjvm-default=all', '-opt-in=kotlin.RequiresOptIn'] - jvmTarget = "1.8" + jvmTarget = "17" } } } + + subprojects { apply plugin: 'com.diffplug.spotless' spotless { @@ -92,31 +91,12 @@ subprojects { allWarningsAsErrors = true freeCompilerArgs += "-opt-in=kotlinx.coroutines.ExperimentalCoroutinesApi" - // Set JVM target to 1.8 - jvmTarget = "1.8" + jvmTarget = "17" } } } -/** - * Update dependencyUpdates task to reject versions which are more 'unstable' than our - * current version. - */ -tasks.named("dependencyUpdates").configure { - rejectVersionIf { - def current = DependencyUpdates.versionToRelease(it.currentVersion) - // If we're using a SNAPSHOT, ignore since we must be doing so for a reason. - if (current == ReleaseType.SNAPSHOT) return true - - // Otherwise we reject if the candidate is more 'unstable' than our version - def candidate = DependencyUpdates.versionToRelease(it.candidate.version) - return candidate.isLessStableThan(current) - } -} - Object propOrDef(String propertyName, Object defaultValue) { def propertyValue = project.properties[propertyName] return propertyValue != null ? propertyValue : defaultValue } - -apply from: file('gradle/dependencyGraph.gradle') diff --git a/buildSrc/build.gradle.kts b/buildSrc/build.gradle.kts deleted file mode 100644 index 445e21f767b47d0d6d4198770c581bb9d0ea0083..0000000000000000000000000000000000000000 --- a/buildSrc/build.gradle.kts +++ /dev/null @@ -1,7 +0,0 @@ -repositories { - jcenter() -} - -plugins { - `kotlin-dsl` -} \ No newline at end of file diff --git a/buildSrc/src/main/java/foundation/e/advancedprivacy/buildsrc/DependencyUpdates.kt b/buildSrc/src/main/java/foundation/e/advancedprivacy/buildsrc/DependencyUpdates.kt deleted file mode 100644 index 1f233d5253b1276e185f8ac5d48789ed80d32882..0000000000000000000000000000000000000000 --- a/buildSrc/src/main/java/foundation/e/advancedprivacy/buildsrc/DependencyUpdates.kt +++ /dev/null @@ -1,42 +0,0 @@ -package foundation.e.advancedprivacy.buildsrc - -enum class ReleaseType(private val level: Int) { - SNAPSHOT(0), - DEV(1), - ALPHA(10), - BETA(20), - RC(60), - RELEASE(100); - - fun isEqualOrMoreStableThan(other: ReleaseType): Boolean = level >= other.level - - fun isLessStableThan(other: ReleaseType): Boolean = level < other.level -} - -object DependencyUpdates { - private val stableKeywords = arrayOf("RELEASE", "FINAL", "GA") - private val releaseRegex = "^[0-9,.v-]+(-r)?$".toRegex(RegexOption.IGNORE_CASE) - private val rcRegex = releaseKeywordRegex("rc") - private val betaRegex = releaseKeywordRegex("beta") - private val alphaRegex = releaseKeywordRegex("alpha") - private val devRegex = releaseKeywordRegex("dev") - - @JvmStatic - fun versionToRelease(version: String): ReleaseType { - val stableKeyword = stableKeywords.any { version.toUpperCase().contains(it) } - if (stableKeyword) return ReleaseType.RELEASE - - return when { - releaseRegex.matches(version) -> ReleaseType.RELEASE - rcRegex.matches(version) -> ReleaseType.RC - betaRegex.matches(version) -> ReleaseType.BETA - alphaRegex.matches(version) -> ReleaseType.ALPHA - devRegex.matches(version) -> ReleaseType.DEV - else -> ReleaseType.SNAPSHOT - } - } - - private fun releaseKeywordRegex(keyword: String): Regex { - return "^[0-9,.v-]+(-$keyword[0-9]*)$".toRegex(RegexOption.IGNORE_CASE) - } -} \ No newline at end of file diff --git a/core/build.gradle b/core/build.gradle index 3b5234df40a55fd0544564716fd462a3642f04f6..e9bf2d4b46a803ea105d6a2108f857e9950fcf43 100644 --- a/core/build.gradle +++ b/core/build.gradle @@ -43,9 +43,10 @@ android { } compileOptions { - sourceCompatibility JavaVersion.VERSION_1_8 - targetCompatibility JavaVersion.VERSION_1_8 + sourceCompatibility JavaVersion.VERSION_17 + targetCompatibility JavaVersion.VERSION_17 } + namespace 'foundation.e.advancedprivacy.core' } dependencies { diff --git a/core/src/main/AndroidManifest.xml b/core/src/main/AndroidManifest.xml index a29e84cf78d5e1e7b2fef75387092f945f3597ff..73d42f86222b3298c7495c420596f7f522214887 100644 --- a/core/src/main/AndroidManifest.xml +++ b/core/src/main/AndroidManifest.xml @@ -16,7 +16,5 @@ You should have received a copy of the GNU General Public License along with this program. If not, see . --> - + \ No newline at end of file diff --git a/fakelocation/build.gradle b/fakelocation/build.gradle index 64fc6336df504e86d48703ee1e6b7162e5a1ff01..2563939c53f390817a76da9438cc1d283866d92e 100644 --- a/fakelocation/build.gradle +++ b/fakelocation/build.gradle @@ -37,12 +37,13 @@ android { } } compileOptions { - sourceCompatibility JavaVersion.VERSION_1_8 - targetCompatibility JavaVersion.VERSION_1_8 + sourceCompatibility JavaVersion.VERSION_17 + targetCompatibility JavaVersion.VERSION_17 } kotlinOptions { - jvmTarget = '1.8' + jvmTarget = '17' } + namespace 'foundation.e.privacymodules.fakelocation' } dependencies { diff --git a/fakelocation/fakelocationdemo/build.gradle b/fakelocation/fakelocationdemo/build.gradle index 6cb9af3a44d16a95c8dcc93e7f3f44f15d5899a5..49b4c3a3bc238b212a78cad7ffd122e53ae9971e 100644 --- a/fakelocation/fakelocationdemo/build.gradle +++ b/fakelocation/fakelocationdemo/build.gradle @@ -41,16 +41,17 @@ android { } } compileOptions { - sourceCompatibility JavaVersion.VERSION_1_8 - targetCompatibility JavaVersion.VERSION_1_8 + sourceCompatibility JavaVersion.VERSION_17 + targetCompatibility JavaVersion.VERSION_17 } kotlinOptions { - jvmTarget = '1.8' + jvmTarget = '17' allWarningsAsErrors = false } buildFeatures { dataBinding true } + namespace 'foundation.e.privacymodules.fakelocationdemo' } dependencies { diff --git a/fakelocation/fakelocationdemo/src/main/AndroidManifest.xml b/fakelocation/fakelocationdemo/src/main/AndroidManifest.xml index 497f27b39992d5deb798715d75135618fe1862bd..a832d59b8402a380f29f18659985fb9114f4136f 100644 --- a/fakelocation/fakelocationdemo/src/main/AndroidManifest.xml +++ b/fakelocation/fakelocationdemo/src/main/AndroidManifest.xml @@ -16,9 +16,7 @@ ~ along with this program. If not, see . --> - + diff --git a/fakelocation/src/main/AndroidManifest.xml b/fakelocation/src/main/AndroidManifest.xml index fde371cbfc85f3c5c5c1f380516fa1bb08cca6bd..623a180d27474fa57a624d2d4f5ae57a24f49ec3 100644 --- a/fakelocation/src/main/AndroidManifest.xml +++ b/fakelocation/src/main/AndroidManifest.xml @@ -19,9 +19,7 @@ + xmlns:tools="http://schemas.android.com/tools"> diff --git a/gradle.properties b/gradle.properties index 2fb49e8c3c96b4c98f39b11ef8c088e6bc89ab70..bcc06b300446baaf09f4f78f5417776c008c3e86 100644 --- a/gradle.properties +++ b/gradle.properties @@ -18,3 +18,6 @@ android.useAndroidX=true # Automatically convert third-party libraries to use AndroidX android.enableJetifier=true gitLabPrivateToken="" +android.defaults.buildfeatures.buildconfig=true +android.nonTransitiveRClass=false +android.nonFinalResIds=false diff --git a/gradle/dependencyGraph.gradle b/gradle/dependencyGraph.gradle deleted file mode 100644 index 29eafa40a7d4e02ca11c0dc2125d96dc9addb7b1..0000000000000000000000000000000000000000 --- a/gradle/dependencyGraph.gradle +++ /dev/null @@ -1,140 +0,0 @@ -/* - * Copyright (C) 2021 E FOUNDATION - * - * This program is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see . - */ - -/** - * Taken from https://github.com/JakeWharton/SdkSearch/blob/master/gradle/projectDependencyGraph.gradle - */ - -def font = "Helvetica" - -task projectDependencyGraph { - doLast { - def dot = new File(rootProject.buildDir, 'reports/dependency-graph/project.dot') - dot.parentFile.mkdirs() - dot.delete() - - dot << 'digraph {\n' - dot << " graph [label=\"${rootProject.name}\\n \",labelloc=t,fontsize=30,ranksep=1.4,fontname=\"$font\"];\n" - dot << " node [style=filled, fillcolor=\"#bbbbbb\", fontname=\"$font\"];\n" - dot << " edge [fontname = \"$font\"];" - dot << ' rankdir=TB;\n' - - def rootProjects = [] - def queue = [rootProject] - while (!queue.isEmpty()) { - def project = queue.remove(0) - rootProjects.add(project) - queue.addAll(project.childProjects.values()) - } - - def projects = new LinkedHashSet() - def dependencies = new LinkedHashMap, List>() - def multiplatformProjects = [] - def jsProjects = [] - def androidProjects = [] - def javaProjects = [] - - queue = [rootProject] - while (!queue.isEmpty()) { - def project = queue.remove(0) - queue.addAll(project.childProjects.values()) - - if (project.plugins.hasPlugin('org.jetbrains.kotlin.multiplatform')) { - multiplatformProjects.add(project) - } - if (project.plugins.hasPlugin('org.jetbrains.kotlin.js')) { - jsProjects.add(project) - } - if (project.plugins.hasPlugin('com.android.library') || project.plugins.hasPlugin('com.android.application')) { - androidProjects.add(project) - } - if (project.plugins.hasPlugin('java-library') || project.plugins.hasPlugin('java')) { - javaProjects.add(project) - } - - project.configurations.all { config -> - config.dependencies - .withType(ProjectDependency) - .collect { it.dependencyProject } - .each { dependency -> - projects.add(project) - projects.add(dependency) - rootProjects.remove(dependency) - - def graphKey = new Tuple2(project, dependency) - def traits = dependencies.computeIfAbsent(graphKey) { new ArrayList() } - - if (config.name.toLowerCase().endsWith('implementation')) { - traits.add('style=dotted') - } - } - } - } - - projects = projects.sort { it.path } - - dot << '\n # Projects\n\n' - for (project in projects) { - def traits = [] - - if (rootProjects.contains(project)) { - traits.add('shape=box') - } - - if (multiplatformProjects.contains(project)) { - traits.add('fillcolor="#ffd2b3"') - } else if (jsProjects.contains(project)) { - traits.add('fillcolor="#ffffba"') - } else if (androidProjects.contains(project)) { - traits.add('fillcolor="#baffc9"') - } else if (javaProjects.contains(project)) { - traits.add('fillcolor="#ffb3ba"') - } else { - traits.add('fillcolor="#eeeeee"') - } - - dot << " \"${project.path}\" [${traits.join(", ")}];\n" - } - - dot << '\n {rank = same;' - for (project in projects) { - if (rootProjects.contains(project)) { - dot << " \"${project.path}\";" - } - } - dot << '}\n' - - dot << '\n # Dependencies\n\n' - dependencies.forEach { key, traits -> - dot << " \"${key.first.path}\" -> \"${key.second.path}\"" - if (!traits.isEmpty()) { - dot << " [${traits.join(", ")}]" - } - dot << '\n' - } - - dot << '}\n' - - def p = 'dot -Tpng -O project.dot'.execute([], dot.parentFile) - p.waitFor() - if (p.exitValue() != 0) { - throw new RuntimeException(p.errorStream.text) - } - - println("Project module dependency graph created at ${dot.absolutePath}.png") - } -} \ No newline at end of file diff --git a/gradle/libs.versions.toml b/gradle/libs.versions.toml index 0bb32ba3b418402c82be42cca03b0b165092b7d0..f15f10dc07128cc1737bbfcd6e918effce008c50 100644 --- a/gradle/libs.versions.toml +++ b/gradle/libs.versions.toml @@ -1,48 +1,39 @@ [versions] - -koin = "3.2.0" -kotlinx-coroutines = "1.6.1" -kotlin = "1.6.10" -androidx-navigation = "2.5.3" -androidx-test = "1.3.0" -androidx-lifecycle = "2.5.0" -androidx-room = "2.3.0" +agp = "8.2.0" +koin = "3.4.3" +kotlinx-coroutines = "1.7.3" +kotlin = "1.9.21" +androidx-navigation = "2.7.6" +androidx-lifecycle = "2.6.2" orbotservice = "orbot-16.6.3-2" retrofit = "2.9.0" pcap4j = "1.8.2" [libraries] -androidx-appcompat = { group = "androidx.appcompat", name = "appcompat", version = "1.4.2" } -androidx-arch-core-testing = {group = "androidx.arch.core", name = "core-testing", version = "2.1.0" } -androidx-collection = { group = "androidx.collection", name = "collection-ktx", version = "1.1.0" } -androidx-core-ktx = { group = "androidx.core", name = "core-ktx", version = "1.8.0" } -androidx-fragment-ktx = { group = "androidx.fragment", name = "fragment-ktx", version = "1.5.0" } +androidx-appcompat = { group = "androidx.appcompat", name = "appcompat", version = "1.6.1" } +androidx-core-ktx = { group = "androidx.core", name = "core-ktx", version = "1.12.0" } +androidx-fragment-ktx = { group = "androidx.fragment", name = "fragment-ktx", version = "1.6.2" } androidx-lifecycle-runtime = { group = "androidx.lifecycle", name = "lifecycle-runtime-ktx", version.ref = "androidx-lifecycle" } androidx-lifecycle-viewmodel = { group = "androidx.lifecycle", name = "lifecycle-viewmodel-ktx", version.ref = "androidx-lifecycle" } -androidx-localbroadcast = { group = "androidx.localbroadcastmanager", name = "localbroadcastmanager", version = "1.0.0" } +androidx-localbroadcast = { group = "androidx.localbroadcastmanager", name = "localbroadcastmanager", version = "1.1.0" } androidx-navigation-fragment = { group = "androidx.navigation", name = "navigation-fragment-ktx", version.ref = "androidx-navigation" } androidx-navigation-ui = { group = "androidx.navigation", name = "navigation-ui-ktx", version.ref = "androidx-navigation" } androidx-palette = { group = "androidx.palette", name = "palette", version = "1.0.0" } -androidx-room-common = { group = "androidx.room", name = "room-common", version.ref = "androidx-room" } -androidx-room-compiler = { group = "androidx.room", name = "room-compiler", version.ref = "androidx-room" } -androidx-room-ktx = { group = "androidx.room", name = "room-ktx", version.ref = "androidx-room" } -androidx-room-runtime = { group = "androidx.room", name = "room-runtime", version.ref = "androidx-room" } androidx-viewpager2 = { group = "androidx.viewpager2", name = "viewpager2", version = "1.0.0" } -androidx-work-ktx = { group = "androidx.work", name = "work-runtime-ktx", version = "2.7.1" } +androidx-work-ktx = { group = "androidx.work", name = "work-runtime-ktx", version = "2.9.0" } eos-elib = { group = "foundation.e", name = "elib", version = "0.0.1-alpha11" } eos-orbotservice = { group = "foundation.e", name = "orbotservice", version.ref = "orbotservice" } eos-telemetry = { group = "foundation.e.lib", name = "telemetry", version = "0.0.8-alpha" } -google-material = { group = "com.google.android.material", name = "material", version = "1.6.1" } +google-material = { group = "com.google.android.material", name = "material", version = "1.11.0" } google-gson = { group = "com.google.code.gson", name = "gson", version = "2.10.1" } -junit = { group = "junit", name = "junit", version = "4.13.1" } +junit = { group = "junit", name = "junit", version = "4.13.2" } koin-core = { group = "io.insert-koin", name = "koin-core", version.ref = "koin" } koin-android = { group = "io.insert-koin", name = "koin-android", version.ref = "koin" } kotlinx-coroutines-android = { group = "org.jetbrains.kotlinx", name = "kotlinx-coroutines-android", version.ref = "kotlinx-coroutines" } kotlinx-coroutines = { group = "org.jetbrains.kotlinx", name = "kotlinx-coroutines-core", version.ref = "kotlinx-coroutines" } -leakcanary = { group = "com.squareup.leakcanary", name = "leakcanary-android", version = "2.9.1" } +leakcanary = { group = "com.squareup.leakcanary", name = "leakcanary-android", version = "2.10" } maplibre = { group = "org.maplibre.gl", name = "android-sdk", version = "10.2.0" } -mockk = { group = "io.mockk", name = "mockk", version = "1.10.5" } mpandroidcharts = { group = "com.github.PhilJay", name = "MPAndroidChart", version = "v3.1.0" } pcap4j = { group = "org.pcap4j", name = "pcap4j-core", version.ref = "pcap4j" } pcap4j-packetfactory-static = { group = "org.pcap4j", name = "pcap4j-packetfactory-static", version.ref = "pcap4j" } @@ -55,10 +46,11 @@ timber = { group = "com.jakewharton.timber", name = "timber", version = "5.0.1" koin = ["koin-core", "koin-android"] kotlin-android-coroutines = ["androidx-core-ktx", "kotlinx-coroutines"] pcap4j = ["pcap4j", "pcap4j-packetfactory-static"] + [plugins] -android-application = { id = "com.android.application", version = "7.2.1" } -android-library = { id = "com.android.library", version = "7.2.1" } +android-application = { id = "com.android.application", version.ref = "agp" } +android-library = { id = "com.android.library", version.ref = "agp" } androidx-navigation-safeargs = { id = "androidx.navigation.safeargs.kotlin", version.ref = "androidx-navigation" } benmanes-versions = { id = "com.github.ben-manes.versions", version = "0.38.0" } kotlin-android = { id = "org.jetbrains.kotlin.android", version.ref = "kotlin" } diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties index 35be582fc9170d7b365c99f974331224dff38557..16a3dd54a644e57dc3f9ed22c83eea1900d9407a 100644 --- a/gradle/wrapper/gradle-wrapper.properties +++ b/gradle/wrapper/gradle-wrapper.properties @@ -1,6 +1,6 @@ #Sat Jul 16 09:07:59 CEST 2022 distributionBase=GRADLE_USER_HOME -distributionUrl=https\://services.gradle.org/distributions/gradle-7.3.3-bin.zip +distributionUrl=https\://services.gradle.org/distributions/gradle-8.2-bin.zip distributionPath=wrapper/dists zipStorePath=wrapper/dists zipStoreBase=GRADLE_USER_HOME diff --git a/ipscrambling/build.gradle b/ipscrambling/build.gradle index 9ff3f8c394c9086255f9ebdcf4009ae667fd361d..e8fa0063a30e65ef8e492281b56188f1de6bb35e 100644 --- a/ipscrambling/build.gradle +++ b/ipscrambling/build.gradle @@ -37,12 +37,13 @@ android { } } compileOptions { - sourceCompatibility JavaVersion.VERSION_1_8 - targetCompatibility JavaVersion.VERSION_1_8 + sourceCompatibility JavaVersion.VERSION_17 + targetCompatibility JavaVersion.VERSION_17 } kotlinOptions { - jvmTarget = '1.8' + jvmTarget = '17' } + namespace 'foundation.e.advancedprivacy.ipscrambler' } dependencies { diff --git a/ipscrambling/src/main/AndroidManifest.xml b/ipscrambling/src/main/AndroidManifest.xml index d6496f0e8f52185e6206514205a4d03fbeebcd59..7a64471f19e90362e97205d96b16dd1ed1ea95b6 100644 --- a/ipscrambling/src/main/AndroidManifest.xml +++ b/ipscrambling/src/main/AndroidManifest.xml @@ -1,5 +1,4 @@ diff --git a/ipscrambling/src/main/java/foundation/e/advancedprivacy/ipscrambler/OrbotSupervisor.kt b/ipscrambling/src/main/java/foundation/e/advancedprivacy/ipscrambler/OrbotSupervisor.kt index 6e0e2055c6b0305d57bd48d7f49ad303b4923f7e..0edc7106fdc9f94701d9d57243bdaad024210462 100644 --- a/ipscrambling/src/main/java/foundation/e/advancedprivacy/ipscrambler/OrbotSupervisor.kt +++ b/ipscrambling/src/main/java/foundation/e/advancedprivacy/ipscrambler/OrbotSupervisor.kt @@ -28,7 +28,6 @@ import android.os.Bundle import android.os.Handler import android.os.Looper import android.os.Message -import androidx.localbroadcastmanager.content.LocalBroadcastManager import foundation.e.advancedprivacy.domain.entities.FeatureState import foundation.e.advancedprivacy.externalinterfaces.servicesupervisors.FeatureSupervisor import kotlinx.coroutines.CoroutineScope @@ -120,8 +119,8 @@ class OrbotSupervisor( init { Prefs.setContext(context) - - val lbm = LocalBroadcastManager.getInstance(context) + @Suppress("DEPRECATION") + val lbm = androidx.localbroadcastmanager.content.LocalBroadcastManager.getInstance(context) lbm.registerReceiver( localBroadcastReceiver, IntentFilter(OrbotConstants.LOCAL_ACTION_STATUS) @@ -175,7 +174,8 @@ class OrbotSupervisor( private fun isServiceRunning(): Boolean { // Reset status, and then ask to refresh it synchronously. currentStatus = Status.OFF - LocalBroadcastManager.getInstance(context) + @Suppress("DEPRECATION") + androidx.localbroadcastmanager.content.LocalBroadcastManager.getInstance(context) .sendBroadcastSync(Intent(OrbotConstants.ACTION_CHECK_RUNNING_SYNC)) return currentStatus != Status.OFF } @@ -307,6 +307,8 @@ class OrbotSupervisor( private set fun onCleared() { - LocalBroadcastManager.getInstance(context).unregisterReceiver(localBroadcastReceiver) + @Suppress("DEPRECATION") + androidx.localbroadcastmanager.content.LocalBroadcastManager.getInstance(context) + .unregisterReceiver(localBroadcastReceiver) } } diff --git a/permissionseos/build.gradle b/permissionseos/build.gradle index d57ea9cece40f99b03c5007646379718673f2fb5..8b558271e5c2cdb6b7d592d9fb1d3bedcc11bf7d 100644 --- a/permissionseos/build.gradle +++ b/permissionseos/build.gradle @@ -18,9 +18,10 @@ android { } } compileOptions { - sourceCompatibility JavaVersion.VERSION_1_8 - targetCompatibility JavaVersion.VERSION_1_8 + sourceCompatibility JavaVersion.VERSION_17 + targetCompatibility JavaVersion.VERSION_17 } + namespace 'foundation.e.advancedprivacy.permissions.eos' } dependencies { diff --git a/permissionseos/libs/hidden-apis-stub/build.gradle b/permissionseos/libs/hidden-apis-stub/build.gradle index 2043edc5128cdba2708b6685da5ee7612328f71d..5e8ca1167fc8d38f626122bc91b51fcaa9b77485 100644 --- a/permissionseos/libs/hidden-apis-stub/build.gradle +++ b/permissionseos/libs/hidden-apis-stub/build.gradle @@ -21,6 +21,7 @@ plugins { android { compileSdkVersion buildConfig.compileSdk + namespace 'foundation.e.advancedprivacy.hidden.apis' } diff --git a/permissionseos/libs/hidden-apis-stub/src/main/AndroidManifest.xml b/permissionseos/libs/hidden-apis-stub/src/main/AndroidManifest.xml index 61f315adbb2ba52eb9dd0a0b1c5e0e4f393f837d..e5fed01c0b1de9982e6c8f5566a21c6f50924ec9 100644 --- a/permissionseos/libs/hidden-apis-stub/src/main/AndroidManifest.xml +++ b/permissionseos/libs/hidden-apis-stub/src/main/AndroidManifest.xml @@ -18,7 +18,6 @@ diff --git a/permissionseos/src/main/AndroidManifest.xml b/permissionseos/src/main/AndroidManifest.xml index ed25c1ce9a40c39058fb000ac4ca7922b7250fa3..ef4917977ebc0d7c3de2e2eecfe62fe7632cd558 100644 --- a/permissionseos/src/main/AndroidManifest.xml +++ b/permissionseos/src/main/AndroidManifest.xml @@ -16,8 +16,7 @@ ~ along with this program. If not, see . --> + xmlns:tools="http://schemas.android.com/tools"> diff --git a/permissionsstandalone/build.gradle b/permissionsstandalone/build.gradle index deb982806ed7c0f950176955e9262db8dca68933..3ddfd888ac8df2b88f4a1f3d2d3bb090ac71cc84 100644 --- a/permissionsstandalone/build.gradle +++ b/permissionsstandalone/build.gradle @@ -38,12 +38,13 @@ android { } } compileOptions { - sourceCompatibility JavaVersion.VERSION_1_8 - targetCompatibility JavaVersion.VERSION_1_8 + sourceCompatibility JavaVersion.VERSION_17 + targetCompatibility JavaVersion.VERSION_17 } kotlinOptions { - jvmTarget = '1.8' + jvmTarget = '17' } + namespace 'foundation.e.advancedprivacy.permissions.standalone' } dependencies { diff --git a/permissionsstandalone/src/main/AndroidManifest.xml b/permissionsstandalone/src/main/AndroidManifest.xml index 60ff274f5b34b5ef1e963622cb4d0e5ac977d3fd..4f1c2953638a48a352d53c585b77a31c79c900c8 100644 --- a/permissionsstandalone/src/main/AndroidManifest.xml +++ b/permissionsstandalone/src/main/AndroidManifest.xml @@ -17,8 +17,6 @@ ~ along with this program. If not, see . --> - + \ No newline at end of file diff --git a/settings.gradle b/settings.gradle index 7eadbc9372ea74382753296fa84ab9aa68f07d08..2ae18aeb50957524c4457ab00fba1d193aaaf30d 100644 --- a/settings.gradle +++ b/settings.gradle @@ -6,8 +6,6 @@ pluginManagement { } } -enableFeaturePreview("VERSION_CATALOGS") - include ':app' rootProject.name = "AdvancedPrivacy" include ':fakelocation' diff --git a/trackers/build.gradle b/trackers/build.gradle index 69faabdf5aec9aa3ebfdf7f94a2821da94f45efe..f75ce5b28cdbec711c0dde8a6c879fa3f077ee7d 100644 --- a/trackers/build.gradle +++ b/trackers/build.gradle @@ -37,9 +37,10 @@ android { } compileOptions { - sourceCompatibility JavaVersion.VERSION_1_8 - targetCompatibility JavaVersion.VERSION_1_8 + sourceCompatibility JavaVersion.VERSION_17 + targetCompatibility JavaVersion.VERSION_17 } + namespace 'foundation.e.advancedprivacy.trackers' } dependencies { diff --git a/trackers/src/main/AndroidManifest.xml b/trackers/src/main/AndroidManifest.xml index b98070636d81833a33b8e422a87483a366ca47b2..0b294b58a9e89d9739c58e71bfcee599f171a785 100644 --- a/trackers/src/main/AndroidManifest.xml +++ b/trackers/src/main/AndroidManifest.xml @@ -16,6 +16,5 @@ You should have received a copy of the GNU General Public License along with this program. If not, see . --> - + \ No newline at end of file diff --git a/trackersserviceeos/build.gradle b/trackersserviceeos/build.gradle index d9f80afa3ebfbef1944103cd1229be9050cf73cd..08913811e15ee703f899eb4032a7bb22443c1553 100644 --- a/trackersserviceeos/build.gradle +++ b/trackersserviceeos/build.gradle @@ -19,11 +19,11 @@ android { } } compileOptions { - sourceCompatibility JavaVersion.VERSION_1_8 - targetCompatibility JavaVersion.VERSION_1_8 + sourceCompatibility JavaVersion.VERSION_17 + targetCompatibility JavaVersion.VERSION_17 } kotlinOptions { - jvmTarget = '1.8' + jvmTarget = '17' } } diff --git a/trackersserviceeos/src/main/AndroidManifest.xml b/trackersserviceeos/src/main/AndroidManifest.xml index 22904321c585cae229f15f6be0e799d597ae043c..688bfb0df7d6884da0d607b4f0f92e8f4c9fee54 100644 --- a/trackersserviceeos/src/main/AndroidManifest.xml +++ b/trackersserviceeos/src/main/AndroidManifest.xml @@ -16,8 +16,7 @@ You should have received a copy of the GNU General Public License along with this program. If not, see . --> - + diff --git a/trackersservicestandalone/build.gradle b/trackersservicestandalone/build.gradle index 5b574cd078d81cf9b256c7253a2da435aa758804..6e6e018f72a2ec42af496220b59247d77e36a8c7 100644 --- a/trackersservicestandalone/build.gradle +++ b/trackersservicestandalone/build.gradle @@ -18,12 +18,13 @@ android { } } compileOptions { - sourceCompatibility JavaVersion.VERSION_1_8 - targetCompatibility JavaVersion.VERSION_1_8 + sourceCompatibility JavaVersion.VERSION_17 + targetCompatibility JavaVersion.VERSION_17 } kotlinOptions { - jvmTarget = '1.8' + jvmTarget = '17' } + namespace 'foundation.e.advancedprivacy.trackers.service' } dependencies { diff --git a/trackersservicestandalone/src/main/AndroidManifest.xml b/trackersservicestandalone/src/main/AndroidManifest.xml index 4bfa4eb0292be2fccbeb6c381b1f1bb879f94982..54327c20b8bae447c270ce6c5955162a1bcd73dd 100644 --- a/trackersservicestandalone/src/main/AndroidManifest.xml +++ b/trackersservicestandalone/src/main/AndroidManifest.xml @@ -15,8 +15,7 @@ ~ You should have received a copy of the GNU General Public License ~ along with this program. If not, see . --> - +