1## Dependencies {#dependencies}
2
3Artifacts may depend on other artifacts within AndroidX as well as sanctioned
4third-party libraries. Additionally, artifacts may have toolchain dependencies
5that are not explicitly specified in their `dependencies` build configuration or
6don't appear in their Maven publications (`pom` or `module` files).
7
8### Versioned artifacts {#dependencies-versioned}
9
10One of the most difficult aspects of independently-versioned releases is
11maintaining compatibility with public artifacts. In a monorepo such as Google's
12repository or Android Git at `main` revision, it's easy for an artifact to
13accidentally gain a dependency on a feature that may not be released on the same
14schedule.
15
16To address this problem, library owners in AndroidX can choose from several
17types of dependencies:
18
19-   Project `project(":core:core")` uses the tip-of-tree sources for the
20    `androidx.core:core` library and requires that they be loaded in the
21    workspace and released at the same time.
22-   Playground `projectOrArtifact(":core:core")` is used for the
23    [Playground](/docs/playground.md) workflow and will use
24    tip-of-tree sources, if present in the workspace, or `SNAPSHOT` prebuilt
25    artifacts from [androidx.dev](http://androidx.dev) otherwise.
26-   Pinned `"androidx.core:core:1.4.0"` uses the prebuilt AAR and requires that
27    it be checked in to the `prebuilts/androidx/internal` local Maven repository
28    or, when using the Playground workflow, the remote Google Maven repository.
29
30Libraries should prefer pinned dependencies with the lowest possible versions
31that include the APIs or behaviors required by the library, and should only use
32project or Playground specs in cases where tip-of-tree APIs or behaviors are
33required.
34
35**Do not** upgrade the version of a library's dependency to artificially boost
36adoption of that version.
37
38#### Pre-release dependencies {#dependencies-pre-release}
39
40Pre-release suffixes **must** propagate up the dependency tree. For example, if
41your artifact has a dependency on an artifact versioned `1.1.0-alpha01` then
42your artifact must also carry the `alpha` suffix.
43
44NOTE This does not apply to test dependencies: suffixes of test dependencies do
45*not* carry over to your artifact.
46
47#### Pinned versions {#dependencies-prebuilt}
48
49To avoid issues with dependency versioning, pin your dependencies to the oldest
50stable version of an artifact that includes the necessary APIs. This will ensure
51that the artifact's release schedule is not accidentally tied to that of another
52artifact and will allow developers to use older libraries if desired.
53
54```
55dependencies {
56   api("androidx.collection:collection:1.0.0")
57   ...
58}
59```
60
61Artifacts are built and tested against both pinned and tip-of-tree versions of
62their dependencies to ensure behavioral compatibility.
63
64#### Tip-of-tree versions {#dependencies-project}
65
66Below is an example of a project dependency, which uses tip-of-tree sources for
67the dependency rather than a prebuilt `JAR` or `AAR`. It ties the artifact's
68release schedule to that of the dependency artifact because the dependency will
69need to be released at the same time.
70
71```
72dependencies {
73   api(project(":collection"))
74   ...
75}
76```
77
78### Non-public APIs {#dependencies-non-public-apis}
79
80Artifacts may depend on non-public or restricted APIs exposed within their own
81artifact or another artifact in the same `groupId`; however, cross-artifact
82usages are subject to binary compatibility guarantees. See
83[`@RestrictTo` APIs](/docs/api_guidelines#restricted-api) for
84more details.
85
86Dependency versioning policies are enforced at build time in the `createArchive`
87task, which ensures that pre-release version suffixes are propagated
88appropriately. Cross-artifact API usage policies are enforced by the `checkApi`
89and `checkApiRelease` tasks.
90
91### Third-party libraries {#dependencies-3p}
92
93Artifacts may depend on libraries developed outside of AndroidX; however, they
94must conform to the following guidelines:
95
96*   Prebuilt **must** be checked into Android Git
97    *   `prebuilts/maven_repo` is recommended if this dependency is only
98        intended for use with AndroidX artifacts, otherwise please use
99        `external`
100*   Prebuilt directory **must** contains an `OWNERS` file identifying one or
101    more individual owners (e.g. NOT a group alias)
102*   Library **must** be approved by legal
103
104Please see Jetpack's
105[open-source policy page](/docs/open_source.md) for more
106details on using third-party libraries.
107
108### Platform extension (sidecar JAR) dependencies {#dependencies-sidecar}
109
110Platform extension or "sidecar JAR" libraries ship as part of the Android system
111image and are made available to developers through the `<uses-library>` manifest
112tag.
113
114Examples include Camera OEM extensions (`androidx.camera.extensions.impl`) and
115Window OEM extensions (`androidx.window.extensions`).
116
117Extension libraries may be defined in AndroidX library projects (see
118`androidx.window.extensions`) or externally, ex. in AOSP alongside the platform.
119In either case, we recommend that libraries use extensions as pinned, rather
120than project-type, dependencies to facilitate versioning across repositories.
121
122*Do not* ship extension interfaces to Google Maven. Teams may choose to ship
123stub JARs publicly, but that is not covered by AndroidX workflows.
124
125Project dependencies on extension libraries **must** use `compileOnly`:
126
127`build.gradle`:
128
129```
130dependencies {
131    // Extension interfaces defined in Jetpack
132    compileOnly(project(":window:extensions:extensions"))
133
134    // Extension interfaces defined in a stub JAR
135    compileOnly(
136        fileTree(
137            dir: "../wear_stubs",
138            include: ["com.google.android.wearable-stubs.jar"]
139        )
140    )
141}
142```
143
144Documentation dependencies **must** use the `stubs` configuration:
145
146`docs-public/build.gradle`:
147
148```
149dependencies {
150  stubs("androidx.window:window-extensions:1.0.0-alpha01")
151  stubs(
152    fileTree(
153        dir: "../wear/wear_stubs/",
154        include: ["com.google.android.wearable-stubs.jar"]
155    )
156  )
157}
158```
159
160See [Packaging and naming](/docs/api_guidelines#module-naming)
161for details about defining extension interfaces in Jetpack projects.
162
163### Types of dependencies {#dependencies-types}
164
165AndroidX allows dependencies to be specified as `api` or `implementation` with a
166"pinned" Maven spec (ex. `androidx.core:core:1.0.0`) or a "tip-of-tree" project
167spec (ex. `project(":core:core")`).
168
169Projects used in Playground, the experimental GitHub workflow, should use a
170"recent" project or artifact spec (ex. `projectOrArtifact(":core:core")`) which
171will default to tip-of-tree when used outside of the Playground workflow or a
172pinned `SNAPSHOT` artifact otherwise.
173
174Regardless of which dependency spec is used, all projects are built against
175tip-of-tree dependencies in CI to prevent regressions and enforce Jetpack's
176compatible-at-head policy.
177
178#### `api` versus `implementation` {#dependencies-api-vs-impl}
179
180`api`-type dependencies will appear in clients' auto-complete as though they had
181added the dependency directly to their project, and Studio will run any lint
182checks bundled with `api`-type dependencies.
183
184Dependencies whose APIs are exposed in a library's API surface **must** be
185included as `api`-type. For example, if your library's API surface includes
186`AccessibilityNodeInfoCompat` then you will use an `api`-type dependency on the
187`androidx.core:core` library.
188
189NOTE Libraries that provide client-facing lint checks, including
190`annotation-experimental`, **must** be included as `api`-type to ensure that
191lint checks are run in the clients' dependent projects.
192
193`implementation`-type dependencies will be included in the classpath, but will
194not be made available at design time (ex. in auto-complete) unless the client
195explicitly adds them.
196
197#### Constraints {#dependencies-constraints}
198
199Dependency constraints ensure that when certain libraries are used together,
200they meet certain requirements. Defining a constraint on a library *does not*
201pull that library into the classpath.
202
203In Jetpack, we use constraints to ensure that atomically-grouped libraries all
204resolve to the same version
205([example](https://android-review.googlesource.com/c/platform/frameworks/support/+/1973425))
206and, in rare cases, to avoid conflicts resulting from classes being moved
207between artifacts
208([example](https://android-review.googlesource.com/c/platform/frameworks/support/+/2086029)).
209
210`core/core-ktx/build.gradle`:
211
212```
213dependencies {
214    // Atomic group
215    constraints {
216        implementation(project(":core:core"))
217    }
218}
219```
220
221In *extremely* rare cases, libraries may need to define a constraint on a
222project that is not in its `studiow` project set, ex. a constraint between the
223Paging and Compose libraries. As a workaround, libraries may hard-code the Maven
224coordinate using a version variable
225([example](https://android-review.googlesource.com/c/platform/frameworks/support/+/2160202))
226to indicate the tip-of-tree version.
227
228`paging/paging-common/build.gradle`:
229
230```
231dependencies {
232    // Atomic group
233    constraints {
234        implementation("androidx.paging:paging-compose:${LibraryVersions.PAGING_COMPOSE}")
235    }
236}
237```
238
239### Dependency considerations {#dependencies-health}
240
241Generally, Jetpack libraries should avoid dependencies that negatively impact
242developers without providing substantial benefit. Libraries should consider the
243implications of their dependencies, including:
244
245-   Large dependencies where only a small portion is needed (e.g. APK bloat)
246-   Dependencies that slow down build times through annotation processing or
247    compiler overhead
248-   Dependencies which do not maintain binary compatibility and conflict with
249    semantic versioning guarantees
250-   Dependencies that are intended for server environments and don't interact
251    well with the Android build toolchain (e.g. R8) or runtime (e.g. ART)
252
253#### Kotlin {#dependencies-kotlin}
254
255Kotlin is *strongly recommended* for new libraries and the Kotlin stdlib will
256already be present in the transitive dependencies of any library that depends on
257`androidx.annotations`.
258
259```
260plugins {
261    id("AndroidXPlugin")
262    id("kotlin-android")
263}
264
265dependencies {
266    implementation(libs.kotlinStdlib)
267}
268```
269
270Java-based libraries *may* migrate to Kotlin, but they must be careful to
271maintain binary compatibility during the migration. Metalava does not cover all
272possible aspects of migration, so some manual work will be required.
273
274#### Kotlin reflect {#dependencies-kotlin-reflect}
275
276Reflection in libraries is
277[only allowed for backwards compatibility support](/docs/api_guidelines#sdk-reflection)
278and those users should use Java reflection. `kotlin-reflect` is very costly at
279runtime and should never be used.
280
281#### Kotlin coroutines {#dependencies-coroutines}
282
283The Kotlin coroutines library adds around 100kB post-shrinking. New libraries
284that are written in Kotlin should prefer coroutines over `ListenableFuture`, but
285existing libraries must consider the size impact on their clients. See
286[Asynchronous work with return values](/docs/api_guidelines#async-return)
287for more details on using Kotlin coroutines in Jetpack libraries.
288
289```
290dependencies {
291    implementation(libs.kotlinCoroutinesAndroid)
292}
293```
294
295#### GSON {#dependencies-gson}
296
297GSON relies heavily on reflection and interacts poorly with app optimization
298tools like R8. Instead, consider using `org.json` which is included in the
299Android platform SDK.
300
301#### Guava {#dependencies-guava}
302
303The full Guava library is very large and should only be used in cases where
304there is a reasonable assumption that clients already depend on full Guava.
305
306For example, consider a library `androidx.foo:foo` implemented using Kotlin
307`suspend fun`s and an optional `androidx.foo:foo-guava` library that provides
308`ListenableFuture` interop wrappers with a direct dependency on
309`kotlinx.coroutines:kotlinx-coroutines-guava` and a transitive dependency on
310Guava.
311
312Libraries that only need `ListenableFuture` may instead depend on the standalone
313`com.google.guava:listenablefuture` artifact. See
314[Asynchronous work with return values](/docs/api_guidelines#async-return)
315for more details on using `ListenableFuture` in Jetpack libraries.
316
317#### Protobuf {#dependencies-protobuf}
318
319**Note**: It is preferred to use the [`wire`](https://github.com/square/wire)
320library for handling protocol buffers in Android libraries as it has a binary
321stable runtime. An example of its usage can be found
322[here](https://cs.android.com/androidx/platform/frameworks/support/+/androidx-main:benchmark/benchmark-common/build.gradle?q=wireRuntime%20file:gradle&ss=androidx%2Fplatform%2Fframeworks%2Fsupport).
323
324[Protocol buffers](https://developers.google.com/protocol-buffers) provide a
325language- and platform-neutral mechanism for serializing structured data. The
326implementation enables developers to maintain protocol compatibility across
327library versions, meaning that two clients can communicate regardless of the
328library versions included in their APKs.
329
330The Protobuf library itself, however, does not guarantee ABI compatibility
331across minor versions and a specific version **must** be used with a library to
332avoid conflict with other dependencies used by the developer. To do this, you
333must first create a new project to repackage the protobuf runtime classes, and
334then have it as a dependency in the project you generate protos in. In the
335project that generates protos, you must also relocate any import statements
336containing `com.google.protobuf` to your target package name. The
337[AndroidXRepackagePlugin](https://cs.android.com/androidx/platform/frameworks/support/+/androidx-main:buildSrc/private/src/main/kotlin/androidx/build/AndroidXRepackageImplPlugin.kt)
338abstracts this for you. An example of its use to repackage the protobuf runtime
339library can be found
340[here](https://cs.android.com/androidx/platform/frameworks/support/+/androidx-main:wear/protolayout/protolayout-external-protobuf/build.gradle)
341and its associated use in the library that generates protos can be found
342[here](https://cs.android.com/androidx/platform/frameworks/support/+/androidx-main:wear/protolayout/protolayout-proto/build.gradle).
343
344Additionally, the Java API surface generated by the Protobuf compiler is not
345guaranteed to be stable and **must not** be exposed to developers. Library
346owners should wrap the generated API surface with well-documented public APIs
347that follow an appropriate language-specific paradigm for constructing data
348classes, e.g. the Java `Builder` pattern.
349
350### Open-source compatibility {#dependencies-aosp}
351
352Jetpack's [open-source](/docs/open_source.md) guidelines
353require that libraries consider the open-source compatibility implications of
354their dependencies, including:
355
356-   Closed-source or proprietary libraries or services that may not be available
357    on AOSP devices
358-   Dependencies that may prevent developers from effectively isolating their
359    tests from third-party libraries or services
360
361Primary artifacts, e.g. `workmanager`, **must not** depend on closed-source
362components including libraries and hard-coded references to packages,
363permissions, or IPC mechanisms that may only be fulfilled by closed-source
364components.
365
366Optional artifacts, e.g. `workmanager-gcm`, *may* depend on closed-source
367components or configure a primary artifact to be backed by a closed-source
368component via service discovery or initialization.
369
370Some examples of safely depending on closed-source components include:
371
372-   WorkManager's GCM Network Manager integration, which uses
373    [manifest metadata](https://cs.android.com/androidx/platform/frameworks/support/+/androidx-main:work/work-gcm/src/main/AndroidManifest.xml)
374    for service discovery and provides an optional artifact exposing the
375    service.
376-   Downloadable Fonts integration with Play Services, which plugs in via a
377    [`ContentProvider`](https://cs.android.com/androidx/platform/frameworks/support/+/androidx-main:core/core/src/androidTest/java/androidx/core/provider/MockFontProvider.java)
378    as a service discovery mechanism with developer-specified
379    [signature verification](https://developer.android.com/guide/topics/ui/look-and-feel/downloadable-fonts#adding-certificates)
380    for additional security.
381
382Note that in all cases, the developer is not *required* to use GCM or Play
383Services and may instead use another compatible service implementing the same
384publicly-defined protocols.
385
386### Toolchain dependencies
387
388Toolchain dependencies are typically specified by the AndroidX build system and
389are often limited, if any, configuration on behalf of library owners.
390
391#### Kotlin language
392
393Several projects within AndroidX depend on aspects of the Kotlin compiler that
394do not guarantee binary compatibility, which means (1) Kotlin updates within
395AndroidX may be more complicated and (2) Kotlin updates may be more complicated
396for external clients.
397
398For this reason, we try to separate (1) and (2) by pinning the Kotlin language
399and API versions until the new compiler has been in use in AndroidX for at least
400three months.
401
402Library owners *may* in limited cases update their Kotlin language version early
403by specifying the `kotlinVersion` DSL property:
404
405```
406androidx {
407    kotlinVersion KOTLIN_1_9
408}
409```
410
411Note that this propagates the version requirement to all dependencies and is not
412appropriate for low-level libraries.
413
414#### Java language (host-side) {#java-host}
415
416The Java language level determines the minimum version of the Java runtime
417required for lint checks and other host-side libraries like compilers.
418
419To avoid causing issues for clients, we try to separate Java compiler or runtime
420updates from language level by pinning the Java language level to the second
421most-recent stable LTS version. In extreme cases, however, we may be required to
422move to a more recent version because of a dependency like AGP or Gradle.
423
424Library owners *may*, in cases where clients are unable to update their Java
425version, temporarily pin their Java language version to a lower value by
426specifying the compatibility DSL properties:
427
428```
429javaExtension.apply {
430    // TODO(b/12345678) Remove this once clients are able to update.
431    sourceCompatibility = VERSION_17
432    targetCompatibility = VERSION_17
433}
434```
435
436When doing so, library owners **must** file a bug and establish a timeline to
437un-pin and rejoin the rest of AndroidX.
438
439#### Java language (device-side) {#java-device}
440
441Currently, the highest Java language level supported for Android libraries is
442Java 1.8 (`VERSION_1_8`). AndroidX **does not** currently support library API
443desugaring, so the use of Java 8 APIs requires `minSdk 26` or higher.
444
445#### Android SDK {#compile-sdk}
446
447Similar to our library dependency versioning policy, libraries should depend on
448the lowest `compileSdk` version that provides the APIs needed by the library.
449
450We try to avoid unnecessary SDK upgrades because raising a library's
451`compileSdk` implicitly raises its `minCompileSdk`, which means that clients are
452required to raise their own `compileSdk`. This often requires updating Android
453Gradle Plugin, which can turn into a long process of upgrading many other
454dependencies.
455