Maven 制品库

该文本是关于Maven制品库的详细文档,涵盖了制品库的创建、令牌的获取与使用、本地及云原生环境下的配置与操作,包括拉取和推送制品的步骤,以及常见问题的解答。支持Maven和Gradle两种构建工具,并提供了开发与构建过程中的具体配置方法和使用示例。

创建制品库

参考 创建制品库

获取制品库地址

参考 获取制品库的地址

创建令牌

云原生构建平台的所有资源(包括代码仓库、制品库、OPENAPI等),都需要通过访问令牌进行操作。 创建令牌

本地开发

配置凭证

:::: tabs @tab Maven

将以下内容复制至settings.xml文件,替换 <YOUR_TOKEN> 为您的令牌, <REPO_RUL> 为制品库地址

<settings>
  <servers>
    <server>
      <id>cnb-maven</id>
      <username>cnb</username>
      <!-- 替换为访问令牌 -->
      <password><YOUR_TOKEN></password>
    </server>
  </servers>
  <profiles>
    <profile>
      <id>cnb-maven-profile</id>
      <repositories>
        <repository>
          <!-- 须与 server 的 id 一致 -->
          <id>cnb-maven</id>
          <!-- 替换为制品库地址 -->
          <!-- 示例 
          <url>https://maven.cnb.cool/cnb/maven_repo/-/packages/</url>
          -->
          <url><REPO_URL></url>
        </repository>
      </repositories>
      <activation>
        <activeByDefault>true</activeByDefault>
      </activation>
    </profile>
  </profiles>
</settings>

@tab Gradle

  1. 在项目根目录的gradle.properties中配置令牌,将 <YOUR_TOKEN> 替换为您的令牌
cnbArtifactsGradlePassword=<YOUR_TOKEN>
  1. 粘贴以下内容到build.gradle中,将 <REPO_RUL> 替换为制品库地址 ::: code-tabs @tab Kotlin
// build.gradle.kts
publishing {
    repositories {
        maven {
            val cnbArtifactsGradlePassword = project.findProperty("cnbArtifactsGradlePassword")
            
            // 示例
            // url = uri("https://maven.cnb.cool/cnb/maven_repo/-/packages/")
            url = uri("<REPO_URL>")
            credentials {
                username = "cnb"
                password = cnbArtifactsGradlePassword.toString()
            }
        }
    }
}

@tab Groovy

// build.gradle
publishing {
      repositories {
        maven {
            def cnbArtifactsGradlePassword = project.findProperty('cnbArtifactsGradlePassword')

            // 示例 
            // url = uri("https://maven.cnb.cool/cnb/maven_repo/-/packages/")
            url = uri('<REPO_URL>')
            credentials {
                username = 'cnb'
                password = cnbArtifactsGradlePassword.toString()
            }
        }
    }
}

::: ::::

拉取制品

:::: tabs @tab Maven

  1. 在 pom.xml 中配置您需要拉取的包
<dependencies>
    <dependency>
        <groupId>[GROUP_ID]</groupId>
        <artifactId>[ARTIFACT_ID]</artifactId>
        <version>[VERSION]</version>
    </dependency>
</dependencies>

<!-- 示例
<dependencies>
    <dependency>
        <groupId>org.cnb</groupId>
        <artifactId>maven_demo</artifactId>
        <version>9.0.0</version>
    </dependency>
</dependencies> -->
  1. 拉取制品
mvn clean install
# 如果选择指定位置的 settings.xml 请执行
mvn clean install -s ./settings.xml

@tab Gradle

  1. 在build.gradle中配置您所需要的依赖 ::: code-tabs @tab Kotlin
// build.gradle.kts
dependencies {
  implementation("[GROUP_ID]:[ARTIFACT_ID]:[VERSION]")
}

// 示例
// dependencies {
//  implementation("com.google.guava:guava:32.1.3-jre")
// }

@tab Groovy

// build.gradle
dependencies {
    implementation '[GROUP_ID]:[ARTIFACT_ID]:[VERSION]'
}

// 示例
// dependencies {
//   implementation 'com.google.guava:guava:32.1.3-jre'
// }

::: 2. 拉取制品

./gradlew build --refresh-dependencies

::::

推送制品

:::: tabs @tab Maven

  1. 在 pom.xml 中配置发布仓库,制品属性,替换 <REPO_URL> 为制品库地址
<project>
  <modelVersion>4.0.0</modelVersion>
  <!-- 制品属性 -->
  <groupId>[GROUP_ID]</groupId>
  <artifactId>[ARTIFACT_ID]</artifactId>
  <version>[VERSION]</version>

  <properties>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
  </properties>

  <!-- 发布仓库 -->
  <distributionManagement>
    <repository>
      <!-- 须与 settings.xml 中 server 的 id 一致 -->
      <id>cnb-maven</id>
      <name>cnb-maven</name>
      <!-- 示例 
      <url>https://maven.cnb.cool/cnb/maven_repo/-/packages/</url>
      -->
      <url><REPO_URL></url>
    </repository>
  </distributionManagement>
</project>
  1. 推送制品
mvn deploy
# 如果选择指定位置的 settings.xml,请执行
mvn deploy -s ./settings.xml

@tab Gradle

  1. 粘贴以下内容到 build.gradle 中 ::: code-tabs @tab Kotlin
// build.gradle.kts
plugins {
    `java-library`
    `maven-publish`
}

group = "[GROUP_ID]"
version = "[VERSION]"
val artifactName = "[ARTIFACT_ID]"

publishing {
    publications {
        create<MavenPublication>("myLibrary") {
            groupId = group.toString()
            version = version.toString()
            artifactId = artifactName
            from(components["java"])
        }
    }
}

@tab Groovy

// build.gradle
plugins {
    id 'java-library'
    id 'maven-publish'
}

group = '[GROUP_ID]'
version = '[VERSION]'
def artifactName = '[ARTIFACT_ID]'

publishing {
    publications {
        myLibrary(MavenPublication) {
            groupId = group
            version = version
            artifactId = artifactName
            from components.java
        }
    }
}

:::

  1. 执行上传命令
./gradlew publish

::::

云原生构建

配置凭证

云原生构建使用令牌有三种方式,参考云原生构建,云原生开发中使用令牌,以下是具体客户端的使用方式

:::: tabs @tab Maven

替换 <REPO_URL> 为制品库地址

<settings>
  <servers>
    <server>
      <id>cnb-maven</id>
      <username>cnb</username>
      <!--第一种方式 使用 CNB_TOKEN-->
      <password>${env.CNB_TOKEN}</password>
      <!--第二种方式 直接使用,替换 <your_token> 为您的令牌即可-->
      <!--<password><your_token></password>-->
      <!--第三种方式,密钥仓库,替换 <ENV_NAME> 为您密钥仓库的变量-->
      <!--<password>${env.<ENV_NAME>}</password>-->
    </server>
  </servers>
  <profiles>
    <profile>
      <id>cnb-maven-profile</id>
      <repositories>
        <repository>
          <!-- 须与 server 的 id 一致 -->
          <id>cnb-maven</id>
          <!-- 示例 
          <url>https://maven.cnb.cool/cnb/maven_repo/-/packages/</url>
          -->
          <url><REPO_URL></url>
        </repository>
      </repositories>
      <activation>
        <activeByDefault>true</activeByDefault>
      </activation>
    </profile>
  </profiles>
</settings>

@tab Gradle

替换 <REPO_URL> 为制品库地址 ::: code-tabs @tab Kotlin

publishing {
    repositories {
        maven {
            // 第一种方式 使用CNB_TOKEN
            val cnbArtifactsGradlePassword = System.getenv("CNB_TOKEN")
            // 第二种方式 直接使用令牌,替换<your_token>为您的令牌
            // val cnbArtifactsGradlePassword = "<your_token>"
            // 第三种方式,密钥仓库,替换 <ENV_NAME> 为您密钥仓库的变量
            // val cnbArtifactsGradlePassword = System.getenv("ENV_NAME")

            // 示例 
            // url = uri("https://maven.cnb.cool/cnb/maven_repo/-/packages/")
            url = uri("<REPO_URL>")
            credentials {
                username = "cnb"
                password = cnbArtifactsGradlePassword.toString()
            }
        }
    }
}

@tab Groovy

publishing {
      repositories {
        maven {
            // 第一种方式 使用CNB_TOKEN
            def cnbArtifactsGradlePassword = System.getenv("CNB_TOKEN")
            // 第一种方式 直接使用令牌,替换<your_token>为您的令牌
            // def cnbArtifactsGradlePassword = '<your_token>'
            // 第三种方式,密钥仓库,替换 <ENV_NAME> 为您密钥仓库的变量
            // def cnbArtifactsGradlePassword = System.getenv("ENV_NAME")

            // 示例 
            // url = uri("https://maven.cnb.cool/cnb/maven_repo/-/packages/")
            url = uri('<REPO_URL>')
            credentials {
                username = 'cnb'
                password = cnbArtifactsGradlePassword.toString()
            }
        }
    }
}

::: ::::

拉取制品

将如下内容粘贴至 .cnb.yml ::: tabs

@tab Maven

main:
  push:
    - docker:
        image: maven:3.8.6-openjdk-8
      stages:
        - name: mvn package
          script:
            mvn clean install -s ./settings.xml

@tab Gradle

main:
  push:
    - docker:
        image: gradle:7.6.6-jdk17
      stages:
        - name: gradle build and run
          script:
            - ./gradlew build --refresh-dependencies

:::

推送制品

将如下内容粘贴至 .cnb.yml

::: tabs @tab Maven

main:
  push:
    - docker:
        image: maven:3.8.6-openjdk-8
      stages:
        - name: mvn package
          script:
            mvn clean deploy -s ./settings.xml

@tab Gradle

main:
  push:
    - docker:
        image: gradle:7.6.6-jdk17
      stages:
        - name: gradle publish
          script:
            - ./gradlew publish

:::

云原生开发

配置凭证

云原生构建 配置凭证 相同

配置开发镜像

根据不同客户端选择您的开发镜像 ::: tabs @tab Maven

$:
  vscode:
    - docker:
        image: maven:3.8.6-openjdk-8

@tab Gradle

$:
  vscode:
    - docker:
        image: gradle:7.6.6-jdk17

:::

拉取制品

本地开发 拉取制品 相同

推送制品

本地开发 推送制品 相同

示例

Gradle本地推送apk包

  1. 配置 android-application 插件, 配置文件在 gradle/libs.versions.toml
[versions]
agp = "8.11.1"
[plugins]
android-application = { id = "com.android.application", version.ref = "agp" }
  1. 在 build.gradle 中配置maven推送插件, apk打包插件 ::: code-tabs @tab Kotlin
// build.gradle.kts
plugins {
    id("com.android.application") // apk打包插件
    id("maven-publish") 
}

@tab Groovy

// build.gradle
plugins {
    id 'com.android.application'  // apk打包插件
    id 'maven-publish'
}

::: 3. 在 build.gradle中 配置构建任务和推送地址 ::: code-tabs @tab Kotlin

// build.gradle.kts
afterEvaluate {
    publishing {
        publications {
            create<MavenPublication>("releaseApk") {
                groupId = "cnb" 
                artifactId = "artifact"
                version = "1.0.0"

                // 如果需要发布签名应用则为 outputs/apk/release/${project.name}-release.apk
                val apkFile = layout.buildDirectory.file(
                    "outputs/apk/release/${project.name}-release-unsigned.apk"
                ).get().asFile

                artifact(apkFile) {
                    builtBy(tasks.named("assembleRelease"))
                    classifier = "release"
                    extension = "apk"
                }
            }
        }
        repositories {
            maven {
                // 可在 gradle.properties 文件中声明 cnbArtifactsGradlePassword = 你在 cnb 的访问令牌
                // 或者 export CNB_TOKEN=${YOUT_TOKEN}
                val cnbArtifactsGradlePassword = System.getenv("CNB_TOKEN") ?: project.findProperty("cnbArtifactsGradlePassword")

                // 示例 
                // url = uri("https://maven.cnb.cool/cnb/maven_repo/-/packages/")
                url = uri("<REPO_URL>")
                credentials {
                    username = "cnb"
                    password = cnbArtifactsGradlePassword.toString()
                }
            }
        }
    }
}

@tab Groovy

// build.gradle
afterEvaluate {
    publishing {
        publications {
            releaseApk(MavenPublication) {
                // 配置成您需要的
                groupId = 'cnb'
                artifactId = "artifact"
                version = '1.0.0'

                // 如果需要发布签名应用则为 outputs/apk/release/${project.name}-release.apk
                def apkFile = layout.buildDirectory.file(
                    'outputs/apk/release/${project.name}-release-unsigned.apk'
                ).get().asFile

                artifact(apkFile) {
                    builtBy tasks.assembleRelease
                    classifier = 'release'
                    extension = 'apk'
                }
            }
        }
        repositories {
            maven {
                // 可在 gradle.properties 文件中声明 cnbArtifactsGradlePassword = 你在 cnb 的访问令牌
                // 或者 export CNB_TOKEN=${YOUT_TOKEN}
                def cnbArtifactsGradlePassword = System.getenv('CNB_TOKEN') ?: project.findProperty('cnbArtifactsGradlePassword')

                // 示例 
                // url = uri("https://maven.cnb.cool/cnb/maven_repo/-/packages/")
                url = '<REPO_URL>'
                credentials {
                    username = 'cnb'
                    password = cnbArtifactsGradlePassword.toString()
                }
            }
        }
    }
}

::: 4. 执行如下命令

./gradlew publish

Gradle本地推送aar包

  1. 配置android-library插件, 配置文件在 gradle/libs.versions.toml
[versions]
agp = "8.11.1"
[plugins]
android-library = { id = "com.android.library", version.ref = "agp" }
  1. 配置aar打包插件和maven推送插件 ::: code-tabs @tab Kotlin
// build.gradle.kts
plugins {
    id("com.android.library") // aar打包插件
    id("maven-publish") 
}

@tab Groovy

// build.gradle
plugins {
    id 'com.android.library'  // aar打包插件
    id 'maven-publish'
}

:::

  1. 在 build.gradle中 配置构建任务和推送地址 ::: code-tabs @tab Kotlin
// build.gradle.kts
afterEvaluate {
    publishing {
        publications {
            create<MavenPublication>("releaseAar") {
                // 配置成您需要的
                groupId = "cnb" 
                artifactId = "artifact"
                version = "1.0.0"

                from(components["release"])
            }
        }
        repositories {
            maven {
                // 可在 gradle.properties 文件中声明 cnbArtifactsGradlePassword = 你在 cnb 的访问令牌
                // 或者 export CNB_TOKEN=${YOUT_TOKEN}
                val cnbArtifactsGradlePassword = System.getenv("CNB_TOKEN") ?: project.findProperty("cnbArtifactsGradlePassword")

                // 示例 
                // url = uri("https://maven.cnb.cool/cnb/maven_repo/-/packages/")
                url = uri("<REPO_URL>")
                credentials {
                    username = "cnb"
                    password = cnbArtifactsGradlePassword.toString()
                }
            }
        }
    }
}

@tab Groovy

// build.gradle
afterEvaluate {
    publishing {
        publications {
            releaseAar(MavenPublication) {
                // 配置成您需要的
                groupId = 'cnb'
                artifactId = "artifact"
                version = '1.0.0'

                from components.release
            }
        }
        repositories {
            maven {
                // 可在 gradle.properties 文件中声明 cnbArtifactsGradlePassword = 你在 cnb 的访问令牌
                // 或者 export CNB_TOKEN=${YOUT_TOKEN}
                def cnbArtifactsGradlePassword = System.getenv('CNB_TOKEN') ?: project.findProperty('cnbArtifactsGradlePassword')

                // 示例 
                // url = uri("https://maven.cnb.cool/cnb/maven_repo/-/packages/")
                url = uri("<REPO_URL>")
                credentials {
                    username = 'cnb'
                    password = cnbArtifactsGradlePassword.toString()
                }
            }
        }
    }
}

:::

  1. 执行如下命令
./gradlew publish

FAQ

覆盖已有版本后,依赖构建仍使用覆盖前的版本?

Maven机制如此,本地缓存有,就不去远程仓库中拉取。有三种解决方案:

  1. 使用--update-snapshots命令,该命令强制Maven检查远程仓库中快照依赖的更新,此策略仅对 SNAPSHOT 有效
mvn clean package -U
  1. 移除缓存中的包,直接删除maven在本地的缓存
# macOS和Linux 默认位置为 ~/.m2
# Windows 默认位置为 C:\Users\{用户名}\.m2\repository
# 也可以直接通过如下命令查询
mvn help:evaluate -Dexpression=settings.localRepository
  1. 将settings.xml 对应依赖仓库的 updatePolicy 调整为 true, 此策略仅对 SNAPSHOT 有效
<settings>
  <profiles>
    <profile>
      <id>cnb-maven-profile</id>
      <repositories>
        <repository>
          <id>cnb-maven</id>
          <url><REPO_URL></url>
          <!-- 这里配置snapshot版本的拉取策略 -->
          <snapshots>
            <enabled>true</enabled>
            <updatePolicy>always</updatePolicy>
          </snapshots>
        </repository>
      </repositories>
      <activation>
        <activeByDefault>true</activeByDefault>
      </activation>
    </profile>
  </profiles>
</settings>

遇到 409 Forbidden

您已经上传过此包且禁止覆盖,如需覆盖包,请进入对应制品仓库->制品库设置->策略管理

  • 仅覆盖SNAPSHOT,请选择 Maven Snapshot策略
  • 覆盖SNAPSHOT和RELEASE,请选择 允许覆盖全部已有版本

更多用法

更多 Maven 用法,请查阅 Maven 官方文档

点评

点赞或评论
加载评论中...