// Copyright 2020 the original author or authors.
//
// 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.
[[fine_tuning_project_layout]]
= Fine Tuning the Project Layout

A multi-project build is a build where you build more than one project during a single execution of Gradle.
You have to declare the projects taking part in the multi-project build in the settings file.


[[sub:project_locations]]
== Project locations

Multi-project builds are always represented by a tree with a single root.
Each element in the tree represents a project.
A project has a path which denotes the position of the project in the multi-project build tree.
In most cases the project path is consistent with the physical location of the project in the file system.
However, this behavior is configurable. The project tree is created in the `settings.gradle` file.
The location of the settings file is also the location of the root project.

[[sub:building_the_tree]]
== Building the tree

In the settings file you can use the `include` method to build the project tree.

.Project layout
====
include::sample[dir="snippets/multiproject/standardLayouts/kotlin",files="settings.gradle.kts[tags=hierarchical-layout]"]
include::sample[dir="snippets/multiproject/standardLayouts/groovy",files="settings.gradle[tags=hierarchical-layout]"]
====

The `include` method takes project paths as arguments.
The project path is assumed to be equal to the relative physical file system path.
For example, a path 'services:api' is mapped by default to a folder 'services/api' (relative from the project root).
You only need to specify the leaves of the tree.
This means that the inclusion of the path 'services:hotels:api' will result in creating 3 projects: 'services', 'services:hotels' and 'services:hotels:api'.
More examples of how to work with the project path can be found in the DSL documentation of link:{groovyDslPath}++/org.gradle.api.initialization.Settings.html#org.gradle.api.initialization.Settings:include(java.lang.String[])++[Settings.include(java.lang.String[\])].


[[sub:modifying_element_of_the_project_tree]]
== Modifying elements of the project tree

The multi-project tree created in the settings file is made up of so called _project descriptors_.
You can modify these descriptors in the settings file at any time.
To access a descriptor you can do:

.Lookup of elements of the project tree
====
include::sample[dir="snippets/multiproject/customLayout/kotlin",files="settings.gradle.kts[tags=lookup-project]"]
include::sample[dir="snippets/multiproject/customLayout/groovy",files="settings.gradle[tags=lookup-project]"]
====

Using this descriptor you can change the name, project directory and build file of a project.

.Modification of elements of the project tree
====
include::sample[dir="snippets/multiproject/customLayout/kotlin",files="settings.gradle.kts[tags=change-project]"]
include::sample[dir="snippets/multiproject/customLayout/groovy",files="settings.gradle[tags=change-project]"]
====

Look at the link:{javadocPath}/org/gradle/api/initialization/ProjectDescriptor.html[ProjectDescriptor] class in the API documentation for more information.
