import org.jetbrains.dokka.gradle.DokkaTask

buildscript {
  ext.versions = [
    'minSdk'    : 14,
    'compileSdk': 34,
  ]
  repositories {
    google()
    gradlePluginPortal()
    mavenCentral()
  }
  dependencies {
    classpath libs.gradlePlugin.android
    classpath libs.gradlePlugin.kotlin
    classpath libs.gradlePlugin.dokka
    classpath libs.gradlePlugin.mavenPublish
    classpath libs.gradlePlugin.detekt
    classpath libs.gradlePlugin.binaryCompatibility
    classpath libs.gradlePlugin.keeper
  }
}

// We use JetBrain's Kotlin Binary Compatibility Validator to track changes to our public binary
// APIs.
// When making a change that results in a public ABI change, the apiCheck task will fail. When this
// happens, run ./gradlew apiDump to generate updated *.api files, and add those to your commit.
// See https://github.com/Kotlin/binary-compatibility-validator
apply plugin: 'binary-compatibility-validator'

apiValidation {
  // Ignore projects that are not uploaded to Maven Central
  ignoredProjects += ["leakcanary-android-sample", "shark-test", "shark-hprof-test", "shark-cli"]
}

// This plugin needs to be applied to the root projects for the dokkaGfmCollector task we use to
// generate the documentation site.
apply plugin: 'org.jetbrains.dokka'

repositories {
  // Needed for the Dokka plugin.
  gradlePluginPortal()
}

subprojects {
  // Note: to skip Dokka on some projects we could add it individually to projects we actually
  // want.
  apply plugin: 'org.jetbrains.dokka'
  group = GROUP
  version = VERSION_NAME

  repositories {
    google()
    mavenCentral()
    //    maven {
    //      url 'https://oss.sonatype.org/content/repositories/snapshots/'
    //    }
    //    mavenLocal()
    jcenter()
  }

  apply plugin: 'io.gitlab.arturbosch.detekt'

  tasks.withType(DokkaTask.class).configureEach {
    dokkaSourceSets.configureEach {
      reportUndocumented.set(false)
      displayName.set(null)
      platform.set(org.jetbrains.dokka.Platform.jvm)

      perPackageOption {
        // will match all .internal packages and sub-packages
        matchingRegex.set("(.*\\.internal.*)")
        suppress.set(true)
      }
      perPackageOption {
        // BuildConfig files
        matchingRegex.set("com.squareup.leakcanary\\..*")
        suppress.set(true)
      }
      perPackageOption {
        // Example app
        matchingRegex.set("com.example.leakcanary\\..*")
        suppress.set(true)
      }
      skipDeprecated.set(true)
      externalDocumentationLink {
        url.set(new URL("https://square.github.io/okio/2.x/okio/"))
      }
      externalDocumentationLink {
        url.set(new URL("https://square.github.io/moshi/1.x/moshi/"))
      }
    }
  }

  pluginManager.withPlugin("com.vanniktech.maven.publish") {
    mavenPublish {
      sonatypeHost = "S01"
    }
  }

  tasks.withType(JavaCompile).configureEach {
    options.compilerArgs += [
        '-Xlint:all',
        '-Xlint:-serial',
        '-Xlint:-deprecation',
        // espresso-core classes say they're compiled with 51.0 but contain 52.0 attributes.
        // warning: [classfile] MethodParameters attribute introduced in version 52.0 class files is ignored in version 51.0 class files
        // '-Werror'
    ]
  }

  tasks.withType(org.jetbrains.kotlin.gradle.tasks.KotlinCompile).configureEach {
    kotlinOptions {
      // Avoid warnings of using older stdlib version 1.3 than compiler version 1.4
      apiVersion = "1.3"
    }
  }

  tasks.withType(Test).configureEach {
    testLogging {
      exceptionFormat 'FULL'
      showCauses true
      showExceptions true
      showStackTraces true
    }
  }

  detekt {
    config = rootProject.files('detekt-config.yml')
    parallel = true
    reports {
      xml.enabled = false
    }
  }

  pluginManager.withPlugin("java") {
    tasks.named("check") { dependsOn("detekt") }
    tasks.named("assemble") { dependsOn(rootProject.tasks.named("installGitHooks")) }
    tasks.named("clean") { dependsOn(rootProject.tasks.named("installGitHooks")) }
  }
}

//Copies git hooks from /hooks folder into .git; currently used to run Detekt during push
//Git hook installation
tasks.register("installGitHooks", Copy) {
  from new File(rootProject.rootDir, 'hooks')
  into { new File(rootProject.rootDir, '.git/hooks') }
  fileMode 0777 //Make files executable
}

tasks.register("siteDokka", Copy) {
  description = "Generate dokka Github-flavored Markdown for the documentation site."
  group = "documentation"
  dependsOn(":dokkaGfmCollector")

  // Copy the files instead of configuring a different output directory on the dokka task itself
  // since the default output directories disambiguate between different types of outputs, and our
  // custom directory doesn't.
  from(layout.buildDirectory.dir("dokka/gfmCollector/leakcanary"))
  // For whatever reason Dokka doesn't want to ignore the packages we told it to ignore.
  // Fine, we'll just ignore it here.
  exclude '**/com.example.leakcanary/**'
  into(rootProject.file("docs/api"))

  filter { line ->
    // Dokka adds [main]\ and [main]<br> everywhere, this just removes it.
    line.replaceAll("\\[main\\]\\\\", "").replaceAll("\\[main\\]<br>", "")
  }
}
