1. Gradle push | Maven Plugin Publish the Plugin
The Maven Publish plug-in provides the ability to Publish build artifacts to the Apache Maven repository. Modules published to the Maven repository can be used by Maven, Gradle, and other tools that understand the format of the Maven repository.
1.1 add-in task | the Tasks
-
Generate MavenPom PubName generatePomFileFor * * Publication –
Create a POM file for a publication named PubName and populate it with known metadata, such as project name, project version, and dependencies. The default location for POM files is build/publications/$pubName/ POM-default.xml.
-
The publish * RepoName PublicationTo PubName * * * Repository – PublishToMavenRepository
Publish the PubName publication to a repository named RepoName. If you have a repository definition without an explicit name, RepoName will be “Maven”.
-
The publish * PubName * PublicationToMavenLocal – PublishToMavenLocal
Copy PubName publications along with published POM files and other metadata to the local Maven cache — typically *$USER_HOME/.m2/repository*.
-
publish
Depends on: All tasks publish*PubName*PublicationTo*RepoName*Repository Aggregate tasks that publish all defined publications to all defined repositories. It does not include the local Maven cache for replication publications.
-
publishToMavenLocal
Depends on: All tasks publish*PubName*PublicationToMavenLocal copies all defined publications to the local Maven cache, including their metadata (POM files, etc.).
/ / generated MavenPom
generateMetadataFileForDebugPublication
generateMetadataFileForReleasePublication
generatePomFileForDebugPublication
generatePomFileForReleasePublication
//PublishToMavenRepository
publish
publishAllPublicationsToMavenRepository
publishDebugPublicationToMavenRepository
publishReleasePublicationToMavenRepository
//PublishToMavenLocal
publishToMavenLocal
publishDebugPublicationToMavenLocal
publishReleasePublicationToMavenLocal
Use the following command if your project uses the Gralde Wrapper component
./gradlew task [name]
./gradlew task :lib-net:publishToMavenLocal
Copy the code
1.2 build product | Publications
There are four main things you can configure in Maven publications:
- A componentFor example, a Java Module, Android Library Module
- Through this method to specify MavenPublication. The from (org.gradle.api.com ponent. SoftwareComponent)
- Custom artifacts
- Custom built products through this method MavenPublication. An artifact (java.lang.object) method.
- Standard metadata
- For example, artifactId, groupId, and Version.
- Other configurations of POM files
- Set mavenvenvenes.pom (org.gradle.api.action) with this method
1.3 warehouse | Repositories
The plug-in provides a repository of type Mavenartice Repository
Define the publication repository:
publishing {
repositories {
maven {
url "url"
credentials {
username = 'name'
password = 'pwd'}}}}Copy the code
Snapshot and release repositories
publishing {
repositories {
maven {
def releasesRepoUrl = layout.buildDirectory.dir('repos/releases')
def snapshotsRepoUrl = layout.buildDirectory.dir('repos/snapshots')
url = version.endsWith('SNAPSHOT')? snapshotsRepoUrl : releasesRepoUrl } } }Copy the code
1.4 Complete Example
The following example demonstrates how to sign and distribute Java libraries containing source code, Javadoc, and custom POM:
build.gradle
plugins {
id 'java-library'
id 'maven-publish'
id 'signing'
}
group = 'com.example'
version = '1.0'
java {
withJavadocJar()
withSourcesJar()
}
publishing {
publications {
mavenJava(MavenPublication) {
artifactId = 'my-library'
from components.java
versionMapping {
usage('java-api') {
fromResolutionOf('runtimeClasspath')
}
usage('java-runtime') {
fromResolutionResult()
}
}
pom {
name = 'My Library'
description = 'A concise description of my library'
url = 'http://www.example.com/library'
properties = [
myProp: "value"."prop.with.dots": "anotherValue"
]
licenses {
license {
name = 'The Apache License, Version 2.0'
url = 'http://www.apache.org/licenses/LICENSE-2.0.txt'
}
}
developers {
developer {
id = 'johnd'
name = 'John Doe'
email = '[email protected]'
}
}
scm {
connection = 'scm:git:git://example.com/my-library.git'
developerConnection = 'scm:git:ssh://example.com/my-library.git'
url = 'http://example.com/my-library/'
}
}
}
}
repositories {
maven {
// change URLs to point to your repos, e.g. http://my.org/repo
def releasesRepoUrl = layout.buildDirectory.dir('repos/releases')
def snapshotsRepoUrl = layout.buildDirectory.dir('repos/snapshots')
url = version.endsWith('SNAPSHOT')? snapshotsRepoUrl : releasesRepoUrl credentials { username ='name'
password = 'pwd'
}
}
}
}
signing {
sign publishing.publications.mavenJava
}
javadoc {
if(JavaVersion.current().isJava9Compatible()) {
options.addBooleanOption('html5'.true)}}Copy the code
As a result of the above configuration, the following artifacts will be published:
- POM file:
My - library - 1.0. Pom
- Key JAR artifacts:
My - library - 1.0. The jar
- Explicitly configured source code:
My - library - 1.0 - sources. The jar
- Explicitly configured Javadoc:
My - library - 1.0 - the javadoc. Jar
The signature plug-in is used to generate a signature file for each artifact. In addition, checksum files are generated for all artifacts and signature files.
1.5 Using Maven to distribute plug-ins in Android
Android Gradle plugin 3.6.0 and later includes support for the Maven Publish Gradle plugin, which allows you to Publish build artifacts to the Apache Maven repository. The Android Gradle plug-in creates a component for each build variant artifact in your application or library module that you can use to customize and publish to the Maven repository.
The components created by Android plug-ins depend on whether the module uses an application plug-in or a library plug-in, as described in the following table.
Android Gradle plug-in | Published artifact | Component name |
---|---|---|
com.android.library |
AAR | components.variant |
com.android.application |
APK ZIP, and available ProGuard or R8 mapping files | components.variant_apk |
com.android.application |
An Android Application Package (AAB) | components.variant_aab |
1.6 Example for Android
// Because the components are created only during the afterEvaluate phase, you must
// configure your publications using the afterEvaluate() lifecycle method.
afterEvaluate {
publishing {
publications {
// Creates a Maven publication called "release".
release(MavenPublication) {
// Applies the component for the release build variant.
from components.release
// You can then customize attributes of the publication as shown below.
groupId = GROUP
artifactId = ARTIFACT_ID
version = VERSION
}
// Creates a Maven publication called “debug”.
debug(MavenPublication) {
// Applies the component for the debug build variant.
from components.debug
groupId = GROUP
artifactId = ARTIFACT_ID + "-debug"
version = VERSION
}
}
repositories {
maven {
// change URLs to point to your repos, e.g. http://my.org/repo
url = URL
credentials {
username USER_NAME
password PASSWORD
}
}
}
}
}
Copy the code
1.7 Android Custom POM File version Example
apply plugin: 'maven-publish'
println("-- -- -- -- -- -- -- - ${project. The name} : Maven Publish Gradle -- -- -- -- -- -- -- --")
// Release and snapshot control switches
def isUploadToRelease = rootProject.ext.mavenRepo['isUploadToRelease']
// The remote Maven repository URL Release
def MAVEN_REPO_RELEASE_URL = rootProject.ext.mavenRepo['mavenRepoUrlRelease']
// Call the snapshots of the remote Maven repository
def MAVEN_REPO_SNAPSHOTS_URL = rootProject.ext.mavenRepo['mavenRepoUrlSnapshots']
// Remote Maven repository user name
def USER_NAME = rootProject.ext.mavenRepo['userName']
// Remote Maven repository password
def PASSWORD = rootProject.ext.mavenRepo['password']
// Uniquely identifies each component to be specified
def GROUP = group.toString()
// Todo defaults to the project name
def ARTIFACT_ID = project.name
// The version number is specified for each component
def VERSION = version.toString()
// Remote Maven repository URL
def URL = isUploadToRelease ? MAVEN_REPO_RELEASE_URL : MAVEN_REPO_SNAPSHOTS_URL
println("dependencies_path: $GROUP:$ARTIFACT_ID:$VERSION")
println("MAVEN_REPO_RELEASE_URL: $MAVEN_REPO_RELEASE_URL")
println("MAVEN_REPO_SNAPSHOTS_URL: $MAVEN_REPO_SNAPSHOTS_URL")
/ / https://docs.gradle.org/7.0/userguide/publishing_maven.html#publishing_maven
//https://developer.android.com/studio/build/maven-publish-plugin
// Because the components are created only during the afterEvaluate phase, you must
// configure your publications using the afterEvaluate() lifecycle method.
task sourceJar(type: Jar) {
from android.sourceSets.main.java.srcDirs
classifier "sources"
}
afterEvaluate {
publishing {
publications {
maven(MavenPublication) {
groupId GROUP
artifactId ARTIFACT_ID
version VERSION
artifact bundleReleaseAar
artifact sourceJar
// Configure a POM based on the input data.
pom.withXml {
final dependenciesNode = asNode().appendNode('dependencies')
//dependenciesNode:dependencies[attributes={}; value=[]]
println "dependenciesNode:" + dependenciesNode
ext.addDependency = { Dependency dep, String scope ->
/ / the Dependency: DefaultExternalModuleDependency {group = 'com. Qlife. Android', name = 'lib - baidu - face, version = "1.0.0", configuration='default'}
//scope:compile
println "Dependency:" + dep
println "scope:" + scope
if (dep.group == null || dep.version == null || dep.name == null || dep.name == "unspecified")
return // invalid dependencies should be ignored
final dependencyNode = dependenciesNode.appendNode('dependency')
dependencyNode.appendNode('artifactId', dep.name)
if (dep.version == 'unspecified') {
dependencyNode.appendNode('groupId', project.ext.pomGroupID)
dependencyNode.appendNode('version', project.ext.pomVersion)
System.println("${project.ext.pomGroupID} ${dep.name} ${project.ext.pomVersion}")}else {
dependencyNode.appendNode('groupId', dep.group)
dependencyNode.appendNode('version', dep.version)
System.println("${dep.group} ${dep.name} ${dep.version}")
}
dependencyNode.appendNode('scope', scope)
// Some dependencies may have types, such as AAR, which should be mentioned in the POM file
// Some dependencies may have types, such as aar, that should be mentioned in the POM file
def artifactsList = dep.properties['artifacts']
if(artifactsList ! =null && artifactsList.size() > 0) {
final artifact = artifactsList[0]
dependencyNode.appendNode('type', artifact.getType())
}
if(! dep.transitive) {// In the case of non-passable dependencies, all of its dependencies should be forcibly excluded from the POM file
// In case of non transitive dependency, all its dependencies should be force excluded from them POM file
final exclusionNode = dependencyNode.appendNode('exclusions').appendNode('exclusion')
exclusionNode.appendNode('groupId'.The '*')
exclusionNode.appendNode('artifactId'.The '*')}else if(! dep.properties.excludeRules.empty) {// For passes with exclusion, all exclusion rules should be added to the POM file
// For transitive with exclusions, all exclude rules should be added to the POM file
final exclusions = dependencyNode.appendNode('exclusions')
dep.properties.excludeRules.each { ExcludeRule rule ->
final exclusionNode = exclusions.appendNode('exclusion')
exclusionNode.appendNode('groupId', rule.group ? :The '*')
exclusionNode.appendNode('artifactId', rule.module ? :The '*')}}}// List all "api" dependencies (for new Gradle) as "compile" dependencies
configurations.api.getDependencies().each { dep -> addDependency(dep, "compile")}// List all "implementation" dependencies (for new Gradle) as "runtime" dependencies
configurations.implementation.getDependencies().each { dep -> addDependency(dep, "runtime") }
}
}
}
repositories {
maven {
url = URL
credentials {
username USER_NAME
password PASSWORD
}
}
}
}
}
task cleanBuildPublishLocal(type: GradleBuild) {
tasks = ['clean'.'build'.'publishToMavenLocal']
}
task cleanBuildPublish(type: GradleBuild) {
tasks = ['clean'.'build'.'publish']}Copy the code
1.8 Maven POM file format
The Project Object Model (POM) is the basic unit of work of The Maven Project. It is an XML file that contains the basic information of the Project, describing how the Project is built, declaring Project dependencies, and so on.
When executing a task or goal, Maven looks for the POM in the current directory. It reads the POM, gets the required configuration information, and then executes the target.
The following configurations can be specified in the POM:
- Project depend on
- The plug-in
- Performance targets
- Project building profile
- Project version
- Project Developer List
- Related mailing list information
All POM files require a project element and three required fields: groupId, artifactId, and Version.
node | describe |
---|---|
project | Project root tag. |
modelVersion | Model version needs to be set to 4.0.0. |
groupId | A unique identifier of a company or organization, and a path generated during configuration, such as com.panyname. project-group. Maven will place the jar package of the project in the local path: /com/companyname/project-group |
artifactId | ArtifactId is used to distinguish the unique ID of a groupId from multiple items. GroupId, together with artifactId, defines the location of the artifact in the repository. |
version | This is the project version number. In repositories of artifacts, it is used to distinguish between different versions. |
packaging | The type of artifact produced by the project, such as JAR, WAR, EAR, POM. Plug-ins can create their own component types, so not all of the component types listed above |
dependencies | This element describes all dependencies associated with the project. These dependencies form part of the project construction process. They are automatically downloaded from the repository defined by the project. |
dependency | dependency |
scope | Dependency scope. During a project release, help determine which artifacts are included. Refer to dependency mechanisms for more information. -compile: indicates the default range for compiling -Provided: similar to compilation, but supports what you’d expect from the JDK or container, similar to classpath – Runtime: used during execution – test: used for the test task – system: the corresponding elements need to be provided externally. Obtain it from systemPath – systemPath: Applies only to system. Provide the corresponding path -optional: Indicates whether the dependency is passed when the project itself is dependent. Used for continuous dependencies |
POM labels in detail
A simple Android dependency library poM file is shown below
<project xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd" xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<! -- This module was also published with a richer model, Gradle metadata, -->
<! -- which should be used instead. Do not delete the following line which -->
<! -- is to indicate to Gradle or any Gradle module metadata file consumer -->
<! -- that they should prefer consuming it instead. -->
<! -- do_not_remove: published-with-gradle-metadata -->
<modelVersion>4.0.0</modelVersion>
<groupId>com.qlife.android</groupId>
<artifactId>lib-net-release</artifactId>
<version>1.0.1</version>
<packaging>aar</packaging>
<dependencies>
<dependency>
<groupId>com.squareup.retrofit2</groupId>
<artifactId>retrofit</artifactId>
<version>server</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>com.squareup.okhttp3</groupId>
<artifactId>logging-interceptor</artifactId>
<version>4.2.2</version>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>com.github.jaydroid1024.JDispatcher</groupId>
<artifactId>jdispatcher-api</artifactId>
<version>0.0.7</version>
<scope>runtime</scope>
</dependency>.</dependencies>
</project>
Copy the code
2. Aliyun – Cloud Effect Maven repository
If you want to build a Nexus Repository Manager (NXRM) server, download the NXRM from the Nexus official website
Ali Cloud Maven central warehouse for Ali Cloud cloud effect to provide a public agent warehouse, to help r&d personnel to improve research and development production efficiency, using Ali Cloud Maven central warehouse as a download source, faster and more stable.
Alibaba Cloud Service is an enterprise-level one-stop DevOps platform, covering the whole r&d cycle of products from demand to operation. Maven private repository Packages are also provided for free and reliable
2.1 Common proxy repository
The name of the warehouse | Ali Cloud warehouse address | Ali Cloud warehouse address (old version) | Source address |
---|---|---|---|
central | Maven.aliyun.com/repository/… | Maven.aliyun.com/nexus/conte… | repo1.maven.org/maven2/ |
jcenter | Maven.aliyun.com/repository/… | Maven.aliyun.com/nexus/conte… | jcenter.bintray.com/ |
public | Maven.aliyun.com/repository/… | Maven.aliyun.com/nexus/conte… | Aggregation of central and JCenter |
Maven.aliyun.com/repository/… | Maven.aliyun.com/nexus/conte… | maven.google.com/ | |
gradle-plugin | Maven.aliyun.com/repository/… | Maven.aliyun.com/nexus/conte… | plugins.gradle.org/m2/ |
spring | Maven.aliyun.com/repository/… | Maven.aliyun.com/nexus/conte… | Repo. Spring. IO/libs – milest… |
spring-plugin | Maven.aliyun.com/repository/… | Maven.aliyun.com/nexus/conte… | Repo. Spring. IO/plugins – rel… |
grails-core | Maven.aliyun.com/repository/… | Maven.aliyun.com/nexus/conte… | repo.grails.org/grails/core |
apache snapshots | Maven.aliyun.com/repository/… | Maven.aliyun.com/nexus/conte… | repository.apache.org/snapshots/ |
2.2 Android related agent warehouse
The name of the warehouse | Ali Cloud warehouse address |
---|---|
central | Maven.aliyun.com/repository/… |
jcenter | Maven.aliyun.com/repository/… |
public | Maven.aliyun.com/repository/… |
Maven.aliyun.com/repository/… | |
gradle-plugin | Maven.aliyun.com/repository/… |
Compared with the
buildscript {
repositories {
//central
maven { url 'https://maven.aliyun.com/repository/central' }
//jcenter&public
maven { url 'https://maven.aliyun.com/repository/public' }
//google
maven { url 'https://maven.aliyun.com/repository/google' }
//gradle-plugin
maven { url 'https://maven.aliyun.com/repository/gradle-plugin' }
mavenCentral()
maven { url "https://jitpack.io" }
google()
jcenter()
}
}
Copy the code
2.3 Private warehouse of products
-
Cloud Packages automatically creates two Maven repositories for you, a Release library and a Snapshot library.
-
The Maven Release library is used to store releases that are stable and currently updated, and can be used for releases.
-
The Maven Snapchat library is used to store unstable, in-development versions, known as snapshot versions.
-
Depending on whether -snapshot is configured in the version field of the build.gradle file in your project directory.
-
-
After entering the warehouse, you can complete the warehouse voucher setting, product file uploading and downloading, and private database migration through the warehouse guide.
-
The package list displays all binary package files in the repository. You can search for package files by Group Id or Artifacts Id.
-
Click the package file to display the package file information. By default, the latest version information is displayed. Click to switch the package version.
-
The default enterprise owner is the repository owner, and other enterprise members need to set members and roles in the repository. The relationship between warehouse openness and member roles is as follows:
Warehouse roles | Warehouse openness: Private warehouses | Warehouse openness: visible within the enterprise |
The owner | Access, download, upload, delete, warehouse management | Access, download, upload, delete, warehouse management |
The administrator | Access, download, upload, delete, warehouse management | Access, download, upload, delete, warehouse management |
Members of the development | Access, download, upload | Access, download, upload |
Ordinary members | Access, download | Access, download |
Non-warehouse member | There is no | Access, download |
2.4 Gradle push
- Setting warehouse credentials
apply plugin: 'maven-publish'
println("-- -- -- -- -- -- -- - ${project. The name} : Maven Publish Gradle -- -- -- -- -- -- -- --")
// Release and snapshot control switches
def isUploadToRelease = rootProject.ext.mavenRepo['isUploadToRelease']
// The remote Maven repository URL Release
def MAVEN_REPO_RELEASE_URL = rootProject.ext.mavenRepo['mavenRepoUrlRelease']
// Call the snapshots of the remote Maven repository
def MAVEN_REPO_SNAPSHOTS_URL = rootProject.ext.mavenRepo['mavenRepoUrlSnapshots']
// Remote Maven repository user name
def USER_NAME = rootProject.ext.mavenRepo['userName']
// Remote Maven repository password
def PASSWORD = rootProject.ext.mavenRepo['password']
// Uniquely identifies each component to be specified
def GROUP = group.toString()
// Todo defaults to the project name
def ARTIFACT_ID = project.name
// The version number is specified for each component
def VERSION = version.toString()
// Remote Maven repository URL
def URL = isUploadToRelease ? MAVEN_REPO_RELEASE_URL : MAVEN_REPO_SNAPSHOTS_URL
println("dependencies_path: $GROUP:$ARTIFACT_ID:$VERSION")
println("MAVEN_REPO_RELEASE_URL: $MAVEN_REPO_RELEASE_URL")
println("MAVEN_REPO_SNAPSHOTS_URL: $MAVEN_REPO_SNAPSHOTS_URL")
/ / https://docs.gradle.org/7.0/userguide/publishing_maven.html#publishing_maven
//https://developer.android.com/studio/build/maven-publish-plugin
// Because the components are created only during the afterEvaluate phase, you must
// configure your publications using the afterEvaluate() lifecycle method.
afterEvaluate {
publishing {
publications {
// Creates a Maven publication called "release".
release(MavenPublication) {
// Applies the component for the release build variant.
from components.release
// You can then customize attributes of the publication as shown below.
groupId = GROUP
artifactId = ARTIFACT_ID
version = VERSION
}
// Creates a Maven publication called “debug”.
debug(MavenPublication) {
// Applies the component for the debug build variant.
from components.debug
groupId = GROUP
artifactId = ARTIFACT_ID + "-debug"
version = VERSION
}
}
repositories {
maven {
url = URL
credentials {
username USER_NAME
password PASSWORD
}
}
}
}
}
Copy the code
- Set up the repository download configuration
allprojects {
repositories {
//central
maven { url 'https://maven.aliyun.com/repository/central' }
//jcenter&public
maven { url 'https://maven.aliyun.com/repository/public' }
//google
maven { url 'https://maven.aliyun.com/repository/google' }
//gradle-plugin
maven { url 'https://maven.aliyun.com/repository/gradle-plugin' }
mavenCentral()
maven { url "https://jitpack.io" }
google()
jcenter()
/**Maven private server configuration */
// Storage type local dev Production
def currentMavenRepositoryType = rootProject.ext.mavenRepo['currentMavenRepositoryType']
def localMavenRepositoryType = rootProject.ext.mavenRepositoryType['local']
maven {
// Distinguish between local and remote repositories
if(currentMavenRepositoryType ! = localMavenRepositoryType) { credentials { username rootProject.ext.mavenRepo['userName']
password rootProject.ext.mavenRepo['password']
}
}
url rootProject.ext.mavenRepo['mavenRepoUrlRelease']
}
maven {
// Distinguish between local and remote repositories
if(currentMavenRepositoryType ! = localMavenRepositoryType) { credentials { username rootProject.ext.mavenRepo['userName']
password rootProject.ext.mavenRepo['password']
}
}
url rootProject.ext.mavenRepo['mavenRepoUrlSnapshots']}}}Copy the code
2.5 Gradle pull
- Setting warehouse credentials
allprojects {
repositories {
//central
maven { url 'https://maven.aliyun.com/repository/central' }
//jcenter&public
maven { url 'https://maven.aliyun.com/repository/public' }
//google
maven { url 'https://maven.aliyun.com/repository/google' }
//gradle-plugin
maven { url 'https://maven.aliyun.com/repository/gradle-plugin' }
mavenCentral()
maven { url "https://jitpack.io" }
google()
jcenter()
/**Maven private server configuration */
// Storage type local dev Production
def currentMavenRepositoryType = rootProject.ext.mavenRepo['currentMavenRepositoryType']
def localMavenRepositoryType = rootProject.ext.mavenRepositoryType['local']
maven {
// Distinguish between local and remote repositories
if(currentMavenRepositoryType ! = localMavenRepositoryType) { credentials { username rootProject.ext.mavenRepo['userName']
password rootProject.ext.mavenRepo['password']
}
}
url rootProject.ext.mavenRepo['mavenRepoUrlRelease']
}
maven {
// Distinguish between local and remote repositories
if(currentMavenRepositoryType ! = localMavenRepositoryType) { credentials { username rootProject.ext.mavenRepo['userName']
password rootProject.ext.mavenRepo['password']
}
}
url rootProject.ext.mavenRepo['mavenRepoUrlSnapshots']}}}Copy the code
- Configuration Package Information
dependencies {
def currentMavenRepositoryType = rootProject.ext.mavenRepo['dependenceTypeIsModule']
if (currentMavenRepositoryType) {
implementation project(path: ':lib-net')}else {
implementation rootProject.ext.libNet
}
}
Copy the code
Grade dependency management
3.1 Dependency types
dependencies {
// The dependency of the local repository module
implementation project(":mylibrary")
// Dependencies on local binaries
implementation fileTree(dir: 'libs'.include: ['*.jar'])
implementation files('libs/foo.jar')
implementation project(path: ':foo-aar-module')
// Dependencies on remote binaries
implementation 'com. The example. The android: app - magic: 12.3'
}
Copy the code
Local library module dependencies
This relies on an Android library module named “myLibrary” (which must match the name of the library defined using include: in your settings.gradle file). When you build your application, the build system compiles the library module and packages the compiled content into APK.
Local binary dependencies
Gradle declares a dependency on JAR files in the module_name/libs/ directory of the project (because Gradle reads the relative path to the build. Gradle file).
You can also specify individual JAR/AAR files or create a dependency like the local repository module by creating an AAR/JAR module
Remote binary dependencies
Implementation 'com. Example. Android: app - magic: 12.3'Copy the code
This is actually a shorthand for the following code:
Implementation Group: 'com.example. Android ', name: 'app-magic', version: '12.3'Copy the code
This declares a dependency on the version 12.3 “app-Magic” library in the “com.example.android” namespace group.
Such remote dependencies require you to declare the appropriate remote code base, which Gradle should look for. If the corresponding library does not exist locally, Gradle extracts it from the remote site.
3.2 Dependency Dependency Mode Configuration
In the Dependencies code block, you can choose one of a number of different dependency configurations, each of which gives Gradle a different description of how to use the dependency. The following table describes the various configurations used by dependencies in Android projects.
The new configuration | The configuration is deprecated | Behavior description |
---|---|---|
implementation |
compile |
Gradle adds dependencies to the compile classpath and packages dependencies into the build output. When the module is configuredimplementation Dependencies are compiled at Gradle timeThis dependency is not passed to other modules. That is, other modules can use this dependency only at run time. Use this dependency configuration insteadapi 或 compile Deprecated yesSignificantly reduce build timesBecause it reduces the number of modules that need to be recompiled to build the system. For example, ifimplementation A dependency changes its API, and Gradle only recompiles the dependency and the modules that directly depend on it. Most applications and test modules should use this configuration. |
api |
compile |
Gradle adds dependencies to the compile classpath and build output. When a module containsapi Makes Gradle dependentExport the dependency to another module in pass-through modeSo that these modules can use the dependency both at run time and compile time. This configuration behaves like thiscompile (deprecated), but it should be used with extreme care only for dependencies that need to be exported to other upstream consumers in pass-through mode. That’s because ifapi A dependency changes its external API, and Gradle recompiles all modules that have access to the dependency at compile time. Therefore, have a large number ofapi Dependencies are displayedIncrease build time. Unless you want to expose a dependency’s API to a separate module, the library module should use it insteadimplementation Dependencies. |
compileOnly |
provided |
Gradle only adds dependencies to the compiled classpath that is,It is not added to the build output. This configuration can be useful if you create an Android module that requires a dependency at compile time but is not required at run time. If you use this configuration, your library module must include a runtime condition that checks if a dependency is provided and then appropriately changes the behavior of the module so that it can function without the dependency. To do soUnimportant transient dependencies are not added, therefore,Helps reduce the size of the final APK. This configuration behaves like thisprovided (now deprecated).Pay attention to: You can’tcompileOnly The configuration works with AAR dependencies. |
runtimeOnly |
apk |
Gradle only adds dependencies to the build output for use at run time. That is, it will not be added to the compiled classpath. This configuration behaves like thisapk (now deprecated). |
annotationProcessor |
compile |
To add a dependency to a library that acts as an annotation processor, you must useannotationProcessor Configure to add it to the annotation processor classpath. This is because using this configuration canImprove build performance by separating the compile classpath from the annotation processor classpath. If Gradle finds a comment handler on the compilation classpath, it is disabledAvoid compilationFeature, which has a negative impact on build time (Gradle 5.0 and later ignore comment handlers found on the compilation classpath). The Android Gradle plugin assumes that the dependency is a comment handler if the JAR file contains the following files:META-INF/services/javax.annotation.processing.Processor . A build error is generated if the plug-in detects a comment handler on the compiled classpath. |
3.3 Dependency Order
The order in which dependencies are listed indicates the priority of each library: the first library has priority over the second, the second library has priority over the third, and so on. This order is important when merging resources or listing elements from libraries into applications.
For example, if your project declares the following:
- Rely on
LIB_A
和LIB_B
(In that order) LIB_A
Depends on theLIB_C
和LIB_D
(In that order)LIB_B
Also depends onLIB_C
//app
dependencies {
implementation('LIB_A')
implementation('LIB_B')}//LIB_A
dependencies {
implementation('LIB_C')
implementation('LIB_D')}//LIB_B
dependencies {
implementation('LIB_C')}Copy the code
The order of flat dependencies would look like this:
LIB_A
LIB_D
LIB_B
LIB_C
This ensures that both LIB_A and LIB_B can replace LIB_C; And LIB_D still takes precedence over LIB_B because LIB_A (which depends on the former) has precedence over LIB_B.
3.4 Dependency conflict
Resolve conflicts between classpath
When Gradle parses the compiled classpath, it first parses the runtime classpath and then uses the results to determine which versions of dependencies should be added to the compiled classpath. In other words, the runtime classpath determines the version numbers required for identical dependencies downstream on the classpath.
The runtime classpath of an application also determines the version number Gradle needs to use for matching dependencies in the runtime classpath of the application’s test APK. Figure 1 illustrates the classpath hierarchy.
For example, when an application uses the implementation dependency configuration to add a version of a dependency, and a library module uses runtimeOnly configuration to add another version of that dependency, conflicts can occur with different versions of the same dependency in multiple classpath.
Android Gradle plugin 3.3.0 and later attempts to resolve some downstream version conflicts automatically when resolving dependencies on runtime and compile-time classpath. For example, if the runtime classpath contains library A version 2.0 and the compiled classpath contains library A version 1.0, the plug-in will automatically update the dependency on the compiled classpath to library A version 2.0 to avoid errors.
However, if the runtime classpath contains library A version 1.0 and the compiled classpath contains library A version 2.0, the plug-in does not downgrade its dependency on the compiled classpath to library A version 1.0, and you still receive an error similar to the following:
Conflict with dependency 'com.example. Library :some-lib:2.0' in project 'my-library'. Resolved versions for Runtime Differ with classpath (1.0) and compile classpath (2.0).Copy the code
To resolve this problem, perform one of the following operations:
- Treat the dependencies of the required version as
api
Dependencies are added to the library module. That is, only library modules declare dependencies, but application modules also have pass-through access to their apis. – Alternatively, you can declare dependencies in both modules at the same time, but make sure that each module uses the same version. considerConfigure project global propertiesTo ensure that versions of each dependency remain consistent throughout the project.
Exclude pass dependencies
As the scope of an application grows, it may contain many dependencies, both direct and transitive (libraries that the imported libraries in the application depend on). To exclude pass-through dependencies that are no longer needed, you can use the exclude keyword, as follows:
dependencies {
implementation('some-library') {
exclude group: 'com.example.imgtools', module: 'native'
}
}
Copy the code
If you define a exclude in the Configuration, all transitive dependencies (specified) are removed. When you define exclude, specify either group only, module name only, or both.
Here are some typical examples of using exclude:
- A licensing issue
- The dependency cannot be obtained from the remote repository
- This is not needed at Runtime
- Version conflict
Force the current version
Implementation (' com. Squareup. Okhttp: okhttp - mt: 2.5.0 ') {force = true}Copy the code
For example, if a dependency contains okHTTP, there will be a version conflict. If a dependency contains okHTTP, there will be a version conflict.
Indirect dependencies transitive
They are called “transitive dependencies” and are more appropriate.
Implementation (' com. At meituan. Android. Terminus: library: 6.6.1.16 @ aar ') {transitive = true}Copy the code
Adding @aar to the end of the script means that you are downloading the AAR package and not the other libraries that the aar package depends on. If you want to download the aar dependent libraries without using @aar, you need to add the transitive=true condition.
4. Reference materials
- Ali cloud | cloud Maven
- Ali cloud | cloud products warehouse Package the official document
- Ali cloud | cloud Package products warehouse address
- Android developers | Android Maven Publish docs
- Gradle user guide | Gradle Maven Publish official page
- What is Maven
- Novice tutorial | Maven tutorial
- Publish an Android library to Maven with aar and source jar
- Android developers | add build dependencies
- Rely on the management of Gradle user guide | Gradle