Project Layout of a Java Project

The default project layout of a Java project is following:

All output files of our build are created under the build directory. This directory contains the following subdirectories which are relevant to this blog post (there are other subdirectories too, but we will talk about them in the future):

Basic

plugins {
    id 'java'
}

sourceCompatibility = '1.8'
targetCompatibility = '1.8'
version = '1.2.1'

By applying the Java Plugin, you get a whole host of features:


Managing Dependencies

repositories {
    mavenCentral()
}

dependencies {
    implementation 'org.hibernate:hibernate-core:3.6.7.Final'
}


The Gradle terminology for the three elements is as follows:

You can find a more comprehensive glossary of dependency management terms here.

As far as configurations go, the main ones of interest are:

You can learn more about these and how they relate to one another in the plugin reference chapter.

Source Sets

Imagine you have a legacy project that uses an src directory for the production code and test for the test code. The conventional directory structure won’t work, so you need to tell Gradle where to find the source files. You do that via source set configuration.

Each source set defines where its source code resides, along with the resources and the output directory for the class files. You can override the convention values by using the following syntax:

sourceSets {
    main {
         java {
            srcDirs = ['src']
         }
    }

    test {
        java {
            srcDirs = ['test']
        }
    }
}


Samples

version '1.0-SNAPSHOT'

apply plugin: 'java'

sourceCompatibility = 1.11
targetCompatibility = 1.11

repositories {
    jcenter()
}

dependencies {
    testCompile project(":cipher")
    testCompile project(":is")
    testCompile group: 'javax.validation', name: 'validation-api', version: '2.0.1.Final'
    testCompile 'com.google.protobuf:protobuf-java:3.6.1'
    testCompile group: 'junit', name: 'junit', version: '4.12'
    testCompile('org.testcontainers:testcontainers:1.10.5')
    testCompile('org.assertj:assertj-core:3.8.0')
    testCompile('io.rest-assured:rest-assured:3.0.3')
    testCompile('io.rest-assured:json-schema-validator:3.0.3')
    testCompile('io.rest-assured:json-path:3.0.3')
    testCompile('ch.qos.logback:logback-classic:1.2.3')
    testCompile('io.cucumber:cucumber-java8:4.7.1')
    testCompile('io.cucumber:cucumber-junit:4.7.1')
    testCompile('io.cucumber:cucumber-picocontainer:3.0.2')
    testCompile('org.bouncycastle:bcprov-jdk15on:1.60')
    testCompile('com.auth0:java-jwt:3.4.0')
    testCompile('org.apache.commons:commons-lang3:3.7')
    testCompile('org.mock-server:mockserver-client-java:5.5.1')
    testCompile group: 'com.rabbitmq', name: 'amqp-client', version: '5.5.2'
    testCompile group: 'org.json', name: 'json', version: '20180813'
    testCompile group: 'commons-cli', name: 'commons-cli', version: '1.4'
}

task testJar(type: Jar) {
    from { configurations.testCompile.collect { it.isDirectory() ? it : zipTree(it) } }
    from sourceSets.test.output.classesDirs
    from sourceSets.test.resources
    jar

    exclude "META-INF/*.SF"
    exclude "META-INF/*.DSA"
    exclude "META-INF/*.RSA"

}

task copyBVTDockerfile(type: Copy) {
    from 'src/main/docker'
    into 'build/libs'
}


task buildBVTDockerImage(type: Exec) {
    workingDir "build/libs"
    commandLine "docker", "build", "--build-arg", "VERSION=${project.version}", "--tag", "${rootProject.name}/${project.name}:${project.version}", "./"
}

testJar.dependsOn(testClasses)

buildBVTDockerImage.dependsOn(copyBVTDockerfile,testJar)
build.dependsOn(buildBVTDockerImage)


References

ReferenceURL
Building Java & JVM projectshttps://docs.gradle.org/current/userguide/building_java_projects.html