Maven最佳实践

作者: whoami2019 | 来源:发表于2018-10-31 14:54 被阅读4次

    Maven是什么?

    Maven是一个项目管理工具,它包含了一个项目对象模型 (Project Object Model),一组标准集合,一个项目生命周期(Project Lifecycle),一个依赖管理系统(Dependency Management System),和用来运行定义在生命周期阶段(phase)中插件(plugin)目标(goal)的逻辑。Maven本身的东西比较简单,主要是解析XML,主要功能是通过插件来实现的。

    • 项目对象模型
      Maven项目,依赖,构建配置,以及构件:所有这些都是要建模和表述的对象。这些对象通过pom.xml描述。
    • 一组标准集合
      Maven的设计坚持“约定优于配置”的原则,提供了很多默认的配置和插件间默认的协同逻辑,使用者只需要很少的配置即可。有些人会觉得这不如Ant灵活,可是Maven的提供的标准化却是高效的,通用的,当然也可以修改默认配置,可是不建议这样做。
    • 一个项目生命周期
      默认(default)的生命周期包括以下阶段:验证、编译、测试、打包、验证、安装、部署
    • 一个依赖管理系统
      这个应该就是大家最熟知的部分了,你不再需要面对一大堆jar感到头大,依赖冲突,无用依赖等问题也能够得到有效的防止和解决。

    最佳实践

    下面来总结一下Maven的最佳实践。

    Maven最佳实践:管理依赖

    依赖归类

    • 把groupId相同,artifactId不同的依赖放到一起,甚至是单独配置到1个pom.xml;
    • 把groupId相同,artifactId不同的依赖的版本号写成变量,把口子缩窄,当版本升级的时候只需要改一个地方,也能避免改动时导致版本不一致。

    依赖范围(scope)

    依赖范围 主源码classpath可用 测试源码classpath可用 会被打包
    compile缺省值 TRUE TRUE TRUE
    test FALSE TRUE FALSE
    runtime FALSE TRUE TRUE
    provided TRUE TRUE FALSE

    依赖管理(dependencyManagement)

    实际的项目中,你会有一大把的Maven模块,而且你往往发现这些模块有很多依赖是完全项目的,A模块有个对spring的依赖,B模块也有,它们的依赖配置一模一样,同样的groupId, artifactId, version,或者还有exclusions, classifer。细心的分会发现这是一种重复,重复就意味着潜在的问题,Maven提供的dependencyManagement就是用来消除这种重复的。
    正确的做法是:

    • 在父模块中使用dependencyManagement配置依赖
    • 在子模块中使用dependencies添加依赖

    dependencyManagement实际上不会真正引入任何依赖,dependencies才会。但是,当父模块中配置了某个依赖之后,子模块只需使用简单groupId和artifactId就能自动继承相应的父模块依赖配置。

    Maven最佳实践:划分模块

    所有用Maven管理的真实的项目都应该是分模块的,每个模块都对应着一个pom.xml。它们之间通过继承和聚合(也称作多模块,multi-module)相互关联。
    分模块的好处:

    • 方便重用,如果你有一个新的swing项目需要用到app-dao和app-service,添加对它们的依赖即可,你不再需要去依赖一个WAR。而有些模块,如app-util,完全可以渐渐进化成公司的一份基础工具类库,供所有项目使用。这是模块化最重要的一个目的
    • pom.xml依赖列表重用
    • 模块可以按需构建,缩短项目构建的时间
    • 遵守一个设计模式原则:“高内聚,低耦合”。虽然web中的controller、service、dao也分层了,这很好。但还不够,因为就构建层次来说,所有东西都被耦合在一起了。因此我们需要使用Maven划分模块
    • 某些模块,如app-util被所有人依赖,但你不想给所有人修改,现在你完全可以从这个项目结构出来,做成另外一个项目,svn只给特定的人访问,但仍提供jar给别人使用。

    Maven最佳实践:遵循约定

    标准的重要性不用我过于强调,想象一下如果不是所有人都基于HTTP开发WEB应用,这个世界会乱成怎样。Maven的用户都应该清楚,Maven提倡的是“约定优于配置(Convention Over Configuration)”,这是Maven最核心的理念之一。

    Maven约定

    配置 默认
    目录src/main/java java源码目录
    目录src/main/resources 资源文件目录
    目录src/test/java 测试java源码目录
    目录src/test/resources 测试资源文件目录
    目录target 打包输出目录
    目录target/classes 编译输出目录
    目录target/test-classes 测试编译输出目录
    目录target/site 项目site输出目录
    目录src/main/webapp web应用文件目录(当打包为war时),如WEB-INF/web.xml
    jar 默认打包格式
    *、Test.java Maven只会自动运行符合该命名规则的测试类
    %user_home%/.m2 Maven默认的本地仓库目录位置
    中央仓库 Maven默认使用远程中央仓库:http://repo1.maven.org/maven2
    1.3 Maven Compiler插件默认以1.3编译,因此需要额外配置支持1.5

    其实基本上所有的约定,或者说默认配置,都可以在Maven的超级POM(super pom)中找到。另外,Maven通过插件提供了绝大部分的默认实现,它们不用做任何配置(或者仅需要很少的配置),就能帮你完成你的工作。

    Maven最佳实践-distributionManagement

    mvn install 会将项目生成的构件安装到本地Maven仓库,mvn deploy 用来将项目生成的构件分发到远程Maven仓库(实际中一般是nexus私有仓库)。本地Maven仓库的构件只能供当前用户使用,在分发到远程Maven仓库之后,所有能访问该仓库的用户都能使用你的构件。我们需要配置POM的distributionManagement来指定Maven分发构件的位置,如下:

    settings.xml

    <settings>
    ...
    <servers>
    <server>
    <id>nexus-releases</id>
    <username>admin</username>
    <password>admin123</password>
    </server>
    <server>
    <id>nexus-snapshots</id>
    <username>admin</username>
    <password>admin123</password>
    </server>
    </servers>
    ...
    </settings>

    pom.xml


    <distributionManagement>
    <repository>
    <id>nexus-releases</id>
    <url>
    http://localhost:8081/nexus/content/repositories/releases/
    </url>
    </repository>
    <snapshotRepository>
    <id>nexus-snapshots</id>
    <url>
    http://localhost:8081/nexus/content/repositories/snapshots/
    </url>
    </snapshotRepository>
    </distributionManagement>

    需要注意的是,settings.xml中server元素下id的值必须与POM中repository或snapshotRepository下id的值完全一致。将认证信息放到settings下而非POM中,是因为POM往往是它人可见的,而settings.xml是本地的。

    最佳实践:版本管理

    主要内容:

    • snapshot和release版本的区别
    • 如何自动化版本发布,使用maven-release-plugin插件
    • Maven的版本规则:<主版本>.<次版本>.<增量版本>
    • 企业实际项目中一般将构件的不同版本分发到nexus私有仓库,使其能让其他项目使用,部署阶段需要用到上一个最佳实践

    相关文章

      网友评论

        本文标题:Maven最佳实践

        本文链接:https://www.haomeiwen.com/subject/dnvotqtx.html