import org.gradle.internal.jvm.Jvm import org.jetbrains.kotlin.gradle.tasks.KotlinCompile import org.jetbrains.kotlin.gradle.tasks.KotlinCompilerExecutionStrategy // Top-level build file where you can add configuration options common to all sub-projects/modules. buildscript { // The version for the Kotlin plugin and dependencies ext.kotlin_version = '1.7.20' ext.lint_version = '30.3.1' ext.acra_version = '5.9.6' ext.ankidroid_backend_version = '0.1.15-anki2.1.54' // this is parsed in tools/setup-anki-backend.sh ext.hamcrest_version = '2.2' ext.junit_version = '5.9.1' ext.coroutines_version = '1.6.4' ext.fragments_version = "1.5.4" repositories { google() maven { url "https://plugins.gradle.org/m2/" } } dependencies { classpath 'com.android.tools.build:gradle:7.3.1' // NOTE: Do not place your application dependencies here; they belong // in the individual module build.gradle files classpath "app.brant:amazonappstorepublisher:0.1.0" classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version" classpath "org.jlleitschuh.gradle:ktlint-gradle:11.0.0" } } repositories { mavenCentral() } allprojects { apply plugin: "org.jlleitschuh.gradle.ktlint" } Properties localProperties = new Properties() if (project.rootProject.file('local.properties').exists()) { localProperties.load(project.rootProject.file('local.properties').newDataInputStream()) } Boolean fatalWarnings = !(localProperties['fatal_warnings'] == "false") // Here we extract per-module "best practices" settings to a single top-level evaluation subprojects { afterEvaluate { project -> if (project.hasProperty('android')) { project.android.testOptions.unitTests { includeAndroidResources = true } project.android.testOptions.unitTests.all { // tell backend to avoid rollover time, and disable interval fuzzing environment "ANKI_TEST_MODE", "1" useJUnitPlatform() testLogging { events "failed", "skipped" showStackTraces = true exceptionFormat = "full" } maxParallelForks = gradleTestMaxParallelForks forkEvery = 40 systemProperties['junit.jupiter.execution.parallel.enabled'] = true systemProperties['junit.jupiter.execution.parallel.mode.default'] = "concurrent" } } ktlint { // remove version override when ktlint gradle plugin releases with 0.45+ transitive // check for "ktlint" here: // https://github.com/JLLeitschuh/ktlint-gradle/blob/master/plugin/gradle/libs.versions.toml version = "0.45.2" disabledRules = ["no-wildcard-imports"] } /** Kotlin allows concrete function implementations inside interfaces. For those to work when Kotlin compilation targets the JVM backend, you have to enable the interoperability via 'freeCompilerArgs' in your gradle file, and you have to choose one of the appropriate '-Xjvm-default' modes. https://kotlinlang.org/docs/java-to-kotlin-interop.html#default-methods-in-interfaces and we used "all" because we don't have downstream consumers https://docs.gradle.org/current/userguide/task_configuration_avoidance.html */ tasks.withType(org.jetbrains.kotlin.gradle.tasks.KotlinCompile).all { kotlinOptions { allWarningsAsErrors = fatalWarnings freeCompilerArgs = ['-Xjvm-default=all'] } } } } ext { jvmVersion = Jvm.current().javaVersion.majorVersion if (jvmVersion != "11" && jvmVersion != "17" && jvmVersion != "18") { println "\n\n\n" println "**************************************************************************************************************" println "\n\n\n" println "ERROR: AnkiDroid builds with JVM version 11, 17 or 18." println " Incompatible major version detected: '" + jvmVersion + "'" println "\n\n\n" println "**************************************************************************************************************" println "\n\n\n" System.exit(1) } ciBuild = System.getenv("CI") == "true" // works for Travis CI or Github Actions // allows for -Dpre-dex=false to be set preDexEnabled = "true" == System.getProperty("pre-dex", "true") // allows for universal APKs to be generated universalApkEnabled = "true" == System.getProperty("universal-apk", "false") if (System.getProperty("os.name") == "Mac OS X") { // macOS reports hardware cores. This is accurate for CI, Intel (halved due to SMT) and Apple Silicon gradleTestMaxParallelForks = "sysctl -n hw.physicalcpu".execute().text.toInteger() } else if (ciBuild) { // GitHub Actions (Standard_DS2_v2) are 1:1 on Linux/Windows with two vCPU cores // Sources: // Standard_DS2_v2 https://docs.github.com/en/actions/using-github-hosted-runners/about-github-hosted-runners#cloud-hosts-for-github-hosted-runners // Which is 1:1 https://docs.microsoft.com/en-gb/azure/virtual-machines/acu : DS1_v2 - DS15_v2 | 1:1 gradleTestMaxParallelForks = 2 // separate gradle compile process is a major speed improvement, but consumes 2x RAM // the CI machines don't have enough RAM to do that without going in to swap quite a bit // so for CI machines only - to improve reliability despite compilation speed hit, compile kotlin in process println "CI build detected: setting compiler execution strategy to IN_PROCESS" tasks.withType(KotlinCompile).configureEach { compilerExecutionStrategy.set(KotlinCompilerExecutionStrategy.IN_PROCESS) } } else { // Use 50% of cores to account for SMT which doesn't help this workload gradleTestMaxParallelForks = Runtime.runtime.availableProcessors().intdiv(2) ?: 1 } }