maven入门

来源:互联网 发布:手机淘宝怎么寄件 编辑:程序博客网 时间:2024/05/08 17:09
1、配置Java运行环境
Maven依赖Java运行环境,因此使用Maven之前需要配置Java的运行环境。下载并安装JDK,配置JDK的环境变量:
    JAVA_HOME=D:\Dev\Tool\Java\jdk1.6.0_38
    在path中加入%JAVA_HOME%\bin;
2、安装Maven
Maven下载地址:http://maven.apache.org/download.cgi
下载Maven最新版本的二进制zip压缩包就可以,如:apache-maven-3.0.5-bin.zip
下载完成后,解压,例如我们把解压后的文件夹放在D:\Dev\Tool\目录下。
然后,将Maven的bin目录添加到path环境变量中,我们这里就是这个目录:D:\Dev\Tool\apache-maven-3.0.4\bin
 
在Windows命令提示符下,输入mvn -v测试一下,如图:
 
这样,maven就安装完成了,就是这么简单。接下来我们先来了解一下Maven是如何来管理项目的。
三、Maven依赖管理
前面讲了,Maven最核心的就是对依赖jar包的管理,那么它是通过什么方式来进行管理的呢?
Maven要求每一个jar包都必须明确定义自己的坐标,Maven就是通过这个坐标来查找管理这些jar包的。
在Maven中,一个jar包的坐标是由它的groupId、artifactId、version这些元素来定义的。例如:
    <groupId>org.apache.struts</groupId>
    <artifactId>struts2-core</artifactId>
    <version>2.3.8</version>
    <packaging>jar</packaging>
groupId:表明其所属组织或公司及其所属项目,命名规则为组织或公司域名反转加项目名称。
artifactId:项目的模块名,通常与实际项目名称一致。模块的命名通常为项目名前缀加模块名。
version:当前项目的版本号。
packaging:定义项目的打包方式,可选值有jar、war、pom。默认为jar
注::一个组织或公司都会有很多的项目,而每个项目下都会划分多个模块,在开发中我们可以灵活选择依赖某个模块。而Maven管理的jar包基本都是模块性质的项目构建出的jar包。所以,artifactId通常都是模块名,而不是项目名称。项目名称是和组织名称组合作为groupId来使用的。
 
上面的配置定义了一个Maven项目的坐标,而如果在项目中依赖这个项目时,同样是利用它的坐标来指定依赖。例如:
<project>
    ...
    <dependencies>
        <dependency>
            <groupId>org.apache.struts</groupId>
            <artifactId>struts2-core</artifactId>
            <version>2.3.8</version>
        </dependency>
    </dependencies>
    ...
</project>
 
Maven的配置文件中dependencies元素包含了所有依赖的jar包,每一个jar包依赖使用dependency元素定义。
在声明一个jar包依赖时,除了指定groupId、artifactId、version这三项基本坐标外,还可以使用使用以下元素进行配置:
scope元素:指定依赖的范围
exclusions元素:排除传递性依赖
 
Maven有以下几种依赖范围:
compile:编译依赖范围(默认值),依赖在编译、测试、运行期间都有效。
test:测试依赖范围,只对测试的classpath有效,在编译或运行时无法使用指定为test的依赖包。
provided:已提供的依赖范围,只对编译和测试的classpath有效,运行期间不会使用这个依赖。例如servlet-api,在运行时容器已经提供,不需要再重复引入。
runtime:运行时依赖范围,编译时无效,只在测试和运行时使用这个依赖。
system:系统依赖范围,和provided范围一致,但是provided是使用容器提供依赖,system是使用系统提供依赖,需要指定依赖文件路径。
 
传递性依赖,是指依赖包对其他包的依赖,比如,我们依赖struts2-core,而strtus2-core需要依赖xwork-core、ognl等,Maven会将这些传递性依赖同时引入项目之中。这也是Maven的一大优点,简化了我们对jar包依赖的管理。而有时我们希望替换某个传递性依赖时,就需要使用exclusions排除掉这个传递性依赖,然后再添加我们自己要替换的依赖包。
 
例如,如下一个Maven的配置文件,pom.xml:
  1. <?xml version="1.0" encoding="UTF-8"?>  
  2. <project xmlns="http://maven.apache.org/POM/4.0.0"  
  3.     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"  
  4.     xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">  
  5.   
  6.     <modelVersion>4.0.0</modelVersion>  
  7.     <groupId>com.boya.spring</groupId>  
  8.     <artifactId>spring_ioc</artifactId>  
  9.     <packaging>jar</packaging>  
  10.     <version>1.0.0</version>  
  11.   
  12.     <name>${project.artifactId}</name>  
  13.     <description>Spring Ioc Sample</description>  
  14.   
  15.     <dependencies>  
  16.         <!-- spring start -->  
  17.         <dependency>  
  18.             <groupId>org.springframework</groupId>  
  19.             <artifactId>spring-core</artifactId>  
  20.             <version>3.2.0.RELEASE</version>  
  21.             <exclusions>  
  22.                 <exclusion>  
  23.                     <groupId>commons-logging</groupId>  
  24.                     <artifactId>commons-logging</artifactId>  
  25.                 </exclusion>  
  26.             </exclusions>  
  27.         </dependency>  
  28.         <dependency>  
  29.             <groupId>org.springframework</groupId>  
  30.             <artifactId>spring-beans</artifactId>  
  31.             <version>3.2.0.RELEASE</version>  
  32.         </dependency>  
  33.         <dependency>  
  34.             <groupId>org.springframework</groupId>  
  35.             <artifactId>spring-context</artifactId>  
  36.             <version>3.2.0.RELEASE</version>  
  37.         </dependency>  
  38.   
  39.         <!-- logging start -->  
  40.         <dependency>  
  41.             <groupId>org.slf4j</groupId>  
  42.             <artifactId>slf4j-api</artifactId>  
  43.             <version>1.6.4</version>  
  44.         </dependency>  
  45.         <dependency>  
  46.             <groupId>org.slf4j</groupId>  
  47.             <artifactId>slf4j-log4j12</artifactId>  
  48.             <version>1.6.4</version>  
  49.         </dependency>  
  50.         <dependency>  
  51.             <groupId>org.slf4j</groupId>  
  52.             <artifactId>jcl-over-slf4j</artifactId>  
  53.             <version>1.6.4</version>  
  54.         </dependency>  
  55.         <dependency>  
  56.             <groupId>log4j</groupId>  
  57.             <artifactId>log4j</artifactId>  
  58.             <version>1.2.16</version>  
  59.         </dependency>  
  60.         <dependency>  
  61.             <groupId>log4jdbc</groupId>  
  62.             <artifactId>log4jdbc4</artifactId>  
  63.             <version>1.2</version>  
  64.         </dependency>  
  65.   
  66.         <!--Test start-->  
  67.         <dependency>  
  68.             <groupId>junit</groupId>  
  69.             <artifactId>junit</artifactId>  
  70.             <version>4.10</version>  
  71.             <scope>test</scope>  
  72.         </dependency>  
  73.     </dependencies>  
  74. </project>  
 
四、Maven仓库
Maven通过项目定义的坐标来管理这些依赖,而这些依赖的物理文件是通过Maven的仓库来统一管理的。
对于一个依赖坐标,它会按照如下方式反映到Maven的仓库中。
1、将groupId转化为路径:将groupId中的包名分隔符(.)转换成路径分隔符(/)。对于上面的例子就是 org.apache.struts -> org/apache/struts/
2、将artifactId转化为路径:在groupId转化的路径基础上连接artifactId。生成路径为: org/apache/struts/struts2-core/
3、将verion转化为路径:在artifactId转化的路径基础上连接version。生成路径为: org/apache/struts/struts2-core/2.3.8/
4、根据artifactId和version生成依赖包文件名:上例就是 struts2-core-2.3.8
5、根据依赖的打包方式确定文件的扩展名。对于上例它的扩展名就是.jar
 
这样根据路径和文件名就找到了这个物理文件在仓库中的位置:org/apache/struts/struts2-core/2.3.8/struts2-core-2.3.8.jar
 
Maven的仓库分为本地仓库和远程仓库。
本地仓库:是Maven在我们本机设置的仓库目录,默认目录为当前用户目录下的.m2/repository.
远程仓库包括中央仓库、私服、其他公共仓库。
中央仓库是Maven提供的远程仓库,地址是:http://repo.maven.apache.org/maven2
私服是我们为了节省带宽和时间,提升效率,在局域网架设的私有Maven仓库。
其他公共库有Java.net的maven库(http://download.java.net/maven/2/)和JBoss Maven库(http://repository.jboss.com/)等。
 
Maven在根据依赖坐标查找依赖时,首先会从本地仓库查找该依赖包,当本地仓库中没有这个依赖包时,Maven会从中央仓库查找依赖,并下载到本地仓库。最后,在我们项目的classpath中引用本地仓库的依赖包路径。
例如,当项目只依赖strtus2-core这个依赖包时,会生成这样的classpath文件:
  1. <?xml version="1.0" encoding="UTF-8"?>  
  2. <classpath>  
  3.   <classpathentry kind="src" path="src/main/java" output="/src/main/webapp/WEB-INF/classes" including="**/*.java"/>  
  4.   <classpathentry kind="src" path="src/main/resources" output="/src/main/webapp/WEB-INF/classes" excluding="**/*.java"/>  
  5.   <classpathentry kind="output" path="src/main/webapp/WEB-INF/classes"/>  
  6.   <classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER"/>  
  7.   <classpathentry kind="con" path="com.genuitec.eclipse.j2eedt.core.J2EE14_CONTAINER"/>  
  8.   <classpathentry kind="var" path="M2_REPO/org/apache/struts/struts2-core/2.3.8/struts2-core-2.3.8.jar" />  
  9.   <classpathentry kind="var" path="M2_REPO/org/apache/struts/xwork/xwork-core/2.3.8/xwork-core-2.3.8.jar" />  
  10.   <classpathentry kind="var" path="M2_REPO/org/apache/commons/commons-lang3/3.1/commons-lang3-3.1.jar" />  
  11.   <classpathentry kind="var" path="M2_REPO/ognl/ognl/3.0.6/ognl-3.0.6.jar" />  
  12.   <classpathentry kind="var" path="M2_REPO/javassist/javassist/3.11.0.GA/javassist-3.11.0.GA.jar" />  
  13.   <classpathentry kind="var" path="M2_REPO/asm/asm/3.3/asm-3.3.jar"/>  
  14.   <classpathentry kind="var" path="M2_REPO/asm/asm-commons/3.3/asm-commons-3.3.jar"/>  
  15.   <classpathentry kind="var" path="M2_REPO/asm/asm-tree/3.3/asm-tree-3.3.jar"/>  
  16.   <classpathentry kind="var" path="M2_REPO/org/freemarker/freemarker/2.3.19/freemarker-2.3.19.jar" />  
  17.   <classpathentry kind="var" path="M2_REPO/commons-fileupload/commons-fileupload/1.2.2/commons-fileupload-1.2.2.jar" />  
  18.   <classpathentry kind="var" path="M2_REPO/commons-io/commons-io/2.3/commons-io-2.3.jar" />  
  19. </classpath>  
其中,本地仓库目录会使用M2_REPO变量表示,因此IDE环境未配置该变量时,需在IDE中添加这个变量的classpath。


搭建架包
每一个java工程都不免使用第三方的架包,Maven的好处就是可以统一管理这些架包,并使多个java工程共享这些架包。我们所需要做的就是按规则编辑pom.xml文件。Maven已经非常智能,使用maven的eclipse插件的向导,只要输入参数就可以将配置文件生成出来。我们的例子是用jdbc方式访问oracle的数据库。所以需要jdbc和oracle的架包的支持。下面我们就来搭建这两个架包到study工程里来。

有两种方式可以采用:
1、自动向导
第一种是采用向导方式并让向导直接去maven的服务器上下载你需要的架包,这种方式存在一定的风险,一来可能maven的服务器上并没有你需要的东东,二来每次智能的maven总是去寻找那并不存在的东东。抛出一大堆红字提示不说,达不到预期目标才是让人郁闷。不过为了保证文档的完整性,还是给出操作步骤。以junit为例(这个东东倒是没有问题,呵呵)当工程的maven被Enable后,弹出菜单的maven2子菜,选择子菜单的“Add Dependency”菜单项,在Query中输入“junit”,向导会自动列出相关列表供选择。选择你最需要的架包,按“OK” 按钮。
如果你的本地仓库已经存在该架包,则向导只在pom.xml加入依赖项信息,pom.xml文件的内容如下
xml 代码
  1. <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://[url]www.w3.org/2001/XMLSchema-instance[/url]"  xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 [url]http://maven.[/url]"apache.org/maven-v4_0_0.xsd>  
  2. <modelVersion>4.0.0</modelVersion>  
  3. <groupId>com.efn</groupId>  
  4. <artifactId>study</artifactId>  
  5. <packaging>jar</packaging>  
  6. <version>1.0-SNAPSHOT</version>  
  7. <name>Maven Quick Start Archetype</name>  
  8. <url>[url]http://maven.apache.org[/url]</url>  
  9. <dependencies>  
  10. <dependency>  
  11. <groupId>junit</groupId>  
  12. <artifactId>junit</artifactId>  
  13. <version>3.8.1</version>  
  14. </dependency>  
  15. </dependencies>  
  16. </project>  
如果本地仓库没有,则向导会去maven的服务器下载架包,并在控制台输出下载日志如下:
06-8-4 上午09时21分07秒: Local repository folder "" does not exist
06-8-4 上午09时21分11秒: Reading /study/pom.xml
06-8-4 上午09时21分11秒: Local repository folder "" does not exist
06-8-4 上午09时21分18秒: Reading /study/pom.xml
06-8-4 上午09时21分18秒: Local repository folder "" does not exist
06-8-4 上午09时21分19秒: Reading /study/pom.xml
06-8-4 上午09时21分19秒: Local repository folder "" does not exist
06-8-4 上午09时36分33秒: Local repository folder "" does not exist
06-8-4 上午09时37分11秒: Reading / study /pom.xml
06-8-4 上午09时37分11秒: Local repository folder "" does not exist
06-8-4 上午09时37分15秒: Local repository folder "" does not exist
06-8-4 上午09时40分07秒: Local repository folder "" does not exist
06-8-4 上午09时40分08秒: Reading / study /pom.xml
06-8-4 上午09时40分08秒: Local repository folder "" does not exist
06-8-4 上午09时46分24秒: Reading / study /pom.xml
06-8-4 上午09时46分24秒: Local repository folder "" does not exist
06-8-4 上午09时46分28秒: Local repository folder "" does not exist
06-8-4 上午09时46分40秒: Local repository folder "" does not exist
06-8-4 上午09时46分47秒: Local repository folder "" does not exist
06-8-4 上午09时46分47秒: Reading / study /pom.xml
06-8-4 上午09时46分47秒: Local repository folder "" does not exist
06-8-4 上午09 时46 分49 秒: Downloading [central] -> [url]http://repo1.maven.org/maven2/junit/junit/3.8.1/junit-3.8.1.pom[/url]
06-8-4 上午09 时46 分49 秒: Downloaded [central] -> [url]http://repo1.maven.org/maven2/junit/junit/3.8.1/junit-3.8.1.pom[/url]
06-8-4 上午09 时46 分51 秒: Downloading [central] -> [url]http://repo1.maven.org/maven2/junit/junit/3.8.1/junit-3.8.1.jar[/url]
06-8-4 上午09时47分00秒: Downloaded [central] -> [url]http://repo1.maven.org/maven2/junit/junit/3.8.1/junit-3.8.1.jar[/url]
----------------------------------------------------------------
补充修正:如果出现错误提示同时你手头也有架包的话可以采用maven的指令进行本地化安装。比如我在安装hibernate的架包时告诉我jta无法下载。要求本地化安装,给出的提示如下:
1) javax.transaction:jta:jar:1.0.1B
Try downloading the file manually from:[url]http://java.sun.com/products/jta.Then[/url], install it using the command:
mvn install:install-file -DgroupId=javax.transaction -DartifactId=jta \  -Dversion=1.0.1B -Dpackaging=jar -Dfile=/path/to/filePath to dependency:
1) com.efn:mywebapp:war:1.0-SNAPSHOT
2) org.hibernate:hibernate:jar:3.1rc2
3) javax.transaction:jta:jar:1.0.1B
----------
1 required artifact is missing.for artifact: com.efn:mywebapp-1.0-SNAPSHOT.war这个提示是说可以先到sun的网站下载jta架包,然后采用命令行的方式按要求安装,因为我本来就有此架包,于是拷到一个方便的位置,比如c:\,然后在命令行下输入:
mvn install:install-file -DgroupId=javax.transaction -DartifactId=jta -Dversion=1.0.1B -Dpackaging=jar -Dfile=C:/jta.jar
执行完毕后,一切OK!
--------------------------------------------------------------

2、手工配置
        手工配置比起自动化来说是麻烦了些,不过任何东东掌握在自己手里总归是吃饱喝足谁也不服了不是J。而且配置一次就可以受益终身。更重要的是能解决自动化完成不了的任务。比如我现在要配置oracle的jdbc驱动,采用自动化就提示我下载不了让我改变下载地址等等,真累。
        算了还是自己来吧。
        手工配置前还是先介绍一下相关背景知识。首先了解一下jar仓库的概念,maven采用集中化的方式管理架包,凡用maven构建的java工程都可以重用统一管理下的架包,所以必须有一个统一存放jar文件的地方,这就是jar仓库,不论是开发还是部署都会建立一个本地仓库。这个仓库的位置默认是X:\Documents and Settings\Administrator.LIPENG\.m2\repository(X是你操作系统所在盘符)下,你可以修改配置文件改变默认的输出位置。该配置文件在maven目录下的conf子目录下。文件名叫settings.xml。在配置文件中加入如下节点信息即可D:/Repository。不过不建议改变,好像eclipse的maven插件只认默认的输出位置。我就是在这方面出了问题搞了半天才发现是输出路径的问题,也许是我还
没有玩转插件。谁要是解决此问题别忘了跟大家共享。
现在我们分析一下配置文件pom.xml的结构,以junit为例,格式如下:
xml 代码
  1. <dependencies>  
  2. <dependency>  
  3. <groupId>junit</groupId>  
  4. <artifactId>junit</artifactId>  
  5. <version>3.8.1</version>  
  6. </dependency>  
  7. </dependencies>  
在来看看本地仓库目录结构
Repository
`-- junit
|-- junit
| `-- 3.8.1
| `-- junit-3.8.1.jar
现在大家应该明白了吧,多余的话不说啦。照葫芦画瓢就是。不过注意先建目录后写配置文件,否则一旦保存,智能的插件就马上开始下载了…

现在开始手动建立oracle的jdbc目录并配置文件,首先建立目录结构如下:
Repository
`-- ojdbc
|-- ojdbc
| `-- 14
| `-- ojdbc-14.jar
如果你手头的jar文件名叫ojdbc14.jar,则改为ojdbc-14.jar,写配置文件:
xml 代码
  1. <dependency>  
  2. <groupId>ojdbc</groupId>  
  3. <artifactId>ojdbc</artifactId>  
  4. <version>14</version>  
  5. </dependency>  
那么现在一个完整的pom.xml文件如下:
xml 代码
  1. <?xml version="1.0"?>
  2. <project>  
  3. <modelVersion>4.0.0</modelVersion>  
  4. <groupId>com.mycompany.app</groupId>  
  5. <artifactId>myapp</artifactId>  
  6. <name>Maven Quick Start Archetype</name>  
  7. <version>1.0-SNAPSHOT</version>  
  8. <url>[url]http://maven.apache.org[/url]</url>  
  9. <dependencies>  
  10. <dependency>  
  11. <groupId>ojdbc</groupId>  
  12. <artifactId>ojdbc</artifactId>  
  13. <version>14</version>  
  14. </dependency>  
  15. <dependency>  
  16. <groupId>junit</groupId>  
  17. <artifactId>junit</artifactId>  
  18. <version>3.8.1</version>  
  19. </dependency>  
  20. </dependencies>  
  21. </project>  

保存之,则发现工程管理透视图发生了一点变化,依此方法再加上jdbc的架包,现在可以开始写程序了,建一个类并添加main函数,编写程序如下:
java 代码
  1. public static void main( String[] args )   
  2. {   
  3. Connection conn = null;   
  4. PreparedStatement ps = null;   
  5. ResultSet rs = null;   
  6. try {   
  7. Class.forName("oracle.jdbc.driver.OracleDriver");   
  8. conn = DriverManager.getConnection("jdbc:oracle:thin:@(description=(address_list=(address=(protocol=TCP)(port=1521)(host=192.168.0.240)))(connect_data=(SERVER = DEDICATED)(SERVICE_NAME = db.efriendnet.com)))""efnx""efnx");   
  9. ps = conn.prepareStatement("select * From tb_partyinfo");   
  10. rs = ps.executeQuery();   
  11. while(rs.next())   
  12. {   
  13. System.out.println(rs.getString("topic"));   
  14. }   
  15. catch (Exception e) {   
  16. System.out.print(e.getMessage());   
  17. }   
  18. finally  
  19. {   
  20. if (rs != null) {try {rs.close();} catch (SQLException e) {}}   
  21. if (ps != null) {try {ps.close();} catch (SQLException e) {}}   
  22. if (conn != null) {try {conn.close();} catch (SQLException e) {}}   
  23. }   
  24. }  

别忘了import相应的包
0 0