buildscript {
  repositories {
    mavenCentral()
  }
  dependencies {
    classpath 'de.obqo.gradle:gradle-lesscss-plugin:1.0-1.3.3'
  }
}

apply plugin: 'java'
apply plugin: 'eclipse'
apply plugin: 'lesscss'

defaultTasks 'dist'

/**
 * Helper that calls a command and returns the output
 */
def cmdCaller = { commandln ->
    def stdout = new ByteArrayOutputStream()
    exec {
        commandLine commandln
        standardOutput = stdout
    }

    return stdout.toString().trim()
}

/**
 * Git version name from git tag
 */
def getVersionName = { ->
    return cmdCaller(['git', 'describe', '--tags', '--abbrev=0'])
}

version = getVersionName()
archivesBaseName = 'azkaban'
check.dependsOn.remove(test)

repositories {
  mavenCentral()
  mavenLocal()
}

configurations {
    all {
        // We don't want the kitchen sink for dependencies. Only the ones we
        // know we need for compile and ones we need to package.
        transitive = false
    }
    compile {
        description = 'compile classpath'
    }
    generateRestli {
        transitive = true
    }
    test {
        extendsFrom compile
    }
}

ext.pegasusVersion = '1.15.7'

dependencies {
  compile (
    [group: 'commons-collections', name:'commons-collections', version: '3.2.1'],
    [group: 'commons-configuration', name:'commons-configuration', version: '1.8'],
    [group: 'commons-codec', name:'commons-codec', version: '1.9'],
    [group: 'commons-dbcp', name:'commons-dbcp', version: '1.4'],
    [group: 'commons-dbutils', name:'commons-dbutils', version: '1.5'],
    [group: 'org.apache.commons', name:'commons-email', version: '1.2'],
    [group: 'commons-fileupload', name:'commons-fileupload', version: '1.2.1'],
    [group: 'commons-io', name:'commons-io', version: '2.4'],
    [group: 'org.apache.commons', name:'commons-jexl', version: '2.1.1'],
    [group: 'commons-lang', name:'commons-lang', version: '2.6'],
    [group: 'commons-logging', name:'commons-logging', version: '1.1.1'],
    [group: 'commons-pool', name:'commons-pool', version: '1.6'],
    [group: 'com.google.guava', name:'guava', version: '13.0.1'],
    [group: 'com.h2database', name:'h2', version: '1.3.170'],
    [group: 'org.apache.httpcomponents', name: 'httpclient', version: '4.2.1'],
    [group: 'org.apache.httpcomponents', name:'httpcore', version: '4.2.1'],
    [group: 'org.codehaus.jackson', name:'jackson-core-asl', version: '1.9.5'],
    [group: 'org.codehaus.jackson', name:'jackson-mapper-asl',version: '1.9.5'],
    [group: 'org.mortbay.jetty', name:'jetty', version: '6.1.26'],
    [group: 'org.mortbay.jetty', name:'jetty-util', version: '6.1.26'],
    [group: 'joda-time', name:'joda-time', version: '2.0'],
    [group: 'net.sf.jopt-simple', name:'jopt-simple', version: '4.3'],
    [group: 'log4j', name:'log4j', version: '1.2.16'],
    [group: 'javax.mail', name:'mail', version: '1.4.5'],
    [group: 'mysql', name:'mysql-connector-java', version: '5.1.28'],
    [group: 'javax.servlet', name:'servlet-api', version: '2.5'],
    [group: 'org.slf4j', name:'slf4j-api', version: '1.6.1'],
    [group: 'org.apache.velocity', name:'velocity', version: '1.7'],
    [group: 'com.linkedin.pegasus', name: 'gradle-plugins', version: pegasusVersion],
    [group: 'com.linkedin.pegasus', name: 'pegasus-common', version: pegasusVersion],
    [group: 'com.linkedin.pegasus', name: 'restli-common', version: pegasusVersion],
    [group: 'com.linkedin.pegasus', name: 'restli-server', version: pegasusVersion],
    [group: 'com.linkedin.pegasus', name: 'data', version: pegasusVersion],
    [group: 'com.linkedin.pegasus', name: 'r2', version: pegasusVersion],
    [group: 'com.linkedin.pegasus', name: 'li-jersey-uri', version: pegasusVersion],
    [group: 'com.linkedin.parseq', name: 'parseq', version: '1.3.7'],
    [group: 'com.fasterxml.jackson.core', name: 'jackson-core', version: '2.3.2']
  )

  generateRestli (
      [group: 'com.linkedin.pegasus', name:'generator', version: pegasusVersion],
      [group: 'com.linkedin.pegasus', name:'restli-tools', version: pegasusVersion]
  )

  testCompile (
    [group: 'junit', name:'junit', version: '4.11'],
    [group: 'org.hamcrest', name:'hamcrest-all', version: '1.3']
  )
}

sourceSets {
    main {
        java {
            srcDirs 'src/main/java', 'src/restli/generatedJava', 'src/restli/java'
        }
    }
    test {
        java {
            srcDirs 'unit/java'
        }
    }
}

jar {
    baseName =  'azkaban'
    manifest {
      attributes(
        'Implementation-Title': 'Azkaban',
        'Implementation-Version': version
      )
    }
}

task restliTemplateGenerator(type: JavaExec) {
    mkdir 'src/restli/generatedJava'

    main = 'com.linkedin.pegasus.generator.PegasusDataTemplateGenerator'
    args = ['src/restli/generatedJava','src/restli/schemas']
    classpath = configurations.generateRestli
}

task restliRestSpecGenerator(dependsOn: [restliTemplateGenerator], type: JavaExec) << {
    mkdir 'src/restli/generatedRestSpec'

    main = 'com.linkedin.restli.tools.idlgen.RestLiResourceModelExporterCmdLineApp'
    args = ['-outdir', 'src/restli/generatedRestSpec', '-sourcepath', 'src/restli/java']
    classpath = configurations.generateRestli
}

task restli(dependsOn: restliTemplateGenerator) << {
}

compileJava.dependsOn.add('restli')

eclipse.classpath.file {
    // Erase the whole classpath
    beforeMerged {
        classpath -> classpath.entries.removeAll { entry -> true }
    }

    // We want to make sure that if there is an entry for src, that it doesn't
    // have any include parameters
    whenMerged { classpath ->
        classpath.entries.findAll { entry -> entry.kind == 'src' }*.includes = []
    }
}

lesscss {
  source = fileTree('src/main/less') {
    include 'azkaban.less'
    include 'azkaban-graph.less'
  }
  dest = 'build/web/css'
}

/**
 * Invokes a makefile target that will compile dust files
 */
task compileDust(type:Exec) {
    workingDir 'src/main/tl'
    commandLine 'make', '-e'
    environment (
      OBJ_DIR : file(new File(buildDir,'/dust'))
    )
}

/**
 * Copies web files to a build directory
 */
task web(dependsOn: ['lesscss', 'compileDust']) << {
    println 'Copying web files'
    copy {
        from('src/web')
        into('build/web')
    }
    copy {
        from('build/dust')
        into('build/web/js')
    }
}

/*
 * Gets the version name from the latest Git tag
 */
task createVersionFile() << {
    String gitCommitHash = cmdCaller(['git', 'rev-parse', 'HEAD']);
    String gitRepo = cmdCaller(['git', 'config', '--get', 'remote.origin.url']);
    def date = new Date()
    def formattedDate = date.format('yyyy-MM-dd hh:mm zzz')

    String versionStr = version + '\n' +
                        gitCommitHash + '\n' +
                        gitRepo + '\n' +
                        formattedDate + '\n'

    File versionFile = file('build/package/version.file')
    versionFile.parentFile.mkdirs()
    versionFile.write(versionStr)
}

ext.soloAppendix = 'solo-server'
ext.soloPackageDir = 'build/package/' + jar.baseName + '-' + soloAppendix

/**
 * Copies the Azkaban Solo Server files into its package directory.
 */
task copySolo(dependsOn: ['jar', 'web', 'createVersionFile']) << {
    delete soloPackageDir
    mkdir soloPackageDir

    println 'Creating Azkaban Solo Server Package into ' + soloPackageDir
    mkdir soloPackageDir + '/lib'
    mkdir soloPackageDir + '/extlib'
    mkdir soloPackageDir + '/plugins'

    copy {
        println 'Copying Soloserver bin & conf'
        from('src/package/soloserver')
        into(soloPackageDir)
    }

    copy {
        println 'Copying Azkaban lib'
        from('build/libs')
        into(soloPackageDir + '/lib')
    }

    copy {
        println 'Copying web'
        from('build/web')
        into(soloPackageDir + '/web')
    }

    copy {
        println 'Copying sql'
        from('src/sql')
        into(soloPackageDir + '/sql')
    }

    copy {
        println 'Copying dependency jars'
        into soloPackageDir + '/lib'
        from configurations.compile
    }

    copy {
        println 'Copying version file'
        into soloPackageDir
        from 'build/package/version.file'
    }
}

/**
 * Packages the SoloServer version of Azkaban
 */
task packageSolo(type: Tar, dependsOn: 'copySolo') {
    appendix = soloAppendix
    extension = 'tar.gz'
    compression = Compression.GZIP

    ext.basedir = baseName + '-' + appendix + '-' + version
    into(basedir) {
        from soloPackageDir
        exclude 'bin'
    }

    ext.dst_bin = basedir + '/bin'
    ext.src_bin = soloPackageDir + '/bin'
    from(src_bin) {
        into dst_bin
        fileMode = 0755
    }
}

ext.sqlPackageDir = 'build/package/sql'

/**
 * Copies the SQL files into its package directory.
 */
task copySql() << {
    println 'Creating Azkaban SQL Scripts into ' + sqlPackageDir
    delete sqlPackageDir
    mkdir sqlPackageDir

    copy {
        println 'Copying SQL files'
        from('src/sql')
        into(sqlPackageDir)
    }

    String destFile = sqlPackageDir + '/create-all-sql-' + version + '.sql';
    ant.concat(destfile:destFile, fixlastline:'yes') {
        println('Concating create scripts to ' + destFile)
        fileset(dir: 'src/sql') {
            exclude(name: 'update.*.sql')
            exclude(name: 'database.properties')
        }
    }
}

/**
 * Packages the Sql Scripts for Azkaban DB
 */
task packageSql(type: Tar, dependsOn: 'copySql') {
    extension = 'tar.gz'
    compression = Compression.GZIP
    appendix = 'sql'

    ext.basedir = baseName + '-' + appendix + '-' + version
    into(basedir) {
        from sqlPackageDir
    }
}

ext.execAppendix = 'exec-server'
ext.execPackageDir = 'build/package/' + jar.baseName + '-' + execAppendix

/**
 * Copies the Azkaban Executor Server files into its package directory.
 */
task copyExec(dependsOn: ['jar', 'createVersionFile']) << {
    delete execPackageDir
    println 'Creating Azkaban Executor Server Package into ' + execPackageDir
    mkdir execPackageDir
    mkdir execPackageDir + '/lib'
    mkdir execPackageDir + '/extlib'
    mkdir execPackageDir + '/plugins'

    copy {
        println 'Copying Exec server bin & conf'
        from('src/package/execserver')
        into(execPackageDir)
    }

    copy {
        println 'Copying Azkaban lib '
        from('build/libs')
        into(execPackageDir + '/lib')
    }

    copy {
        println 'Copying dependency jars'
        into execPackageDir + '/lib'
        from configurations.compile
    }

    copy {
        into execPackageDir
        from 'build/package/version.file'
    }
}

/**
 * Packages the Azkaban Executor Server
 */
task packageExec(type: Tar, dependsOn: 'copyExec') {
    appendix = execAppendix
    extension = 'tar.gz'
    compression = Compression.GZIP

    ext.basedir = baseName + '-' + appendix + '-' + version
    into(basedir) {
        from execPackageDir
        exclude 'bin'
    }

    ext.dst_bin = basedir + '/bin'
    ext.src_bin = execPackageDir + '/bin'
    from(src_bin) {
        into dst_bin
        fileMode = 0755
    }
}

ext.webAppendix = 'web-server'
ext.webPackageDir = 'build/package/' + jar.baseName + '-' + webAppendix

/**
 * Copies the Azkaban Web Server files into its package directory.
 */
task copyWeb(dependsOn: ['jar', 'web', 'createVersionFile']) << {
    println 'Creating Azkaban Web Server Package into ' + webPackageDir
    delete webPackageDir
    mkdir webPackageDir
    mkdir webPackageDir + '/lib'
    mkdir webPackageDir + '/extlib'
    mkdir webPackageDir + '/plugins'

    println 'Copying Web server bin & conf'
    copy {
        from('src/package/webserver')
        into(webPackageDir)
    }

    println 'Copying Azkaban lib '
    copy {
        from('build/libs')
        into(webPackageDir + '/lib')
    }

    println 'Copying web'
    copy {
        from('build/web')
        into(webPackageDir + '/web')
    }

    println 'Copying dependency jars'
    copy {
        into webPackageDir + '/lib'
        from configurations.compile
    }

    copy {
        into webPackageDir
        from 'build/package/version.file'
    }
}

/**
 * Packages the Azkaban Web Server
 */
task packageWeb(type: Tar, dependsOn: 'copyWeb') {
    appendix = webAppendix
    extension = 'tar.gz'
    compression = Compression.GZIP

    ext.basedir = baseName + '-' + appendix + '-' + version
    into(basedir) {
        from webPackageDir
        exclude 'bin'
    }

    ext.dst_bin = basedir + '/bin'
    ext.src_bin = webPackageDir + '/bin'
    from(src_bin) {
        into dst_bin
        fileMode = 0755
    }
}

task packageAll(dependsOn: ['packageWeb',
                            'packageExec',
                            'packageSolo',
                            'packageSql']) {
}

task dist(dependsOn: 'packageAll') {
}

task wrapper(type: Wrapper) {
    gradleVersion = '1.11'
}
