提交项目到Maven中央仓库

之前提到我写了一个读取ply格式的工具放到了Github上,想要引用这个库可以用 mvn package 把 jar 打包出来,但是我习惯了在 pom.xml 中引入依赖项,我就想能否直接把那个库提交到Maven仓库上,断断续续弄了几天最后真的放上去了。其实整个过程还算简单,主要就参考了一篇中文博客,这里大概把遇到的问题记一下。

申请创建 Project

第一步是去 Sonatype注册一个账号。完成注册进入 Dashboard 后点击最上方的 Create :

页面会弹出一个模态框,把该填的填上,所有描述性的输入我都用英文,至于 Usernames 那一栏,虽然我估计不用填,但还是把自己在 Sonatype 上的用户名给填进去了。


然后就等待审核,我大概等了 5 天左右,不必每天登录上去看,审核通过后会有邮件通知。
审核通过后,我啥也没管,也没有像别的博客里提到的 close issue 之类的操作。

补全项目 pom.xml 中的信息

先不说如何部署到仓库上,先说几个必要的步骤。
pom.xml 中有些信息是必须的:

  • 项目描述(description)
  • 开源许可 (license)
  • 开发者信息(developers)
  • 去哪提 issue(issueManagement)
  • 版本控制(scm)
    当时我不知道,缺了好多,提交上去就报了错。后来就照葫芦画瓢把信息补上去了:
<?xml version="1.0" encoding="UTF-8"?>

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
  <modelVersion>4.0.0</modelVersion>

  <groupId>cn.jimmiez</groupId>
  <artifactId>pcutil</artifactId>
  <version>0.0.3</version>
  <description>A 3d point cloud utility.</description>
  <name>pcutil</name>
  <url>http://www.jimmiez.cn/pcu/</url>

  <properties>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    <maven.compiler.source>1.7</maven.compiler.source>
    <maven.compiler.target>1.7</maven.compiler.target>

  </properties>

  <packaging>jar</packaging>

  <licenses>
    <license>
      <name>MIT License</name>
      <url>https://opensource.org/licenses/MIT</url>
      <distribution>repo</distribution>
    </license>
  </licenses>

  <developers>
    <developer>
      <email>cquzjl@gmail.com</email>
      <name>Jianling Zhou</name>
      <url>https://github.com/Jimmie00x0000</url>
      <id>Jimmie00x0000</id>
    </developer>
  </developers>

  <issueManagement>
    <url>https://github.com/Jimmie00x0000/PointCloudUtil/issues</url>
    <system>GitHub Issues</system>
  </issueManagement>
  <scm>
    <url>https://github.com/Jimmie00x0000/PointCloudUtil</url>
    <connection>scm:git:https://git@github.com/Jimmie00x0000/PointCloudUtil.git</connection>
  </scm>



  <distributionManagement>
    <snapshotRepository>
      <id>sonatype</id>
      <url>https://oss.sonatype.org/content/repositories/snapshots</url>
    </snapshotRepository>
    <repository>
      <id>sonatype</id>
      <url>https://oss.sonatype.org/service/local/staging/deploy/maven2/</url>
    </repository>
  </distributionManagement>

  <dependencies>
    
  </dependencies>

  <build>
    <resources>
      <resource>
        <directory>${basedir}/src/main/resources</directory>
      </resource>
    </resources>
    <testResources>
      <testResource>
        <directory>${basedir}/src/test/resources</directory>
      </testResource>

    </testResources>
    <plugins>
      <plugin>
        <artifactId>maven-clean-plugin</artifactId>
        <version>3.0.0</version>
      </plugin>
      <!-- see http://maven.apache.org/ref/current/maven-core/default-bindings.html#Plugin_bindings_for_jar_packaging -->
      <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-source-plugin</artifactId>
        <version>2.2.1</version>
        <executions>
          <execution>
            <id>attach-sources</id>
            <goals>
              <goal>jar-no-fork</goal>
            </goals>
          </execution>
        </executions>
      </plugin>
      <plugin>
        <artifactId>maven-resources-plugin</artifactId>
        <version>3.0.2</version>
      </plugin>
      <plugin>
        <artifactId>maven-compiler-plugin</artifactId>
        <version>3.7.0</version>
      </plugin>
      <plugin>
        <artifactId>maven-surefire-plugin</artifactId>
        <version>2.20.1</version>
      </plugin>
      <plugin>
        <artifactId>maven-jar-plugin</artifactId>
        <version>3.0.2</version>
      </plugin>
      <plugin>
        <artifactId>maven-install-plugin</artifactId>
        <version>2.5.2</version>
      </plugin>
      <plugin>
        <artifactId>maven-site-plugin</artifactId>
        <version>3.3</version>
      </plugin>
      <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-project-info-reports-plugin</artifactId>
        <version>2.7</version>
      </plugin>
      <plugin>
        <artifactId>maven-deploy-plugin</artifactId>
        <version>2.8.2</version>
      </plugin>
      <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-gpg-plugin</artifactId>
        <version>1.6</version>
        <executions>
          <execution>
            <id>sign-artifacts</id>
            <phase>verify</phase>
            <goals>
              <goal>sign</goal>
            </goals>
            <configuration>
              <keyname>${gpg.keyname}</keyname>
              <passphraseServerId>${gpg.keyname}</passphraseServerId>
            </configuration>
          </execution>
        </executions>
      </plugin>
      <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-javadoc-plugin</artifactId>
        <version>3.0.1</version>
        <executions>
          <execution>
            <id>attach-javadocs</id>
            <goals>
              <goal>jar</goal>
            </goals>
          </execution>
        </executions>
      </plugin>
    </plugins>
  </build>
</project>

文档信息

这一部分我不是很确定,因为我怀疑 javadoc 不是必须的。
我第一次提交出了错,除了 pom.xml 中缺了信息外,Nexus 系统还告诉我没有附上 source 和 javadoc。

格式

然后我就研究了下,首先,你需要确保你的 JavaDoc 没有格式上的错误,对于你的库的API,你可以不写doc,但是一定要保证没有格式上的错误。常见的错误:

  • 写了 @param ,忘了 @return
/**
 * this is another api, bala bala
 * @param foo is to xxx
 **/
public int api1(String foo) {
    // ....
    return 0;
}
  • 在标签以外的地方乱用尖括号 > 和 <
/**
 * this is an api , you can refer to -> cn.edu.cqu.xxx.
 * @param foo is to xxx
 * @return status code
 **/
public int api2(String foo) {
    // ....
    return 0;
}

像 IntelliJ IDEA 这样的 IDE会在你 doc 错误的地方提示的,所以不要忽视 IDE 的警告。

附上 doc

为此我去翻了 apache maven-doc plugin 的文档,最后发现的简单的办法好像就是在 pom.xml 中声明插件就 OK了:

<plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-source-plugin</artifactId>
        <version>2.2.1</version>
        <executions>
          <execution>
            <id>attach-sources</id>
            <goals>
              <goal>jar-no-fork</goal>
            </goals>
          </execution>
        </executions>
      </plugin>
<plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-javadoc-plugin</artifactId>
        <version>3.0.1</version>
        <executions>
          <execution>
            <id>attach-javadocs</id>
            <goals>
              <goal>jar</goal>
            </goals>
          </execution>
        </executions>
      </plugin>

想要验证能否无错误地生成javadoc的话,可以在项目的根目录下执行

mvn site

之后根目录下的 target 目录下就会出现 site 目录,点击进去就可以看到根据你的 doc 生成的网页了。注意生成site这个目录只是一个调试行为,并不是上传到Maven仓库所需要的命令

在这里我踩了一个坑,就是我用 IDEA 的自带工具,结果并不能生成 javadoc ,不知何故。

签名

想要上传到仓库,jar 包必须被签名,这一步略麻烦。首先要下载 gpg4win,下载地址

安装好后,需要生成签名所需要的公私钥对,进入命令行,输入

gpg --gen-key

之后需要输入一些信息,像名字之类的,可以和 Sonatype 里的不一样,之后会弹个框让你设置一个密码,这个密码一定要记住,之后部署的时候需要输入。

安装了 gpg4win 后应该还会装上一个 Kleopatra 的客户端,打开这个软件,右键你刚才生成证书,点击“在服务器上发布”。


之后在 Maven 的 setting.xml 的 servers 标签下插入如下信息

<server>
        <id>sonatype</id>
        <username>你在sonatype上的用户名</username>
        <password>你在sonatype上的密码</password>
      </server>

部署到仓库

搞定了上述步骤后,在项目根目录下输入如下命令。如果最后看到了 BUILD SUCCESS,基本就没有太大问题了。

mvn deploy -X

使用 Sonatype 的用户名和密码,进入仓库的管理页面。注意上传成功后这次提交在Nexus Repo Manager 只会处于一个暂存的状态。

想要发布到中央仓库,先通过包名找到你的仓库(如果找不到说明没有上传成功,回去看看是不是忘了在 pom.xml 里指定 distributionManagement),选中仓库,上面有 close 可选。先close,再release。但是点击close不一定会成功,因为系统会检查你这次提交,比如javadoc有没有问题,有没有签名,有没有缺少信息之类的,检查的结果可以在下方的 Activity 标签页看到。

如果 close 失败,可以点击 drop 放弃这次提交,记得当时我还犹豫了会,在想这个 drop 会不会直接把 Project 给 drop 掉,事实证明不会。

如果 close 成功了,点击 release。不出啥意外的话大概等待五六个小时就可以在中央仓库上查到你的库了。

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 211,948评论 6 492
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 90,371评论 3 385
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 157,490评论 0 348
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 56,521评论 1 284
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 65,627评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 49,842评论 1 290
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,997评论 3 408
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,741评论 0 268
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,203评论 1 303
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,534评论 2 327
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,673评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,339评论 4 330
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,955评论 3 313
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,770评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,000评论 1 266
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,394评论 2 360
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,562评论 2 349

推荐阅读更多精彩内容

  • 为什么写这篇文章 现在OkHttp很火,研究学习了一下,铺天盖地的教程和通用工具都是Android用的,封装了很多...
    邪影oO阅读 13,918评论 13 25
  • 最近尝试发布自己的项目到Maven中央仓库,发现网上的教程虽然不少,但多多少少都有一些问题,其中最主要的问题是...
    伊凡的一天阅读 9,770评论 17 5
  • 本文系转载,原文地址: https://www.iteblog.com/archives/1807.html 本博...
    冯文议阅读 9,014评论 8 2
  • 周日花了一个下午五个小时完成一幅画,虽然耗时弥久,但丝毫不觉乏味,反而觉得自己在创造一件作品。羡慕做画师的人,在画...
    chensannihao阅读 116评论 0 0
  • 这几天只想死,做设计真的不是人干的, 特别是文件没存起,天昏地暗 痛不欲生 求死不得 所有的所有 一个字 烦 闷 ...
    暖暖栗子阅读 208评论 0 0