Skip to content
Snippets Groups Projects
build.gradle 15.9 KiB
Newer Older
apply plugin: 'com.android.application'
apply plugin: 'kotlin-android'
apply plugin: 'kotlin-kapt'
apply plugin: 'kotlin-parcelize'
apply plugin: 'androidx.navigation.safeargs.kotlin'
apply plugin: 'jacoco'

def environmentExtractor = { File path ->
    def rawJson = path.text
    def escapedJson = rawJson.replace("\"", "\\\"").replace("\n", "").replace("\r", "")
android {
    println("Current VERSION_MAJOR: ${VERSION_MAJOR}")
    println("Current VERSION_MINOR: ${VERSION_MINOR}")
    println("Current VERSION_PATCH: ${VERSION_PATCH}")
    println("Current VERSION_BUILD: ${VERSION_BUILD}")

Mohamed Metwalli's avatar
Mohamed Metwalli committed
    compileSdkVersion 29
    buildToolsVersion "29.0.3"

    defaultConfig {
        applicationId 'de.rki.coronawarnapp'
        minSdkVersion 23
Mohamed Metwalli's avatar
Mohamed Metwalli committed
        targetSdkVersion 29
                        + VERSION_MINOR.toInteger() * 10000
                        + VERSION_PATCH.toInteger() * 100
                        + VERSION_BUILD.toInteger()
        versionName "${VERSION_MAJOR}.${VERSION_MINOR}.${VERSION_PATCH}"
        println("Used versionName: $versionName")
        testInstrumentationRunner "testhelpers.TestApplicationUIRunner"
        resConfigs "de", "en", "tr", "bg", "pl", "ro"
        def prodEnvJson = environmentExtractor(file("../prod_environments.json"))
        buildConfigField "String", "ENVIRONMENT_JSONDATA", prodEnvJson
        if (project.hasProperty("commit_hash")) {
            buildConfigField "String", "GIT_COMMIT_SHORT_HASH", "\"$commit_hash\""
        } else {
            buildConfigField "String", "GIT_COMMIT_SHORT_HASH", "\"no commit hash\""
        }

        def devEnvironmentFile = file("../test_environments.json")
        if (devEnvironmentFile.exists()) {
            def devEnvJson = environmentExtractor(devEnvironmentFile)
            buildConfigField "String", "ENVIRONMENT_JSONDATA", devEnvJson
        javaCompileOptions {
            annotationProcessorOptions {
                arguments += ["room.schemaLocation": "$projectDir/schemas".toString()]
            }
    def signingPropFile = file("../keystore.properties")
    if (signingPropFile.canRead()) {
        Properties signingProps = new Properties()
        signingProps.load(new FileInputStream(signingPropFile))
        signingConfigs {
                if (signingProps['deviceRelease.storePath'] != null) {
                    storeFile file(signingProps['deviceRelease.storePath'])
                    keyAlias signingProps['deviceRelease.keyAlias']
                    storePassword signingProps['deviceRelease.storePassword']
                    keyPassword signingProps['deviceRelease.keyPassword']
                }
                if (signingProps['deviceForTestersRelease.storePath'] != null) {
                    storeFile file(signingProps['deviceForTestersRelease.storePath'])
                    keyAlias signingProps['deviceForTestersRelease.keyAlias']
                    storePassword signingProps['deviceForTestersRelease.storePassword']
                    keyPassword signingProps['deviceForTestersRelease.keyPassword']
                }
            }
        }
    buildTypes {
        release {
            minifyEnabled true
            shrinkResources true
            proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
        }
    }

    flavorDimensions "version"
    productFlavors {
        device {
            dimension "version"
            resValue "string", "app_name", "Corona-Warn"

            ext {
                envTypeDefault = [debug: "INT", release: "PROD"]
            }
            if (signingPropFile.canRead()) {
                signingConfig signingConfigs.deviceRelease
            }
        deviceForTesters {
            dimension "version"
            resValue "string", "app_name", "CWA TEST"
            applicationIdSuffix '.test'
            ext {
                envTypeDefault = [debug: "INT", release: "WRU-XD"]
            }
            if (signingPropFile.canRead()) {
                signingConfig signingConfigs.deviceForTestersRelease
            }
    applicationVariants.all { variant ->
        def flavor = variant.productFlavors[0]
        def typeName = variant.buildType.name // debug/release
        variant.buildConfigField "String", "ENVIRONMENT_TYPE_DEFAULT", "\"${flavor.envTypeDefault[typeName]}\""

        if (flavor.name == "deviceForTesters") {
            def adjustedVersionName = "${VERSION_MAJOR}.${VERSION_MINOR}.${VERSION_PATCH}-RC${VERSION_BUILD}"
            variant.outputs.each { output ->
                output.versionNameOverride = adjustedVersionName
            }
            println("deviceForTesters adjusted versionName: $adjustedVersionName")
        }
        if (flavor.name != "device") {
            variant.outputs.each { output ->
                def apkName = "Corona-Warn-App-${output.versionNameOverride}-${flavor.name}-${variant.buildType.name}.apk"
                println("Override APK Name: $apkName")
                output.outputFileName = apkName
            }
    buildFeatures {
        dataBinding true
        viewBinding true
    }

    compileOptions {
        sourceCompatibility JavaVersion.VERSION_1_8
        targetCompatibility JavaVersion.VERSION_1_8
    }
    tasks.withType(org.jetbrains.kotlin.gradle.tasks.KotlinCompile).all {
            jvmTarget = "1.8"

            freeCompilerArgs += [
                    "-Xno-kotlin-nothing-value-exception",
                    "-Xuse-experimental=kotlinx.coroutines.ExperimentalCoroutinesApi",
                    "-Xuse-experimental=kotlinx.coroutines.FlowPreview",
                    "-Xuse-experimental=kotlin.time.ExperimentalTime"
    lintOptions {
        checkAllWarnings = true
    }

    testOptions {
            if (project.hasProperty('testFilter')) {
                List<String> props = project.getProperties().get("testFilter").split("\\s+")
                props.each {
                    def replaced = it
                            .replaceFirst("^(Corona-Warn-App/src/test.*/java/)(.+)\$", "**/\$2")
                            .replace(".kt", ".class")
                    project.logger.lifecycle("testFilter File: before=$it, after=$replaced")
                    include(replaced)
                }
            }
        unitTests {
            includeAndroidResources = true
            returnDefaultValues = true
        }
        // Using orchestration together with mockk on x86 (32bit) emulator images crashes
        // Leaving this in here as reminder
        // https://github.com/android/android-test/issues/352
        // https://github.com/mockk/mockk/issues/466
        // execution 'ANDROIDX_TEST_ORCHESTRATOR'
    }

    kapt {
        useBuildCache true
        includeCompileClasspath = false
    }
    dexOptions {
        preDexLibraries true
    }
    packagingOptions {
        exclude "**/module-info.class"
        exclude 'NOTICE'
        exclude 'LICENSE'
        exclude 'CODEOWNERS'
        exclude 'README.md'
        exclude 'CODE_OF_CONDUCT.md'
    sourceSets {
        deviceForTesters {
            kotlin {
                srcDirs = ['src/deviceForTesters']
            }
            res {
                srcDirs 'src/deviceForTesters/res', 'src/deviceForTesters/res/navigation'
            }
        }
        device {
            kotlin {
                srcDirs = ['src/device']
            }
        }
        test {
            java.srcDirs += "$projectDir/src/testShared/java"
        }
        androidTest {
            java.srcDirs += "$projectDir/src/testShared/java"
            androidTest.assets.srcDirs += files("$projectDir/schemas".toString())
task jacocoTestReportDeviceRelease(type: JacocoReport, dependsOn: 'testDeviceReleaseUnitTest') {
    group = "Reporting"
    description = "Generate Jacoco coverage reports for the DeviceRelease build."

    reports {
        html.enabled = false
        xml {
            enabled = true
            destination file("$buildDir/reports/jacoco/deviceRelease/jacoco.xml")
        }
    }

    def excludes = [
            '**/R.class',
            '**/R$*.class',
            '**/BuildConfig.*',
            '**/Manifest*.*',
            '**/*Test*.*',
            'android/**/*.*',
            '**/*$$*',
    ]

    def classPaths = [
            "**/intermediates/classes/deviceRelease/**",
            "**/intermediates/javac/deviceRelease/*/classes/**", // Android Gradle Plugin 3.2.x support.
            "**/intermediates/javac/deviceRelease/classes/**", // Android Gradle Plugin 3.4 and 3.5 support.
            "**/tmp/kotlin-classes/deviceRelease/**"
    ]

    def debugTree = fileTree(dir: "$buildDir", includes: classPaths, excludes: excludes)
    def mainSrc = "src/main/java"

    getSourceDirectories().from(files([mainSrc]))
    getClassDirectories().from(files([debugTree]))
    getExecutionData().from(fileTree(dir: "$buildDir", includes: ["jacoco/testDeviceReleaseUnitTest.exec"]))
}

configurations.all {
    resolutionStrategy {
        force "androidx.test:monitor:1.3.0"
    }
}

dependencies {
    implementation "org.jetbrains.kotlinx:kotlinx-coroutines-core:$coroutineVersion"
    implementation "org.jetbrains.kotlinx:kotlinx-coroutines-android:$coroutineVersion"
    implementation "org.jetbrains.kotlinx:kotlinx-coroutines-play-services:$coroutineVersion"
    testImplementation "org.jetbrains.kotlinx:kotlinx-coroutines-test:$coroutineVersion"

    // ANDROID STANDARD
    def nav_version = "2.3.3"
    implementation 'androidx.appcompat:appcompat:1.2.0'
    implementation 'androidx.core:core-ktx:1.3.2'
    implementation 'com.google.android.material:material:1.2.1'
    implementation 'androidx.constraintlayout:constraintlayout:2.0.4'
    implementation "androidx.navigation:navigation-fragment-ktx:$nav_version"
    implementation "androidx.navigation:navigation-ui-ktx:$nav_version"
    implementation 'androidx.legacy:legacy-support-v4:1.0.0'
    implementation 'androidx.preference:preference-ktx:1.1.1'
    implementation 'androidx.work:work-runtime-ktx:2.5.0'
    implementation 'androidx.lifecycle:lifecycle-common-java8:2.2.0'
    implementation 'androidx.lifecycle:lifecycle-process:2.2.0'
    implementation 'androidx.lifecycle:lifecycle-viewmodel-ktx:2.2.0'
    implementation 'androidx.lifecycle:lifecycle-viewmodel-savedstate:2.2.0'
    implementation 'androidx.lifecycle:lifecycle-livedata-ktx:2.2.0'
    implementation 'androidx.annotation:annotation:1.1.0'
    implementation "androidx.recyclerview:recyclerview:1.1.0"
    implementation "androidx.recyclerview:recyclerview-selection:1.1.0"
    def dagger_version = "2.31.2"
    implementation "com.google.dagger:dagger:$dagger_version"
    implementation "com.google.dagger:dagger-android:$dagger_version"
    implementation "com.google.dagger:dagger-android-support:$dagger_version"
    kapt "com.google.dagger:dagger-compiler:$dagger_version"
    kaptTest "com.google.dagger:dagger-compiler:$dagger_version"
    kaptAndroidTest "com.google.dagger:dagger-compiler:$dagger_version"
    kapt "com.google.dagger:dagger-android-processor:$dagger_version"
    kaptTest "com.google.dagger:dagger-android-processor:$dagger_version"
    kaptAndroidTest "com.google.dagger:dagger-android-processor:$dagger_version"
    implementation('com.journeyapps:zxing-android-embedded:4.1.0') { transitive = false }
    // noinspection GradleDependency - needed for SDK 23 compatibility, in combination with com.journeyapps:zxing-android-embedded:4.1.0
    implementation 'com.google.zxing:core:3.3.0'
    implementation files('libs/play-services-nearby-exposurenotification-18.0.3.aar')
    testImplementation "androidx.arch.core:core-testing:2.1.0"
    testImplementation('org.robolectric:robolectric:4.4') {
        exclude group: 'com.google.protobuf'
    }
    testImplementation "io.mockk:mockk:1.10.4"
    testImplementation "com.squareup.okhttp3:mockwebserver:4.9.0"
    testImplementation 'org.hamcrest:hamcrest-library:2.2'
    testImplementation 'junit:junit:4.13.1'
    testImplementation "org.junit.vintage:junit-vintage-engine:5.7.0"
    testImplementation "androidx.test:core-ktx:1.3.0"

    def jupiter_version = "5.7.0"
    testImplementation "org.junit.jupiter:junit-jupiter-api:$jupiter_version"
    testRuntimeOnly "org.junit.jupiter:junit-jupiter-engine:$jupiter_version"
    testImplementation "org.junit.jupiter:junit-jupiter-params:$jupiter_version"

    def kotest_version = "4.3.2"
    testImplementation "io.kotest:kotest-runner-junit5:$kotest_version"
    testImplementation "io.kotest:kotest-assertions-core-jvm:$kotest_version"
    testImplementation "io.kotest:kotest-property-jvm:$kotest_version"
    androidTestImplementation "io.kotest:kotest-assertions-core-jvm:$kotest_version"
    androidTestImplementation "io.kotest:kotest-property-jvm:$kotest_version"
    testImplementation "io.github.classgraph:classgraph:4.8.90"

    androidTestImplementation 'junit:junit:4.13.1'
    androidTestImplementation 'androidx.test:runner:1.3.0'
    androidTestImplementation 'androidx.test.ext:junit:1.1.2'
    androidTestImplementation 'androidx.test.espresso:espresso-core:3.3.0'
    androidTestImplementation 'androidx.test:rules:1.3.0'
    androidTestImplementation 'androidx.test.ext:truth:1.3.0'
    androidTestImplementation 'androidx.test.ext:junit:1.1.2'
    androidTestImplementation 'androidx.work:work-testing:2.5.0'
    androidTestImplementation "io.mockk:mockk-android:1.10.4"
    debugImplementation 'androidx.fragment:fragment-testing:1.2.5'
    debugImplementation 'androidx.test:core-ktx:1.3.0'
    androidTestImplementation 'tools.fastlane:screengrab:2.0.0'
    androidTestImplementation "androidx.navigation:navigation-testing:$nav_version"
    // Play Services
    implementation 'com.google.android.play:core:1.9.0'
    implementation 'com.google.android.gms:play-services-base:17.5.0'
    implementation 'com.google.android.gms:play-services-basement:17.5.0'
    implementation 'com.google.android.gms:play-services-safetynet:17.0.0'
    implementation 'com.google.android.gms:play-services-tasks:17.2.0'
    // HTTP
    implementation 'com.squareup.retrofit2:retrofit:2.9.0'
    implementation 'com.squareup.retrofit2:converter-gson:2.9.0'
    implementation('com.squareup.retrofit2:converter-protobuf:2.9.0') {
        exclude group: 'com.google.protobuf', module: 'protobuf-java'
    }
    implementation("com.squareup.okhttp3:logging-interceptor:4.9.0")
    implementation 'com.squareup.okhttp3:okhttp:4.9.0'
    // PERSISTENCE
    def room_version = "2.2.6"
    implementation "androidx.sqlite:sqlite-ktx:2.1.0"
    implementation "androidx.room:room-runtime:$room_version"
    implementation "androidx.room:room-ktx:$room_version"
    implementation "androidx.room:room-guava:$room_version"
    kapt "androidx.room:room-compiler:$room_version"
    androidTestImplementation "androidx.room:room-testing:$room_version"
    // UTILS
    implementation project(":Server-Protocol-Buffer")
    implementation 'com.google.code.gson:gson:2.8.6'
    implementation 'com.google.guava:guava:30.0-android'
    implementation 'joda-time:joda-time:2.10.6'
    // SECURITY
    implementation "androidx.security:security-crypto:1.0.0-rc03"
    implementation 'net.zetetic:android-database-sqlcipher:4.4.0'
    implementation 'org.conscrypt:conscrypt-android:2.5.1'
    implementation 'com.jakewharton.timber:timber:4.7.1@aar'
    implementation "com.airbnb.android:lottie:3.5.0"