jar包放置在WEB-INF/lib下和通过Build Path导入的区别是什么?

版权声明:本文为博主原创文章,转载请附上博文链接。感谢合作! https://blog.csdn.net/Angelia620/article/details/86601206
  • jar包直接拷贝到WEB-INF/lib下和以userLibrary(自己新建的存放jar的文件夹)形式引入的区别?
  • jar包放置在WEB-INF/lib下和通过build path导入的区别是什么?

问题:

1、web架包找不到

2、maven项目转变web项目通过 Deployment Assembly把架包添加到WEB-INF/lib引起的架包冲突

Build Path 和 WEB-INF/lib 简介

Build Path:可以看成是引用

WEB-INF/lib:可以看成是固定在一个地方

Eclipse编译项目时,是根据Build Path找jar包,如果不用Eclipse来发布项目的话,就会出现找不到jar包,Tomact运行项目,首先是在它自己的公共lib里找jar包,如果找不到就会去项目的WEB-INF/lib目录找,如果找不到就报错。

复制Java项目,报错

因为Eclipse把Build Path的配置写在了项目的.classpath文件中,add Extenrnal jar将jar包引入到工程,.classpath文件的内容就会被更新,所以就会报错。

有时直接把jar包复制到项目的WEB-INF/lib文件夹中没然后刷新项目,Eclipse会自动把jar包在Build Path中引用。如果jar包不是在Build Path里删除引用,而是自己直接把jar包删除或者移到另外一个位置,刷新项目就会出现错误,要去Build Path里吧引用删除。(导入jar包可以从此导入)

纯Java项目:

通俗的讲和classLoder有关,对于纯Java项目来说,它不存在WEB-INF目录,所以在引入jar包的时候一般都是通过Build Path直接引入。纯Java项目使用的是自己本地的JRE,那么classLoder在加载jar和class的时候时分开的们对于我们自己编写的class,会在APP_HOME/bin下。导入的jar包或者user library的配置信息会出现在APP_HOME/.classpath文件中,ClassLoader会很智能去加载这些classes和jar。

Java Web项目:

虽然Eclipse的workspace中存在.calsspath文件,但是即使你导入了自己的user library,它也不会出现在.classpath中,这个就是问题的关键???

对于Java Web项目来说,它最终不是通过本地是JRE去运行的,而是部署到Web服务器上,如Tomact、Weblogic、WebSphere、Jetty等,这些服务器都实现了自身的类加载器

比如Tomact服务器,它有自己的类加载器,根据J2EE的规范去%web-project%/WEB-INF/lib目录下找相应的lib,这就是我们发布的Web应用要符合那个格式。

以Tomact典型结果为例,它的目录结构分别对应4个不同的类加载器,关系如下:

  • common   ------   CommonClassLoder
  • server       ------   CatalinaClassLoader
  • shared      ------    SharedClassLoder
  • webapps   ------    WebappClassLoder

我们的Web应用都是部署到webapps目录下,而WebappClassLoder类加载器专门负责加载webapps下所有的web项目的WEB-INF下的类库和类文件。而我们通过Build Path引入的jar包自然不会被WebappClassLoder加载器加载,所以才会出现ClassNotFoundException。

Eclipse引用Library是为了编译代码生成WEB-INF/classes里面的class文件使用,使用Eclipse J2EE IDE时,会将WEB-INF/lib中所有的lib自动加入到library中。

Eclipse工程下的library是用来编译src下的java文件,实际发布发到Tomact时,仅仅只复制了WEB-INF/lib里面的jar包,所有出现Eclipse可以正常编辑但Tomact运行时找不到类。

如果你是用的Eclipse J2EE IDE,你去WorkSpace\.metadata\.plugins\**.server.core\wtpwebapps找到运行时发布的工程就可以明白了。说白了就是用Eclipse J2EE IDE开发web的时候,如果是编译java代码用到的jar可以作为library引用,如果是框架非java代码部分用到的jar就必须放在lib下面。


问题一:

maven 转变成web项目时经常会出现架包冲突(servlet -api.jar这个架包会和Tomcat中的冲突)但是把项目打成架包就会不由冲突这是怎么解决的呢?

解决的方法是:

<dependency>
   <groupId>javax.servlet</groupId>
   <artifactId>servlet-api</artifactId>
   <version>2.4</version>
   <scope>provided</scope>
 </dependency>

// 把scope的值填成provided就可以了,意思是在打包时不把这个架包打进去

问题二:

确定是编译环境报错还是程序报错?

因为程序中只认识WEB-INF/lib中jar包,但是编译环境不是。如果编辑环境在配置中说在某个地方有它要的jar包,那么一旦那个地方没有,就会提示警告信息。

如果要在程序中正常运行,那么不管来自哪里,最后jar包都是放在WEB-INF/lib中的。(建议还是先理解下应用程序中包的组成,如果过于依赖于IDE,很多基本的概念会不理解的。)

问题三:

在Eclipse工程的Java Build Path设置中,可以通过加入第三方的jar包,但是,我发现是有好几种方法来完成这个操作的,有“Add jars”,“Add Externel jars”,“Add library”,“Add Classes Loader”等,这几种方式有什么区别吗?

  • add jar:是表示从你的工程里添加JAR,前提是你把jar已经放到自己的工程目录里。
  • add external jar:表示这个jar的位置需要URI来定位,需要给出全路径。
  • add library: 是一些已经定义好的jar的集合,因为它们经常是一起用,所以简化了些操作,比如你做RCP开发的时候就会有个plugin library包含了运行工程所需要的基本插件。
  • Add classes Loader :这个跟添加jar是一个意思,就是告诉ClassLoader去哪找class

问题四:

当出现java.lang.ClassNotFoundException: org.springframework.web.context.ContextLoaderListener类似这种找不到Listener的异常时,要切记spring的jar包一定要放在工程的lib下这样才能避免这个错误的发生?

虽说无论用什么方式导入包在本地运行都是一样的,但实事上我运行时,有的只有Java Build Path才起作用,有的只有导入到lib下才行。用Java Build Path导入包和把包复制到lib下是有区别的,它俩其实不会冲突,也没有什么关系的,Java Build Path是我们编译需要的包,在比如在import *.*.*时如果没用Java Build Path导入包的话类里面就有红叉,说不识别这个类;导入到lib下是程序运行时需要的包,即便用Java Build Path导入过的包,没放到lib下,运行项目时会出现ClassNotFoundException的异常。

猜你喜欢

转载自blog.csdn.net/Angelia620/article/details/86601206