maven

其实 java 里面的确有一些不错的东西,比如说 maven。

和 maven 比较的很多次的另一个工具是 ant,这个基本上沿袭了 make 的思路,但是使用了 XML 语法描述编译等等的依赖关系。个人觉得 XML 的选择是一种失败的搞法,因为不适合人来写。但是也有人觉得不错,因为很多时候 IDE 能够帮助我们生成合理的文件。maven 在此之上提出了一种和 repository 结合的做法,它提供了中心的 repository 供项目使用,这意味着项目所依赖的外部资源可以通过 maven 自动的获得。wikipedia 上将 maven 与 ant 做了一个比较细致的比较,

  • maven 假定项目有一定的“固定结构”,而 ant 并没有类似的假设,这是什么意思呢?也就是说 maven 会认为你的 source code 一般放在 src/ 里面,主要的程序在 src/main 而测试在 sr/test,这更像一个 IDE,它不会问你你要把 source code 放在哪里,而是自动的帮你放在那里了,你不按照它的规定来就会很麻烦;ant 却没有这种严格的假定,虽然很多项目也是这样组织代码的,但是 ant 本身并不限制你一定要这样做
  • maven 藉此假定更注重一些 high level 的项目理念,而 ant 仍然停留在 low-level 上各个 target 的依赖关系上。比如 maven 提供了所谓 life cycle 的概念,帮助开发者能比较清楚的了解这个项目的进度;ant 更倾向让编写人员设定不同的目标,让这些目标彼此依赖,藉此表述某种 high level 的概念。这意味着 ant 的语法可能更加简单,因为只涉及 target 的关系,什么都不懂的人看看也许也能写出 ant 的 build.xml;但是很可能不同的项目表述自己的 high-level 概念通过的依赖关系并不一样,因此很难看懂不懂项目直接这些概念的异同。但是对 maven 却不一样,因为它提供的 life cycle 在不同 project 上是一致或者类似的,这样对 maven 有一定了解的人能够很快了解其他的项目的 high-level 概念,尽管新手可能不是太理解这些东西
  • 从这个角度来说 maven 更适合比如与 IDE 整合,它牺牲了一定的“自由度”,换来的是 consistency,降低了不同 project 之间的学习成本

与 maven 类似的衍生工具还有 gradle(首页见此,没有使用 XML 而是用了一种 DSL groovy 来描述项目),scala 的 sbt(首页见此,也是用自己的 DSL)似乎也用了 maven 的 repository。下面我们来看一个简单的例子。我们只需要简单的执行一下

mvn archetype:generate -DgroupId=com.mycompany.app -DartifactId=my-app -DarchetypeArtifactId=maven-archetype-quickstart -DinteractiveMode=false

就能生成我们需要的一些结构,并且可以到此目录里面 mvn package 并执行了。由此看来,我们创建一个项目首先可以选择一个合理的 archetype,之后有些什么就是靠编辑对应的 pom.xml 了。其他的一些细节可以参看这里

maven 的 archetype

archetype 的目的就是为某种类型的项目生成一个框架,这使得某些公司可以为自己的规范形成合适的初始态,帮助程序员 follow 规范,常用的一些 archetype 包括

  • maven-archetype-archetype 用来开发 archetype 的 archetype
  • maven-archetype-j2ee-simple 用来开发 j2ee 程序
  • maven-archetype-mojo 开发 maven plugin 的 sample
  • maven-archetype-plugin(-site) 开发 maven plugin (site) 的 archetype
  • maven-archetype-portlet 开发 JSR-268
  • maven-archetype-quickstart 和 maven-archetype-simple 一般通用的 archetype
  • maven-archetype-site(-simple) 开发 site
  • maven-archetype-webapp 开发 web app

从合适的 archetype 出发能减少额外的配置。

maven 的 pom.xml

项目的 pom.xml 继承自一个公共的 super pom.xml,这个 pom 里面比较重要的有

  • modelVersion、name 标记一些常量
  • repositories 表示使用的仓库,pluginsRepositories 表示 plugin 的仓库
  • build 里面是关于源文件路径、测试文件路径、编译出来的目录

下面是个简单的例子

<project>
  <modelVersion>4.0.0</modelVersion>
  <groupId>com.mycompany.app</groupId>
  <artifactId>my-app</artifactId>
  <version>1</version>
</project>

如果我们需要产生层次结构,可以用 parent,如

<project>
  <parent>
    <groupId>com.mycompany.app</groupId>
    <artifactId>my-app</artifactId>
    <version>1</version>
  </parent>
  <modelVersion>4.0.0</modelVersion>
  <groupId>com.mycompany.app</groupId>
  <artifactId>my-module</artifactId>
  <version>1</version>
</project>

如果并非子目录关系,我们可以用 relativePath,如果我们希望 module 被整合进原先的 project 可以用 modules 将其包括。另外可以用 $ 和花括号表示某些变量的值,常用的有 basedir,还可以在 properties 里面设定一些值。下面是依赖关系的例子,

<project>
  <dependencies>
    <dependency>
      <groupId>junit</groupId>
      <artifactId>junit</artifactId>
      <version>3.8.1</version>
      <scope>test</scope>
    </dependency>
  </dependencies>
</project>

通过 plugin 我们可以增强 mvn 的功能,下面是一个使用 plugin 的例子

<build>
  <plugins>
    <plugin>
      <groupId>org.apache.maven.plugins</groupId>
      <artifactId>maven-compiler-plugin</artifactId>
      <version>2.0.2</version>
      <configuration>
        <source>1.5</source>
        <target>1.5</target>
      </configuration>
    </plugin>
  </plugins>
</build>

是一些官方的 plugin,还是很不错的一个 set。

使用 maven 管理 C/C++

这个可以使用 maven-nar-plugin。看起来也沿袭了 maven 那套 repository 的东西,挺有意思,不清楚与现有的 auto-make、cmake 等是否有重大区别。

——————
Now therefore swear to me here by God that you will not deal falsely with me, nor with my son, nor with my son’s son: but according to the kindness that I have done to you, you shall do to me, and to the land wherein you have sojourned.

Advertisements
maven

发表评论

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / 更改 )

Twitter picture

You are commenting using your Twitter account. Log Out / 更改 )

Facebook photo

You are commenting using your Facebook account. Log Out / 更改 )

Google+ photo

You are commenting using your Google+ account. Log Out / 更改 )

Connecting to %s