前言
本编文章将较大家如何上传库到mavenCentral仓库
如果你是一个第三方库开发者,且之前没有上传库到 mavenCentral 经验的话,本文可以助你早日上传库到 mavenCentral。
一、Sonatype 账号
1、注册 Sonatype
在上传库到 MavenCentral 之前,需要先注册登录 Sonatype,访问 https://issues.sonatype.org 链接根据提示进行账户注册,注册成功后再登录 Sonatype。
注意:注册时填写的邮箱很重要,建议是你常用的邮箱,才能及时收到 Sonatype 在 issue 中给你的答复信息提醒
2、申请上传权限
现在你已经有 Sonatype 账号了,接下来理应就是借助 grdle 脚本经管理后台(s01.oss.sonatype.org) 把库上传到 MavenCentral ,但是,Sonatype 新用户默认是没有这个权限的,不信你可以访问 s01.oss.sonatype.org后,点击右上角 “Log In” 登录试试看,会提示没有权限,所以,现在我们需要让 Sonatype 给我们开通这个权限,回到登录成功后跳转的那个页面issues.sonatype.org,点击顶部的 新建 按钮,填写项目信息:
这个步骤中,唯一需要注意的地方就是 Group Id,有两种情况:
无网站域名:可以直接使用 github 的子域名 io.github.username,比如我的 github 账号名是 yexzj,那么可以填写 io.github.yexzj。
有网站域名:可以填写个人或公司域名,比如:com.gitlqr,另外,还需要在 DNS 配置中配置一个 TXT 记录来验证域名所有权,具体请看:https://central.sonatype.org/pages/producers.html
填写信息后,点击"新建"按钮,开启一个 issue,会显示 wait for response,等待 Sonatype 工作人员审核回复,因为 Sonatype 是国外运营,所以工作时间上会有时差,我们需要耐心等待 Sonatype 工作人员处理这个 issue,比如我这样:
二、Gradle 配置
1.新建gradles文件夹,添加publis-maven.gradle配置文件,如下
publis-maven.gradle配置如下(示例):
apply plugin: 'maven-publish'
apply plugin: 'signing'
def GROUP_ID = 'io.github.yeszj'//改成第一步申请上传权限时填写的Group Id
def ARTIFACT_ID = 'simpleCompress' //随意命名 你自己编写的第三方库的名称
def VERSION_NAME = '1.0.0' //版本
def DESCRIPTION = '图片压缩库'
def GIT_LOCATION = 'github.com/yeszj/ImgPressDemos' //github项目的链接
def GIT_LOCATION_URL = 'https://' + GIT_LOCATION
//仓库地址
def MAVEN_URL = "https://s01.oss.sonatype.org/service/local/staging/deploy/maven2/"
def nexusUsername = 'zhengjun' //Sonatype账号
def nexusPassword = 'Wanghui04882f'//Sonatype账号密码
task sourceJar(type: Jar) {
if (hasAndroidPlugin()) {
println "======> Android"
from android.sourceSets.main.java.srcDirs
//noinspection GroovyAccessibility
archiveClassifier = 'sources'
} else if (hasJavaPlugin()) {
println "======> Java"
from sourceSets.main.allSource
//noinspection GroovyAccessibility
archiveClassifier = 'sources'
}
}
afterEvaluate { project ->
tasks.all { Task task ->
if
(task.name.equalsIgnoreCase('publishAarPomPublishPublicationToSimpleCompressRepository')) {
task.dependsOn tasks.getByName('assemble')
}
}
}
def hasJavaPlugin() {
if (plugins.hasPlugin("java-library")) {
return true
}
return false
}
def hasAndroidPlugin() {
if (plugins.hasPlugin("com.android.library")) {
return true
}
return false
}
publishing {
println "======> ${project.name}"
println "====> the aar path is " + "$buildDir/outputs/aar/${project.name}-release.aar"
println "====>" + MAVEN_URL
println "====>" + VERSION_NAME
publications {
aarPomPublish(MavenPublication) {
groupId GROUP_ID
artifactId ARTIFACT_ID
version VERSION_NAME
artifact(sourceJar)
artifact("$buildDir/outputs/aar/${project.name}-release.aar")
pom {
packaging 'aar'
name = ARTIFACT_ID
description = DESCRIPTION
url = GIT_LOCATION_URL
licenses {
license {
name = 'The Apache License, Version 2.0'
url = 'http://www.apache.org/licenses/LICENSE-2.0.txt'
}
}
developers {
developer {
id = 'zhengjun'
name = 'zhengjun'//用户名
email = '458384201@qq.com'申请Sonatype账号时的邮箱地址
}
}
scm {
connection = 'scm:git:' + GIT_LOCATION + '.git'
developerConnection = 'scm:git:ssh://' + GIT_LOCATION + '.git'
url = GIT_LOCATION_URL
}
}
pom.withXml {
//asNode().appendNode('测试').appendNode('自定义key', '自定义value')
def dependenciesNode = asNode().appendNode('dependencies')
configurations.implementation.allDependencies.each {
if (it.version != "unspecified") { // 过滤项目内library引用
println "=====>" + it.properties
println "=====>" + it.group + " " + it.name + it.version
if (it.group == null || it.name == null || it.version == null) return
if (it.group == group) return
def dependencyNode = dependenciesNode.appendNode('dependency')
dependencyNode.appendNode('groupId', it.group)
dependencyNode.appendNode('artifactId', it.name)
dependencyNode.appendNode('version', it.version)
if (it.excludeRules.size() > 0) {
def exclusionsNode = dependencyNode.appendNode('exclusions')
it.excludeRules.each { rule ->
def exclusionNode = exclusionsNode.appendNode('exclusion')
exclusionNode.appendNode('groupId', rule.group)
exclusionNode.appendNode('artifactId', rule.module)
}
}
}
}
}
}
}
repositories {
maven {
name "simpleCompress"
url MAVEN_URL
credentials {
username = nexusUsername
password = nexusPassword
}
}
}
}
// signing 必须在 publishing 配置之后
signing {
sign publishing.publications.aarPomPublish
}
2.在你编写的第三方库library中的build.gradle的结尾添加
apply from: "${getRootDir().absolutePath}/gradles/publish-maven.gradle"
三、GPG 签名
由于本人开发用的是mac电脑,所以一下介绍的是使用mac生成gpg签名的过程,如是Windows电脑可参考此篇文章 [windows创建GPG签名](https://blog.csdn.net/u011174139/article/details/120139497)
- 创建GPG密钥
在往上找到一些关于创建GPG密钥的文章,安装方式各异,我这里使用的命令行安装,不过首先Mac电脑上需要安装了brew才可以,brew不会安装的自行百度,这里就不赘述了,下面说一下如何安装GPG:
在命令行使用如下命令
brew install gpg
2.创建密钥
在命令行中使用如下命令作为开始
gpg --full-gen-key
在执行过程会让选择加密方式,我这边使用的是RSA and RSA,长度输入4096,过期时间直接回车代表不过期,然后提示让输入User ID和一个邮箱,这里可以使用注册SonaType时候用的用户名和邮箱,接着最后一步输入O,注意这里是大写的O不是零,然后回车接着就会提示让输入密码,输入一次后还会有一次确认输入,这个密码一定要记住后期会用到。
接下来创建gpg文件,通过如下命令创建,我建议先在命令行中把目录切到~/.gnupg/下再去执行如下命令这样不会找不到文件。
gpg --export-secret-keys -o secring.gpg
执行以上命令创建文件secring.gpg,创建过程会让输入上边我们创建密钥过程中输入的密码,验证完密码后会在~/.gnupg目录生成secring.gpg文件,这个文件的路径我们后续在生成配置文件的时候也需要。
到此我们生成的所有文件都在.gnupg文件内,如图:
把secring.gpg文件复制到gradles文件内
3.在项目的gradle.properties中添加如下代码:
signing.keyId=D76DC4FD //此文件夹.gunopg/openpgp-revocs.d内的.rev结尾的文件的名称后8位
signing.password=zhengjun0808 //创建密钥时设置的密码
signing.secretKeyRingFile=../gradles/secring.gpg //gpg文件路径
ossrhUsername=zhengjun //Sonatype账号
ossrhPassword=Wanghui04882f//Sonatype密码
四、上传密钥
密钥位文件夹.gunopg/openpgp-revocs.d内的.rev结尾的文件的名称
gpg --send-keys 密钥 --keyserver hkp://subkeys.pgp.net
这一步非常重要,否则后期上传库后,在管理台点击close会失败
五、上传库
先build项目,生成aar包,然后点击库library中的tasks/publishing下的publishAarPomPublishPublicationToSimpleCompressRepository进行上传,如下图:
上传成功后,进入https://s01.oss.sonatype.org/管理后台,通过点击Staging Repositories去找到我们刚刚发布的包并继续发包流程。包刚上传上来你会发现只有Refresh、Close和Drop可以点击,这个时候我们如果想立即发布直接点击Close,通过页面的下半部分可以看到处理的状态,刷新需要我们点击Refresh进行刷新,每一次点击Close都是一个单独的Task,如果Task中每个环节都是绿色通过的状态,那么这个包的状态就回变成closed,Release菜单就可以点击发布了,操作完后等待差不多10分钟就可以访问发布包的新版本了。
总结
以上就是今天要讲的内容,本文介绍了如何第一次上传第三方库到mavenCentral仓库,整个过程如有不懂的欢迎大家留言反馈,看到后会第一时间回复。