import android.support.checkapi.CheckApiTask
import android.support.checkapi.UpdateApiTask
import android.support.doclava.DoclavaMultilineJavadocOptionFileOption
import android.support.doclava.DoclavaTask

import com.android.build.gradle.internal.coverage.JacocoReportTask
import com.android.build.gradle.internal.tasks.DeviceProviderInstrumentTestTask
import org.gradle.internal.os.OperatingSystem

import com.google.common.base.Charsets
import com.google.common.hash.HashCode
import com.google.common.hash.HashFunction
import com.google.common.hash.Hashing
import com.google.common.io.Files

import groovy.io.FileType

buildscript {
    repositories {
        maven { url '../../prebuilts/gradle-plugin' }
        maven { url '../../prebuilts/tools/common/m2/repository' }
        maven { url '../../prebuilts/tools/common/m2/internal' }
        maven { url "../../prebuilts/maven_repo/android" }
    }
    dependencies {
        // Keep gradle plugin version in sync with ub_supportlib-master manifest.
        classpath 'com.android.tools.build:gradle:2.2.1'
    }
}

repositories {
    maven { url '../../prebuilts/tools/common/m2/repository' }
}

configurations {
    doclava
}

dependencies {
    doclava project(':doclava')
}

gradle.ext.currentSdk = 25
ext.supportVersion = '25.1.1-SNAPSHOT'
ext.extraVersion = 41
ext.supportRepoOut = ''
ext.buildToolsVersion = '24.0.1'
ext.buildNumber = Integer.toString(ext.extraVersion)

ext.testRunnerVersion = '0.6-alpha'
ext.espressoVersion = '2.3-alpha'

// Enforce the use of prebuilt dependencies in all sub-projects. This is
// required for the doclava dependency.
ext.usePrebuilts = "true"

// Use the embedded SDK by default, which can be overridden by setting the 'sdk.dir' property
// (e.g. local.properties) or the 'ANDROID_HOME' environment variable.
final String platform = OperatingSystem.current().isMacOsX() ? 'darwin' : 'linux'
ext.sdkDirectory = "${rootDir}/../../prebuilts/fullsdk-${platform}";
System.setProperty('android.home', sdkDirectory)

/*
 * With the build server you are given two env variables.
 * The OUT_DIR is a temporary directory you can use to put things during the build.
 * The DIST_DIR is where you want to save things from the build.
 *
 * The build server will copy the contents of DIST_DIR to somewhere and make it available.
 */
if (System.env.DIST_DIR != null && System.env.OUT_DIR != null) {
    buildDir = new File(System.env.OUT_DIR + '/gradle/frameworks/support/build').getCanonicalFile()
    project.ext.distDir = new File(System.env.DIST_DIR).getCanonicalFile()

    // the build server does not pass the build number so we infer it from the last folder of the dist path.
    ext.buildNumber = project.ext.distDir.getName()
} else {
    buildDir = file("${project.rootDir}/../../out/host/gradle/frameworks/support/build")
    project.ext.distDir = file("${project.rootDir}/../../out/dist")
}

subprojects {
    // Change buildDir first so that all plugins pick up the new value.
    project.buildDir = project.file("$project.parent.buildDir/../$project.name/build")
}

ext.docsDir = new File(buildDir, 'javadoc')
ext.supportRepoOut = new File(buildDir, 'support_repo')
ext.testApkDistOut = ext.distDir

// Main task called by the build server.
task(createArchive) << {
}

// upload anchor for subprojects to upload their artifacts
// to the local repo.
task(mainUpload) << {
}

// repository creation task
task createRepository(type: Zip, dependsOn: mainUpload) {
    from project.ext.supportRepoOut
    destinationDir project.ext.distDir
    into 'm2repository'
    baseName = String.format("sdk-repo-linux-m2repository-%s", project.ext.buildNumber)
}
createArchive.dependsOn createRepository

// prepare repository with older versions
task unzipRepo(type: Copy) {
    from "${project.rootDir}/../../prebuilts/maven_repo/android"
    into project.ext.supportRepoOut
}

unzipRepo.doFirst {
    project.ext.supportRepoOut.deleteDir()
    project.ext.supportRepoOut.mkdirs()
}

// anchor for prepare repo. This is post unzip + sourceProp.
task(prepareRepo) << {
}

// lint every library
task(lint) << {
}

task(createXml) << {
    def repoArchive = createRepository.archivePath
    def repoArchiveName = createRepository.archiveName
    def size = repoArchive.length()
    def sha1 = getSha1(repoArchive)

    def xml =
"<sdk:sdk-addon xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\" xmlns:sdk=\"http://schemas.android.com/sdk/android/addon/6\">\n\
  <sdk:extra>\n\
    <sdk:revision>\n\
      <sdk:major>${project.ext.extraVersion}</sdk:major>\n\
    </sdk:revision>\n\
    <sdk:vendor-display>Android</sdk:vendor-display>\n\
    <sdk:vendor-id>android</sdk:vendor-id>\n\
    <sdk:name-display>Local Maven repository for Support Libraries</sdk:name-display>\n\
    <sdk:path>m2repository</sdk:path>\n\
    <sdk:archives>\n\
      <sdk:archive>\n\
       <sdk:size>${size}</sdk:size>\n\
       <sdk:checksum type=\"sha1\">${sha1}</sdk:checksum>\n\
       <sdk:url>${repoArchiveName}</sdk:url>\n\
      </sdk:archive>\n\
    </sdk:archives>\n\
  </sdk:extra>\n\
</sdk:sdk-addon>"

    Files.write(xml, new File(project.ext.distDir, 'repo-extras.xml'), Charsets.UTF_8)
}
createArchive.dependsOn createXml

task(createSourceProp) << {
    def sourceProp =
"Extra.VendorDisplay=Android\n\
Extra.Path=m2repository\n\
Archive.Arch=ANY\n\
Extra.NameDisplay=Android Support Repository\n\
Archive.Os=ANY\n\
Pkg.Desc=Local Maven repository for Support Libraries\n\
Pkg.Revision=${project.ext.extraVersion}.0.0\n\
Extra.VendorId=android"

    Files.write(sourceProp, new File(project.ext.supportRepoOut, 'source.properties'), Charsets.UTF_8)
}
createSourceProp.dependsOn unzipRepo
prepareRepo.dependsOn createSourceProp

import java.nio.charset.Charset

/**
 * Generates SHA1 hash for the specified file's absolute path.
 *
 * @param inputFile file to hash
 * @return SHA1 hash
 */
String getSha1(File inputFile) {
    HashFunction hashFunction = Hashing.sha1()
    HashCode hashCode = hashFunction.hashString(inputFile.getAbsolutePath(), Charset.forName("UTF-8"))
    return hashCode.toString()
}

/**
 * Returns the Android prebuilt JAR for the specified API level.
 *
 * @param apiLevel the API level or "current"
 * @return a file collection containing the Android prebuilt JAR
 */
FileCollection getAndroidPrebuilt(apiLevel) {
    files("${ext.sdkDirectory}/platforms/android-${apiLevel}/android.jar")
}

void registerForDocsTask(Task task, Project subProject, releaseVariant) {
    task.dependsOn releaseVariant.javaCompile
    task.source {
        def buildConfig = fileTree(releaseVariant.getGenerateBuildConfig().sourceOutputDir)
        return releaseVariant.javaCompile.source.minus(buildConfig) +
            fileTree(releaseVariant.aidlCompile.sourceOutputDir) +
            fileTree(releaseVariant.outputs[0].processResources.sourceOutputDir)
    }
    task.classpath += files(releaseVariant.javaCompile.classpath) +
            files(releaseVariant.javaCompile.destinationDir)
}

// Generates online docs.
task generateDocs(type: DoclavaTask, dependsOn: configurations.doclava) {
    docletpath = configurations.doclava.resolve()
    destinationDir = new File(project.docsDir, "online")

    // Base classpath is Android SDK, sub-projects add their own.
    classpath = getAndroidPrebuilt(gradle.ext.currentSdk)

    def hdfOption = new DoclavaMultilineJavadocOptionFileOption('hdf')
    hdfOption.add(
            ['android.whichdoc', 'online'],
            ['android.hasSamples', 'true']);

    // Default hidden errors + hidden superclass (111) and
    // deprecation mismatch (113) to match framework docs.
    final def hidden = [105, 107, 111, 112, 113, 115, 116, 121]

    doclavaErrors = (101..122) - hidden
    doclavaWarnings = []
    doclavaHidden += hidden

    options {
        addStringOption "templatedir",
                "${project.rootDir}/../../build/tools/droiddoc/templates-sdk"
        addStringOption "federate Android", "http://developer.android.com"
        addStringOption "stubpackages", "android.support.*"
        addStringOption "samplesdir", "${project.rootDir}/samples"
        addOption hdfOption
    }

    exclude '**/BuildConfig.java'
}

// Generates API files.
task generateApi(type: DoclavaTask, dependsOn: configurations.doclava) {
    docletpath = configurations.doclava.resolve()
    destinationDir = project.docsDir

    // Base classpath is Android SDK, sub-projects add their own.
    classpath = getAndroidPrebuilt(gradle.ext.currentSdk)

    apiFile = new File(project.docsDir, 'release/current.txt')
    removedApiFile = new File(project.docsDir, 'release/removed.txt')
    generateDocs = false

    options {
        addStringOption "templatedir",
                "${project.rootDir}/../../build/tools/droiddoc/templates-sdk"
        addStringOption "federate Android", "http://developer.android.com"
        addStringOption "stubpackages", "android.support.*"
    }
    exclude '**/BuildConfig.java'
    exclude '**/R.java'
}

// Copies generated API files to current version.
task updateApi(type: UpdateApiTask, dependsOn: generateApi) {
    newApiFile = new File(project.docsDir, 'release/current.txt')
    oldApiFile = new File(project.rootDir, 'api/current.txt')
    newRemovedApiFile = new File(project.docsDir, 'release/removed.txt')
    oldRemovedApiFile = new File(project.rootDir, 'api/removed.txt')
}

// Checks generated API files against current version.
task checkApi(type: CheckApiTask, dependsOn: generateApi) {
    doclavaClasspath = generateApi.docletpath

    checkApiTaskPath = name
    updateApiTaskPath = updateApi.name

    // Check that the API we're building hasn't changed from the development
    // version. These typed of changes require an explicit API file update.
    checkApiErrors = (2..30)-[22]
    checkApiWarnings = []
    checkApiHidden = [22]

    newApiFile = new File(project.docsDir, 'release/current.txt')
    oldApiFile = new File(project.rootDir, 'api/current.txt')
    newRemovedApiFile = new File(project.docsDir, 'release/removed.txt')
    oldRemovedApiFile = new File(project.rootDir, 'api/removed.txt')
}
createArchive.dependsOn checkApi

// Checks generated API files against current version.
task checkApiStable(type: CheckApiTask, dependsOn: generateApi) {
    doclavaClasspath = generateApi.docletpath

    checkApiTaskPath = name
    updateApiTaskPath = updateApi.name

    // Check that the API we're building hasn't broken the last-released
    // library version. These types of changes are forbidden.
    checkApiErrors = (7..18)
    checkApiWarnings = [23, 24]
    checkApiHidden = (2..6) + (19..22) + (25..30)

    def lastReleasedApiFile = null
    def apiDir = new File(project.rootDir, 'api')
    apiDir.eachFileMatch FileType.FILES, ~/(\d+\.){3}txt/, { File apiFile ->
        if (lastReleasedApiFile == null || apiFile.name > lastReleasedApiFile.name) {
            lastReleasedApiFile = apiFile;
        }
    }

    newApiFile = new File(project.docsDir, 'release/current.txt')
    oldApiFile = lastReleasedApiFile
    newRemovedApiFile = new File(project.docsDir, 'release/removed.txt')
    oldRemovedApiFile = new File(project.rootDir, 'api/removed.txt')
}
checkApi.dependsOn checkApiStable

subprojects {
    // Only modify Android projects.
    if (project.name.equals('doclava')) return;

    // Current SDK is set in studioCompat.gradle.
    project.ext.currentSdk = gradle.ext.currentSdk
    apply plugin: 'maven'

    version = rootProject.ext.supportVersion
    group = 'com.android.support'

    repositories {
        maven { url "${project.parent.projectDir}/../../prebuilts/tools/common/m2/repository" }
        maven { url "${project.parent.projectDir}/../../prebuilts/tools/common/m2/internal" }
        maven { url "${project.parent.projectDir}/../../prebuilts/maven_repo/android" }
    }

    project.plugins.whenPluginAdded { plugin ->
        def isAndroidLibrary = "com.android.build.gradle.LibraryPlugin".equals(plugin.class.name)
        def isAndroidApp = "com.android.build.gradle.AppPlugin".equals(plugin.class.name)
        def isJavaLibrary = "org.gradle.api.plugins.JavaPlugin".equals(plugin.class.name)

        if (isAndroidLibrary || isAndroidApp) {
            project.android.buildToolsVersion = rootProject.buildToolsVersion

            // Enable code coverage for debug builds only if we are not running inside the IDE,
            // since enabling coverage reports breaks the method parameter resolution in the IDE
            // debugger.
            project.android.buildTypes.debug.testCoverageEnabled = !hasProperty('android.injected.invoked.from.ide')

            // Enforce NewApi lint check as fatal.
            project.android.lintOptions.check 'NewApi'
            project.android.lintOptions.fatal 'NewApi'
            project.parent.lint.dependsOn project.lint
        }

        if (isAndroidLibrary || isJavaLibrary) {
            // Add library to the aggregate dependency report.
            task allDeps(type: DependencyReportTask) {}

            // Create release and separate zip task for library.
            task release(type: Upload) {
                configuration = configurations.archives
                repositories {
                    mavenDeployer {
                        repository(url: uri("$rootProject.ext.supportRepoOut"))

                        // Disable unique names for SNAPSHOTS so they can be updated in place.
                        setUniqueVersion(false)
                        doLast {
                            // Remove any invalid maven-metadata.xml files that may have been
                            // created for SNAPSHOT versions that are *not* uniquely versioned.
                            pom*.each { pom ->
                                if (pom.version.endsWith('-SNAPSHOT')) {
                                    final File artifactDir = new File(
                                            rootProject.ext.supportRepoOut,
                                            pom.groupId.replace('.', '/')
                                                    + '/' + pom.artifactId
                                                    + '/' + pom.version)
                                    delete fileTree(dir: artifactDir,
                                            include: 'maven-metadata.xml*')
                                }
                            }
                        }
                    }
                }
            }

            def deployer = release.repositories.mavenDeployer
            deployer.pom*.whenConfigured { pom ->
                pom.dependencies.findAll { dep ->
                    dep.groupId == 'com.android.support' && dep.artifactId != 'support-annotations'
                }*.type = 'aar'
            }

            ext.versionDir = {
                def groupDir = new File(rootProject.ext.supportRepoOut,
                        project.group.replace('.','/'))
                def artifactDir = new File(groupDir, archivesBaseName)
                return new File(artifactDir, version)
            }

            task generateSourceProps(dependsOn: createRepository) << {
                def content = "Maven.GroupId=$deployer.pom.groupId\n" +
                        "Maven.ArtifactId=$deployer.pom.artifactId\n" +
                        "Maven.Version=$deployer.pom.version\n" +
                        "Extra.VendorDisplay=Android\n" +
                        "Extra.VendorId=android\n" +
                        "Pkg.Desc=$project.name\n" +
                        "Pkg.Revision=1\n" +
                        "Maven.Dependencies=" +
                        String.join(",", project.configurations.compile.allDependencies.collect {
                            def p = parent.findProject(it.name)
                            return p ? "$p.group:$p.archivesBaseName:$p.version" : null
                        }.grep()) +
                        "\n"
                Files.write(content, new File(versionDir(), 'source.properties'), Charsets.UTF_8)
            }

            task createSeparateZip(type: Zip, dependsOn: generateSourceProps)  {
                into archivesBaseName
                destinationDir project.parent.ext.distDir
                baseName = project.group
                version = project.parent.ext.buildNumber
            }
            project.parent.createArchive.dependsOn createSeparateZip

            // Before the upload, make sure the repo is ready.
            release.dependsOn rootProject.tasks.prepareRepo

            // Make the mainupload depend on this one.
            mainUpload.dependsOn release
        }
    }

    project.afterEvaluate {
        // The archivesBaseName isn't available intially, so set it now
        def createZipTask = project.tasks.findByName("createSeparateZip")
        if (createZipTask != null) {
            createZipTask.appendix = archivesBaseName
            createZipTask.from versionDir()
        }

        // Copy instrumentation test APK into the dist dir
        def assembleTestTask = project.tasks.findByPath('assembleAndroidTest')
        if (assembleTestTask != null) {
            assembleTestTask.doLast {
                // If the project actually has some instrumentation tests, copy its APK
                if (!project.android.sourceSets.androidTest.java.sourceFiles.isEmpty()) {
                    def pkgTask = project.tasks.findByPath('packageDebugAndroidTest')
                    copy {
                        from(pkgTask.outputFile)
                        into(rootProject.ext.testApkDistOut)
                    }
                }
            }
        }
    }

    project.afterEvaluate { p ->
        // remove dependency on the test so that we still get coverage even if some tests fail
        p.tasks.findAll { it instanceof JacocoReportTask}.each { task ->
            def toBeRemoved = new ArrayList()
            def dependencyList = task.taskDependencies.values
            dependencyList.each { dep ->
                if (dep instanceof String) {
                    def t = tasks.findByName(dep)
                    if (t instanceof DeviceProviderInstrumentTestTask) {
                        toBeRemoved.add(dep)
                        task.mustRunAfter(t)
                    }
                }
            }
            toBeRemoved.each { dep ->
                dependencyList.remove(dep)
            }
        }
    }

    project.afterEvaluate { p ->
        if (p.hasProperty('android')
                && p.android.hasProperty('libraryVariants')
                && !(p.android.hasProperty('noDocs') && p.android.noDocs)) {
            p.android.libraryVariants.all { v ->
                if (v.name == 'release') {
                    registerForDocsTask(rootProject.generateDocs, p, v)
                    registerForDocsTask(rootProject.generateApi, p, v)
                }
            }
        }
    }
}

project.gradle.buildFinished { buildResult ->
    if (buildResult.getFailure() != null) {
        println()
        println 'Build failed. Possible causes include:'
        println '    1) Bad codes'
        println '    2) Out of date prebuilts in prebuilts/sdk'
        println '    3) Need to update the compileSdkVersion in a library\'s build.gradle'
        println()
    }
}
