/*
 * Copyright (C) 2016 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */


import android.support.SupportConfig

import static android.support.dependencies.DependenciesKt.*
import android.support.LibraryGroups
import android.support.LibraryVersions
import android.support.SupportLibraryExtension

apply plugin: android.support.SupportKotlinLibraryPlugin

def antlrOut = "$buildDir/generated/antlr/grammar-gen/"
sourceSets {
    main.java.srcDirs += 'src/main/grammar-gen'
    test.java.srcDirs += 'src/tests/kotlin'
    main.java.srcDirs += antlrOut
}

// Temporary hack to stop AS to adding two guavas into test's classpath
configurations.all {
    resolutionStrategy {
        force GUAVA
    }
}

dependencies {
    // taken from ButterKnife
    def logger = new com.android.build.gradle.internal.LoggerWrapper(project.logger)
    def sdkHandler = new com.android.build.gradle.internal.SdkHandler(project, logger)
    compile(project(":room:common"))
    compile(project(":room:migration"))
    compile(KOTLIN_STDLIB)
    compile(AUTO_COMMON)
    compile(JAVAPOET)
    compile(ANTLR)
    compile(XERIAL)
    compile(APACHE_COMMONS_CODEC)
    testCompile(GOOGLE_COMPILE_TESTING)
    testCompile project(":paging:common")
    testCompile(JUNIT)
    testCompile(INTELLIJ_ANNOTATIONS)
    testCompile(JSR250)
    testCompile(MOCKITO_CORE)
    testCompile fileTree(dir: "${sdkHandler.sdkFolder}/platforms/android-$SupportConfig.CURRENT_SDK_VERSION/",
            include : "android.jar")
    testCompile fileTree(dir: "${new File(project(":room:runtime").buildDir, "libJar")}",
            include : "*.jar")
    testCompile fileTree(dir: "${new File(project(":persistence:db").buildDir, "libJar")}",
            include : "*.jar")
    testCompile files(org.gradle.internal.jvm.Jvm.current().getToolsJar())
}

def generateAntlrTask = task('generateAntlrGrammar', type: JavaExec) {
    def outFolder = file(antlrOut)
    outputs.dir(outFolder)
    inputs.file("$projectDir/SQLite.g4")
    classpath configurations.runtime
    main "org.antlr.v4.Tool"
    args "SQLite.g4", "-visitor", "-o", new File(outFolder, "android/arch/persistence/room/parser").path,
            "-package", "android.arch.persistence.room.parser"
}

tasks.findByName("compileKotlin").dependsOn(generateAntlrTask)
tasks.findByName("compileKotlin").dependsOn(":room:runtime:jarDebug")
tasks.findByName("compileKotlin").dependsOn(":persistence:db:jarDebug")

supportLibrary {
    name = "Android Room Compiler"
    publish = true
    generateDocs = false
    mavenVersion = LibraryVersions.ROOM
    mavenGroup = LibraryGroups.ROOM
    inceptionYear = "2017"
    description = "Android Room annotation processor"
    url = SupportLibraryExtension.ARCHITECTURE_URL
}
