// Copyright (C) 2024 Gradle, Inc.
//
// Licensed under the Creative Commons Attribution-Noncommercial-ShareAlike 4.0 International License.;
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//      https://creativecommons.org/licenses/by-nc-sa/4.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.

[[service_injection]]
= Services and Service Injection
:keywords: services, service, injection, inject

Gradle exposes a set of _services_, covering things like file and archive operations, process execution, dependency creation, worker scheduling, problem reporting, build-feature flags, and dataflow scheduling.

A *service* is a collaborator object whose lifecycle Gradle manages; a single instance is shared across the build and supplied to your code on demand.
These services aren't meant to be constructed directly, since they rely on internal Gradle state.

To use a *service*, your custom type declares a dependency on it and Gradle supplies the instance.
This pattern is called _service injection_, and it works uniformly across every type Gradle instantiates for you, including tasks, plugins, extensions, value sources, build services, and worker actions.

The most common form is constructor injection on an abstract type.
The same `CleanTempTask` is shown below as a Kotlin DSL class, a Groovy DSL class, and a stand-alone Java class that you would typically place in `buildSrc` or a binary plugin:

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="build.gradle.kts[tags=clean-temp-inject]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="build.gradle[tags=clean-temp-inject]"]
include::sample[dir="snippets/reference/gradle-types/services/kotlin/buildSrc/src/main/java/org/example",files="CleanTempTask.java[tags=clean-temp-inject]"]
====

A task that needs to run work in parallel injects the link:{javadocPath}/org/gradle/workers/WorkerExecutor.html[`WorkerExecutor`] service in the same way, as shown in the <<worker_api.adoc#worker_api,worker API>> section.

Reaching for service injection rather than `project.copy(...)`, `project.exec(...)`, or other ad-hoc `Project` accessors helps keep your code compatible with the <<configuration_cache.adoc#config_cache,Configuration Cache>> and <<isolated_projects.adoc#isolated_projects,Isolated Projects>>, and makes your types easier to unit-test by passing stub services.
See <<#service_injection_patterns,Service injection patterns>> for the full set of `@Inject` forms used in the rest of this page.

[[services_for_injection]]
== Available services

WARNING: You should avoid injecting types not listed below. Internal services can sometimes technically be injected, but this practice is not supported and may lead to breaking changes in the future.
Only inject the services explicitly listed below to ensure stability and compatibility.

The following services are available for injection in all Gradle instantiated objects:

[%header,cols="1,4"]
|===
| Service | Description

| <<objectfactory,`ObjectFactory`>>
| Creates model objects, properties, collections, and file-related objects. Use it when defining custom Gradle types or nested DSL objects in a plugin or extension.

| <<providerfactory,`ProviderFactory`>>
| Creates `Provider` instances and exposes environment, system-property, and Gradle-property values. Use it to read environment variables, system properties, or to wrap a computed value as a lazy `Provider`.

| <<filesystemoperations,`FileSystemOperations`>>
| Runs filesystem operations such as deleting, copying, or syncing files and directories. Use it from a task or worker action that needs to delete, copy, or sync files.

| <<archiveoperations,`ArchiveOperations`>>
| Runs operations on archive files such as ZIP or TAR. Use it to read or extract the contents of an archive.

| <<execoperations,`ExecOperations`>>
| Runs external processes, with dedicated support for running external `java` programs. Use it to run an external program or `java` process from a task or worker action.

| <<problems,`Problems`>> incubating-label:[]
| Reports structured problems that surface in the console, the HTML problems report, and the Tooling API. Use it to surface errors or warnings consistently to the IDE, the problems report, and Build Scan.
|===

=== Additional services in workers

The following services are available for injection in worker API actions and parameters:

[%header,cols="1,4"]
|===
| Service | Description

| <<workerexecutor,`WorkerExecutor`>>
| Schedules work to run in parallel via the Worker API. Use it from a task that needs to run CPU-bound work in parallel or in an isolated classloader.
|===

=== Additional services in projects and settings

The following services are available for injection in both project and settings plugins, extensions and objects:

[%header,cols="1,4"]
|===
| Service | Description

| <<toolingmodelbuilderregistry,`ToolingModelBuilderRegistry`>>
| Registers a Gradle Tooling API model builder. Use it to expose a custom model to the Tooling API so IDEs and other tools can consume it.

| <<dependencyfactory,`DependencyFactory`>>
| Creates `Dependency` instances in a type-safe way. Use it to programmatically construct `Dependency` instances in a plugin without a `Project` reference.

| <<dependencyconstraintfactory,`DependencyConstraintFactory`>> incubating-label:[]
| Creates `DependencyConstraint` instances in a type-safe way. Use it to programmatically construct dependency constraints in a plugin without a `Project` reference.

| <<buildfeatures,`BuildFeatures`>>
| Reports whether features such as Configuration Cache and Isolated Projects are requested and active. Use it to branch plugin logic on whether the Configuration Cache or Isolated Projects is active.

| <<flow_services,`FlowScope` and `FlowProviders`>> incubating-label:[]
| Register dataflow actions that run on build lifecycle events such as build completion. Use them to run cleanup, notification, or reporting work at the end of every build.

| <<buildinvocationdetails,`BuildInvocationDetails`>> incubating-label:[]
| Exposes information about the current build invocation, such as its wall-clock start time. Use it to read the build's start time for timing or reporting.
|===

=== Additional services in projects

The following services are available for injection in project plugins, extensions and objects created in a project:

[%header,cols="1,4"]
|===
| Service | Description

| <<sec:projectlayout,`ProjectLayout`>>
| Provides access to key project locations such as the project directory and build directory. Use it to resolve paths relative to the project directory or build directory.

| <<workerexecutor,`WorkerExecutor`>>
| Schedules work to run in parallel via the Worker API. Use it from a task that needs to run CPU-bound work in parallel or in an isolated classloader.

| <<testeventreporterfactory,`TestEventReporterFactory`>> incubating-label:[]
| Provides access to Gradle's test event reporting API. Use it to emit test events from a custom task that runs tests itself.

| <<softwarecomponentfactory,`SoftwareComponentFactory`>>
| Creates adhoc software components for publishing. Use it to define a custom publishable software component without a full component model.
|===

=== Additional services in settings

The following services are available for injection in settings plugins, extensions and objects created in a settings script:

[%header,cols="1,4"]
|===
| Service | Description

| <<buildlayout,`BuildLayout`>>
| Provides access to important locations for a Gradle build, such as the root directory and settings file. Use it from a settings plugin to resolve paths relative to the root settings directory.
|===

[[objectfactory]]
== `ObjectFactory`

link:{javadocPath}/org/gradle/api/model/ObjectFactory.html[`ObjectFactory`] is a service for creating custom Gradle types, allowing you to define nested objects and DSLs in your build logic.
It provides methods for creating instances of different types, such as properties (`Property<T>`), collections (`ListProperty<T>`, `SetProperty<T>`, `MapProperty<K, V>`), file-related objects (`RegularFileProperty`, `DirectoryProperty`, `ConfigurableFileCollection`, `ConfigurableFileTree`), and more.

You can obtain an instance of `ObjectFactory` using the `project.objects` property.
Here's a simple example demonstrating how to use `ObjectFactory` to create a property and set its value:

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="build.gradle.kts[tags=object-factory]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="build.gradle[tags=object-factory]"]
====

TIP: It is preferable to let Gradle create objects automatically by using <<properties_providers.adoc#managed_properties,managed properties>>.

Using `ObjectFactory` to create these objects ensures that they are properly managed by Gradle, especially in terms of configuration avoidance and lazy evaluation.
This means that the values of these objects are only calculated when needed, which can improve build performance.

In the following example, a project extension called `DownloadExtension` receives an `ObjectFactory` instance through its constructor.
The constructor uses this to create a nested `Resource` object (also a custom Gradle type) and makes this object available through the `resource` property:

[source,java]
.DownloadExtension.java
----
include::{snippetsPath}/reference/plugin-development/nestedObjects/groovy/buildSrc/src/main/java/DownloadExtension.java[tags=download-extension]
include::{snippetsPath}/reference/plugin-development/nestedObjects/groovy/buildSrc/src/main/java/Resource.java[tags=resource]
----

Here is another example using `javax.inject.Inject`:

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="build.gradle.kts[tags=object-factory-inject]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="build.gradle[tags=object-factory-inject]"]
====

The `MyObjectFactoryTask` task uses an `ObjectFactory` instance, which is injected into the task's constructor using the `@Inject` annotation.

[[sec:projectlayout]]
== `ProjectLayout`

link:{groovyDslPath}/org.gradle.api.file.ProjectLayout.html[`ProjectLayout`] is a service that provides access to the layout of a Gradle project's directories and files.
It's part of the `org.gradle.api.file` package and allows you to query the project's layout to get information about source sets, build directories, and other file-related aspects of the project.

You can obtain a `ProjectLayout` instance from a `Project` object using the `project.layout` property.
Here's a simple example:

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="build.gradle.kts[tags=project-layout]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="build.gradle[tags=project-layout]"]
====

Here is an example using `javax.inject.Inject`:

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="build.gradle.kts[tags=project-layout-inject]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="build.gradle[tags=project-layout-inject]"]
====

The `MyProjectLayoutTask` task uses a `ProjectLayout` instance, which is injected into the task's constructor using the `@Inject` annotation.

[[buildlayout]]
== `BuildLayout`

link:{groovyDslPath}/org.gradle.api.file.BuildLayout.html[`BuildLayout`] is a service that provides access to the root and settings directory in a Settings plugin or a Settings script, it is analogous to `ProjectLayout`.
It's part of the `org.gradle.api.file` package to access standard build-wide file system locations as lazily computed value.

NOTE: These APIs are currently incubating but eventually should replace existing accessors in Settings, which return eagerly computed locations: +
`Settings.rootDir` -> `Settings.layout.rootDirectory` +
`Settings.settingsDir` -> `Settings.layout.settingsDirectory`

You can obtain a `BuildLayout` instance from a `Settings` object using the `settings.layout` property.
Here's a simple example:

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="settings.gradle.kts[tags=build-layout]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="settings.gradle[tags=build-layout]"]
====

Here is an example using `javax.inject.Inject`:

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="settings.gradle.kts[tags=build-layout-inject]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="settings.gradle[tags=build-layout-inject]"]
====

This code defines a `MyBuildLayoutPlugin` plugin that implements the `Plugin` interface for the `Settings` type.
The plugin expects a `BuildLayout` instance to be injected into its constructor using the `@Inject` annotation.

[[providerfactory]]
== `ProviderFactory`

link:{groovyDslPath}/org.gradle.api.provider.ProviderFactory.html[`ProviderFactory`] is a service that provides methods for creating different types of providers.
Providers are used to model values that may be computed lazily in your build scripts.

The `ProviderFactory` interface provides methods for creating various types of providers, including:

- `provider(Callable<T> value)` to create a provider with a value that is lazily computed based on a `Callable`.
- `provider(Provider<T> value)` to create a provider that simply wraps an existing provider.
- `property(Class<T> type)` to create a property provider for a specific type.
- `gradleProperty(Class<T> type)` to create a property provider that reads its value from a Gradle project property.

Here's a simple example demonstrating the use of `ProviderFactory` using `project.providers`:

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="build.gradle.kts[tags=provider-factory]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="build.gradle[tags=provider-factory]"]
====

The task named `printMessage` uses the `ProviderFactory` to create a `provider` that supplies the message string.

Here is an example using `javax.inject.Inject`:

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="build.gradle.kts[tags=provider-factory-inject]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="build.gradle[tags=provider-factory-inject]"]
====

The `ProviderFactory` service is injected into the `MyProviderFactoryTask` task's constructor using the `@Inject` annotation.

[[workerexecutor]]
== `WorkerExecutor`

link:{javadocPath}/org/gradle/workers/WorkerExecutor.html[`WorkerExecutor`] is a service that allows you to perform parallel execution of tasks using worker processes.
This is particularly useful for tasks that perform CPU-intensive or long-running operations, as it allows them to be executed in parallel, improving build performance.

Using `WorkerExecutor`, you can submit units of work (called actions) to be executed in separate worker processes.
This helps isolate the work from the main Gradle process, providing better reliability and performance.

Here's a basic example of how you might use `WorkerExecutor` in a build script:

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="build.gradle.kts[tags=worker-executor]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="build.gradle[tags=worker-executor]"]
====

See <<worker_api.adoc#worker_api,the worker API>> for more details.

[[filesystemoperations]]
== `FileSystemOperations`

link:{javadocPath}/org/gradle/api/file/FileSystemOperations.html[`FileSystemOperations`] is a service that provides methods for performing file system operations such as copying, deleting, and syncing.
It is part of the `org.gradle.api.file` package and is typically used in custom tasks or plugins to interact with the file system.

Here is an example using `javax.inject.Inject`:

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="build.gradle.kts[tags=file-system-inject]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="build.gradle[tags=file-system-inject]"]
====

The `FileSystemOperations` service is injected into the `MyFileSystemOperationsTask` task's constructor using the `@Inject` annotation.

With some ceremony, it is possible to use `FileSystemOperations` in an ad-hoc task defined in a build script:

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="build.gradle.kts[tags=file-system-adhoc]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="build.gradle[tags=file-system-adhoc]"]
====

First, you need to declare an interface with a property of type `FileSystemOperations`, here named `InjectedFsOps`, to serve as an injection point.
Then call the method link:{javadocPath}/org/gradle/api/model/ObjectFactory.html#newInstance(java.lang.Class,java.lang.Object%2E%2E%2E)[`ObjectFactory.newInstance`] to generate an implementation of the interface that holds an injected service.

TIP: This is a good time to consider extracting the ad-hoc task into a proper class.

[[archiveoperations]]
== `ArchiveOperations`

link:{javadocPath}/org/gradle/api/file/ArchiveOperations.html[`ArchiveOperations`] is a service that provides methods for accessing the contents of archives, such as ZIP and TAR files.
It is part of the `org.gradle.api.file` package and is typically used in custom tasks or plugins to unpack archive files.

Here is an example using `javax.inject.Inject`:

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="build.gradle.kts[tags=archive-op-inject]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="build.gradle[tags=archive-op-inject]"]
====

The `ArchiveOperations` service is injected into the `MyArchiveOperationsTask` task's constructor using the `@Inject` annotation.

With some ceremony, it is possible to use `ArchiveOperations` in an ad-hoc task defined in a build script:

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="build.gradle.kts[tags=archive-op-adhoc]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="build.gradle[tags=archive-op-adhoc]"]
====

First, you need to declare an interface with a property of type `ArchiveOperations`, here named `InjectedArcOps`, to serve as an injection point.
Then call the method link:{javadocPath}/org/gradle/api/model/ObjectFactory.html#newInstance(java.lang.Class,java.lang.Object%2E%2E%2E)[`ObjectFactory.newInstance`] to generate an implementation of the interface that holds an injected service.

TIP: This is a good time to consider extracting the ad-hoc task into a proper class.

[[execoperations]]
== `ExecOperations`

link:{javadocPath}/org/gradle/process/ExecOperations.html[`ExecOperations`] is a service that provides methods for executing external processes (commands) from within a build script.
It is part of the `org.gradle.process` package and is typically used in custom tasks or plugins to run command-line tools or scripts as part of the build process.

Here is an example using `javax.inject.Inject`:

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="build.gradle.kts[tags=exec-op-inject]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="build.gradle[tags=exec-op-inject]"]
====

The `ExecOperations` is injected into the `MyExecOperationsTask` task's constructor using the `@Inject` annotation.

With some ceremony, it is possible to use `ExecOperations` in an ad-hoc task defined in a build script:

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="build.gradle.kts[tags=exec-op-adhoc]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="build.gradle[tags=exec-op-adhoc]"]
====

First, you need to declare an interface with a property of type `ExecOperations`, here named `InjectedExecOps`, to serve as an injection point.
Then call the method link:{javadocPath}/org/gradle/api/model/ObjectFactory.html#newInstance(java.lang.Class,java.lang.Object%2E%2E%2E)[`ObjectFactory.newInstance`] to generate an implementation of the interface that holds an injected service.

TIP: This is a good time to consider extracting the ad-hoc task into a proper class.

[[toolingmodelbuilderregistry]]
== `ToolingModelBuilderRegistry`

link:{javadocPath}/org/gradle/tooling/provider/model/ToolingModelBuilderRegistry.html[`ToolingModelBuilderRegistry`] is a service that allows you to register custom tooling model builders.
Tooling models are used to provide rich IDE integration for Gradle projects, allowing IDEs to understand and work with the project's structure, dependencies, and other aspects.

The `ToolingModelBuilderRegistry` interface is part of the `org.gradle.tooling.provider.model` package and is typically used in custom Gradle plugins that provide enhanced IDE support.

Here's a simplified example:

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="build.gradle.kts[tags=tooling-model]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="build.gradle[tags=tooling-model]"]
====

You can learn more at <<tooling_api.adoc#tooling_api,Tooling API>>.

[[testeventreporterfactory]]
== `TestEventReporterFactory` incubating-label:[]

link:{javadocPath}/org/gradle/api/tasks/testing/TestEventReporterFactory.html[`TestEventReporterFactory`] is a service that provides access to the test event reporting API.

You can learn more at <<test_reporting_api.adoc#test_reporting_api,Test Reporting API>>.

[[dependencyfactory]]
== `DependencyFactory`

link:{javadocPath}/org/gradle/api/artifacts/dsl/DependencyFactory.html[`DependencyFactory`] is a service that provides methods for creating dependencies in a type-safe way.

You can learn more in the <<implementing_gradle_plugins_binary.adoc#sec:differences_with_top_level_dependencies_plugins,Implementing Binary Plugins guide>>.

[[dependencyconstraintfactory]]
== `DependencyConstraintFactory` incubating-label:[]

link:{javadocPath}/org/gradle/api/artifacts/dsl/DependencyConstraintFactory.html[`DependencyConstraintFactory`] is a service that provides methods for creating link:{javadocPath}/org/gradle/api/artifacts/DependencyConstraint.html[`DependencyConstraint`] instances in a type-safe way.
It is the constraint-creation counterpart to <<dependencyfactory,`DependencyFactory`>> and is typically used by plugins that publish or consume dependency constraints.

The service is only available via `@Inject`, there is no project-level accessor.

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="build.gradle.kts[tags=dependency-constraint-factory-inject]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="build.gradle[tags=dependency-constraint-factory-inject]"]
====

The `CreateConstraintTask` task receives a `DependencyConstraintFactory` instance through its constructor using the `@Inject` annotation.

[[problems]]
== `Problems` incubating-label:[]

link:{javadocPath}/org/gradle/api/problems/Problems.html[`Problems`] is a service that allows tasks and plugins to report structured problems.
Reported problems surface in the console, the HTML <<reporting_problems.adoc#sec:generated_html_report,problems report>>, and through the <<tooling_api.adoc#tooling_api,Tooling API>>, so IDEs and Build Scan can render them consistently.

Obtain a link:{javadocPath}/org/gradle/api/problems/ProblemReporter.html[`ProblemReporter`] from the injected `Problems` service via `problems.getReporter()` and call `report()` (recoverable) or `throwing()` (fatal).

====
include::sample[dir="snippets/reference/plugin-development/reportingProblems/kotlin",files="plugin/src/main/kotlin/org/example/HelloProblemsPlugin.kt[tags=problems-service]"]
include::sample[dir="snippets/reference/plugin-development/reportingProblems/groovy",files="plugin/src/main/groovy/org/example/HelloProblemsPlugin.groovy[tags=problems-service]"]
====

You can learn more in the <<reporting_problems.adoc#sec:reporting_problems,Reporting Plugin Problems with the Problems API>> guide.

[[buildfeatures]]
== `BuildFeatures`

link:{javadocPath}/org/gradle/api/configuration/BuildFeatures.html[`BuildFeatures`] is a service that exposes the requested and active state of major Gradle features currently the <<configuration_cache.adoc#config_cache,Configuration Cache>> and <<isolated_projects.adoc#isolated_projects,Isolated Projects>>, so plugins can adapt their behavior accordingly.

A plugin can, for example, gate optional logic that is incompatible with Isolated Projects on the active state of that feature:

[source,java]
.MyPlugin.java
----
include::{snippetsPath}/reference/plugin-development/reactingToBuildFeatures/groovy/buildSrc/src/main/java/MyPlugin.java[tags=my-plugin]
----
<1> The `BuildFeatures` service can be injected into plugins, tasks, and other managed types.
<2> Use `getRequested()` to read the user's opt-in or opt-out, returning a `Provider<Boolean>` that may be empty when the user expressed no preference.
<3> Use `getActive()` to read whether the feature is actually active in the current build, returning a non-empty `Provider<Boolean>`.

You can learn more in the <<implementing_gradle_plugins_binary.adoc#sec:reacting_to_build_features,Implementing Binary Plugins guide>>.

[[flow_services]]
== `FlowScope` and `FlowProviders` incubating-label:[]

link:{javadocPath}/org/gradle/api/flow/FlowScope.html[`FlowScope`] and link:{javadocPath}/org/gradle/api/flow/FlowProviders.html[`FlowProviders`] are services that together let a plugin register <<dataflow_actions.adoc#dataflow_action,dataflow actions>> (isolated pieces of work that run when their input providers become available, such as at the end of a build).

`FlowScope` registers the actions; `FlowProviders` exposes build lifecycle events (such as the build work result) as `Provider` values that can be wired into action parameters. Both services are typically injected together into a project or settings plugin:

[source,java]
.SoundFeedbackPlugin.java
----
include::{snippetsPath}/reference/gradle-types/playSound/groovy/plugin/src/main/java/org/gradle/sample/sound/SoundFeedbackPlugin.java[tag=flow-action]
----
<1> Use service injection to obtain `FlowScope` and `FlowProviders` instances.
<2> Register an action in the `always` scope so it runs at the end of every build.
<3> Wire `FlowProviders.getBuildWorkResult()` into the action's parameters so the action receives the success-or-failure outcome.

You can learn more in the <<dataflow_actions.adoc#dataflow_action,Dataflow Actions>> reference.

[[buildinvocationdetails]]
== `BuildInvocationDetails` incubating-label:[]

link:{javadocPath}/org/gradle/api/invocation/BuildInvocationDetails.html[`BuildInvocationDetails`] is a service that exposes information about the current build invocation, most notably the wall-clock time at which the build was started.
It is useful for plugins that report build duration, emit timing metrics, or display a banner with the build's start time.

The service is only available via `@Inject`, there is no project-level accessor.

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="build.gradle.kts[tags=build-invocation-details-inject]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="build.gradle[tags=build-invocation-details-inject]"]
====

The `ReportBuildStartTask` task receives a `BuildInvocationDetails` instance through its constructor using the `@Inject` annotation.

[[softwarecomponentfactory]]
== `SoftwareComponentFactory`

link:{javadocPath}/org/gradle/api/component/SoftwareComponentFactory.html[`SoftwareComponentFactory`] is a service that lets a plugin create link:{javadocPath}/org/gradle/api/component/AdhocComponentWithVariants.html[`AdhocComponentWithVariants`] instances (adhoc software components built from outgoing variants) for publication via the <<publishing_setup.adoc#publishing_components,publishing plugins>>.
It is typically used by plugins that produce custom component types and want to publish them without defining a full component model.

The service is only available via `@Inject`, there is no project-level accessor.

====
include::sample[dir="snippets/reference/gradle-types/services/kotlin",files="build.gradle.kts[tags=software-component-factory-inject]"]
include::sample[dir="snippets/reference/gradle-types/services/groovy",files="build.gradle[tags=software-component-factory-inject]"]
====

The `CustomComponentPlugin` plugin receives a `SoftwareComponentFactory` instance through its constructor using the `@Inject` annotation, creates an adhoc component, and adds it to the project's components container so it can be referenced by a publication.

[[service_injection_patterns]]
== Service injection patterns

There are two ways that services can be provided to an object.

=== Constructor injection

A service can be injected into the constructor of the class. The constructor must be public and annotated with the `javax.inject.Inject` annotation.

Gradle uses the declared type of each constructor parameter to determine the services that the object requires.
The order of the constructor parameters and their names are not significant and can be whatever you like.

Here is an example that shows a task type that receives an `WorkerExecutor` via its constructor:

[source,java]
.Download.java
----
include::{snippetsPath}/reference/plugin-development/constructorServiceInjection/groovy/buildSrc/src/main/java/Download.java[tags=download]
----

[[property_injection]]
=== Property injection

A service can be injected by adding a property getter method annotated with the `javax.inject.Inject` annotation to the class.

Gradle defers the creation of the service until the getter method is called. This can be more performant than constructor injection.

The property getter method must be `public` or `protected`. Gradle uses the declared return type of the getter method to determine the service to make available.

The method should be `abstract` or, in cases where this isn't possible, should have a dummy method body.
The method body is discarded. The name of the property is not significant and can be whatever you like.

Here is an example that shows a task type that receives two services via property getter methods:

[source,java]
.Download.java
----
include::{snippetsPath}/reference/plugin-development/propertyServiceInjection/groovy/buildSrc/src/main/java/Download.java[tags=download]
----
