Standard Project Structure

Maven uses convention based approach, and hence, it defines a standard directory structure for the project to organize the files.

Familiarity with this structure is important for understanding how the project files are used by Maven to build and assemble the project.

Here is the video explaining these.

But why?

But, why limit ourselves to one project structure?

Because, this discipline allows you to be more productive. It might take a bit of time for you to get used to this structure, but the effort is worth it.

Prior to Maven, projects had very varied directory structure and if you worked on multiple projects, keeping track of files across these projects, would have been really difficult.

Maven made all of this simpler, by having a consistent project structure across projects. So, even if you moved to a different organization or worked on an open source project, you will feel completely at home and navigating the project files would be a walk in the park.

With this consistent project structure, Maven plugins can easily assume the location of certain files that they need for execution. That means you can just include the plugin and they will just work, out of the box. You don’t need to configure anything specific for most cases. It really, really reduces the time to get your builds running.

Let’s now look at a standard directory structure for a Maven Project.

Maven Configuration File - pom.xml

The first and foremost, maven configuration file - pom.xml. This should be located in your project’s root directory or project’s home directory.

In this directory, you also will have src folder that will contain all the files that, Maven plugins will use.

Below, is the example of the project’s home directory.

-> tree . -L 1
.
β”œβ”€β”€ pom.xml
└── src

Let’s see how src folder is laid out, to store the files.

Source Code Files in src

For all of your Application code files, they need to be placed inside the main directory of src. Within the main directory, you need to put the files inside the language specific folder.

So, your java files will be stored in src/main/java and your scala or kotlin files will be stored at src/main/scala or src/main/kotlin respectively.

Within each of these directories, you have your regular package structure, that is unique to your application.

Here is an example.

-> tree .
.
β”œβ”€β”€ pom.xml
└── src
    |  +-----------------------------------+
    └──|── main                            |
       |Β  β”œβ”€β”€ java                         |
       |Β  β”‚Β Β  └── io                       |
       |Β  β”‚Β Β      └── devjournal           |
       |Β  β”‚Β Β          └── maven            |
       |Β  β”‚Β Β              └── App.java     |
       |Β  β”œβ”€β”€ kotlin                       |
       |Β  └── scala                        |
       +-----------------------------------+

Application Config Files

For storing the application configuration files, like property configs, yaml configs, xml configs, or any other file that your application needs to use from classpath when its run, you need to store those in resources folder inside main directory.

So, full path is src/main/resources.

-> tree .
.
β”œβ”€β”€ pom.xml
└── src
    └───── main
        Β  β”œβ”€β”€ java
        Β  β”œβ”€β”€ kotlin
        Β  β”œβ”€β”€ scala
       +--|--------------------------------+
       |  └── resources                    |
     Β Β | Β Β  └── application.properties     |
       +-----------------------------------+

Web Application Files

If you working on a web application, you need to store your html, css, javascript, jsp, etc. They are stored in src/main/webapp. The directory structure inside webapp should confirm to Java Servlet Specification so that these can be packaged correctly and gets deployed correctly on Application servers.

-> tree .
.
β”œβ”€β”€ pom.xml
└── src
    └───── main
        Β  β”œβ”€β”€ java
        Β  β”œβ”€β”€ kotlin
        Β  β”œβ”€β”€ scala
          └── resources
       +--|--------------------------------+
       |Β  └── webapp                       |
       |Β      β”œβ”€β”€ META-INF                 |
       |Β      β”œβ”€β”€ resources                |
       |Β      β”‚Β Β  β”œβ”€β”€ css                  |
       |Β      β”‚Β Β  β”œβ”€β”€ images               |
       |Β      β”‚Β Β  └── js                   |
       |Β      └── WEB-INF                  |
       |Β          β”œβ”€β”€ jsp                  |
       |Β          └── web.xml              |
       +-----------------------------------+

Application Test Code Files

When we talk about files for testing, Maven expects these to be stored in a separate directory - test inside src folder.

And for Test class files for your source classes, the structure is similar to files under src/main. So, if you have application Java class files under src/main/java, then you need to place your test classes for these at src/test/java.

Similarly, for other language class files for scala, kotlin and groovy.

-> tree .
.
β”œβ”€β”€ pom.xml
└── src
    β”œβ”€β”€β”€β”€β”€ main
    |   Β  β”œβ”€β”€ java
    |   Β  β”œβ”€β”€ kotlin
    |   Β  β”œβ”€β”€ scala
    |     β”œβ”€β”€ resources
    |   Β  └── webapp
    |  +--------------------------------------+
    └──|─ test                                |
       |  β”œβ”€β”€ java                            |
       |  |   └── io                          |
       |  |       └── devjournal              |
       |  |           └── maven               |
       |  |               └── AppTest.java    |
       |  β”œβ”€β”€ kotlin                          |
       |  └── scala                           |
       +--------------------------------------+

Application Test Config Files

And if you require any test specific configuration files, then you need to store those in resources folder in your src/test folder. Again, similar to what the structure is for src/main.

-> tree .
.
β”œβ”€β”€ pom.xml
└── src
    β”œβ”€β”€β”€β”€β”€ main
    |   Β  β”œβ”€β”€ java
    |   Β  β”œβ”€β”€ kotlin
    |   Β  β”œβ”€β”€ scala
    |     β”œβ”€β”€ resources
    |   Β  └── webapp
    |
    └──── test
          β”œβ”€β”€ java
          β”œβ”€β”€ kotlin
          β”œβ”€β”€ scala
       +--|-------------------------------------+
       |  └── resources                         |
     Β Β | Β Β  └── application-test.properties     |
       +----------------------------------------+

Integration Test Code Files

If you have some integration tests that maven needs to run, Maven expects you to store these in a separate directory inside src. It is src/it, short form for integration test.

The directory structure of integration test folder is exactly similar to that of src/main or src/test. You get language specific folders to store your integration test class files and an additional resources folder to store any configuration files that you might need during the integration tests.

-> tree .
.
β”œβ”€β”€ pom.xml
└── src
    β”œβ”€β”€β”€β”€β”€ main
    β”œβ”€β”€β”€β”€β”€ test
    |  +-----------------------+
    └──|─ it                   |
       |  β”œβ”€β”€ java             |
       |  β”œβ”€β”€ kotlin           |
       |  β”œβ”€β”€ scala            |
       |  |                    |
       |  └── resources        |
       +-----------------------+

Generating a Site

As you know, Maven can generate a project site for your application. To facilitate this, maven expects you to store these files in a separate folder called site inside the src folder.

The site directory contains a site.xml that defines how Maven should build the site. To store the site pages, maven provides different folders for each supported markup language.

-> tree .
.
β”œβ”€β”€ pom.xml
└── src
    β”œβ”€β”€β”€β”€β”€ main
    β”œβ”€β”€β”€β”€β”€ test
    β”œβ”€β”€β”€β”€β”€ it
    |  +----------------------+
    └──|─ site                |
       |  β”œβ”€β”€ apt             |
       |  β”œβ”€β”€ fml             |
       |  β”œβ”€β”€ markdown        |
       |  β”œβ”€β”€ xdoc            |
       |  |                   |
       |  └── site.xml        |
       +----------------------+

Assembly Files

And finally, assembly directory that tells Maven how to assemble your project. Without specifying any assembly configuration, maven assembles the project based on the default packaging from pom.xml.

But if you want to assemble your project differently, you can define the configuration in the assembly directory, and provide the configuration file to the maven-assembly plugin.

-> tree .
.
β”œβ”€β”€ pom.xml
└── src
    β”œβ”€β”€β”€β”€β”€ main
    β”œβ”€β”€β”€β”€β”€ test
    β”œβ”€β”€β”€β”€β”€ it
    β”œβ”€β”€β”€β”€β”€ site
    |  +-------------------------+
    └──|─ assembly               |
       |  └── distribution.xml   |
       +-------------------------+

And that is pretty much it. Again, adhering to Maven’s standard project structure streamlines project management and enhances productivity. By following these conventions, you can ensure consistency and ease of collaboration across different projects and teams.