Loading [MathJax]/jax/output/CommonHTML/config.js
前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >[1117]maven依赖中scope=compile和provided区别

[1117]maven依赖中scope=compile和provided区别

作者头像
周小董
发布于 2022-04-13 07:12:43
发布于 2022-04-13 07:12:43
2.8K00
代码可运行
举报
文章被收录于专栏:python前行者python前行者
运行总次数:0
代码可运行

scope的其他参数如下

  • compile

默认的scope,表示dependency(依赖)都可以在生命周期中使用。而且,这些dependencies 会传递到依赖的项目中。适用于所有阶段,会随着项目一起发布

  • provided

跟compile相似,但是表明了dependency 由JDK或者容器提供,例如Servlet AP和一些Java EE APIs。这个scope 只能作用在编译和测试时,同时没有传递性。

  • runtime

表示dependency不作用在编译时,但会作用在运行和测试时,如JDBC驱动,适用运行和测试阶段。 test表示dependency作用在测试时,不作用在运行时。 只在测试时使用,用于编译和运行测试代码。不会随项目发布。 system跟provided 相似,但是在系统中要以外部JAR包的形式提供,maven不会在repository查找它

解释:

对于scope=compile的情况(默认scope),也就是说这个项目在编译,测试,运行阶段都需要这个artifact对应的jar包在classpath中。

而对于scope=provided的情况,则可以认为这个provided是目标容器已经provide这个artifact。换句话说,它只影响到编译,测试阶段。在编译测试阶段,我们需要这个artifact对应的jar包在classpath中,而在运行阶段,假定目标的容器(比如我们这里的liferay容器)已经提供了这个jar包,所以无需我们这个artifact对应的jar包了。

听起来很玄乎,对吧,其实一点也不难理解。举个scope=provided的例子。

比如说,假定我们自己的项目ProjectABC 中有一个类叫C1,而这个C1中会import这个portal-impl的artifact中的类B1,那么在编译阶段,我们肯定需要这个B1,否则C1通不过编译,因为我们的scope设置为provided了,所以编译阶段起作用,所以C1正确的通过了编译。测试阶段类似,故忽略。

那么最后我们要吧ProjectABC部署到Liferay服务器上了,这时候,我们到$liferay-tomcat-home\webapps\ROOT\WEB-INF\lib下发现,里面已经有了一个portal-impl.jar了,换句话说,容器已经提供了这个artifact对应的jar,所以,我们在运行阶段,这个C1类直接可以用容器提供的portal-impl.jar中的B1类,而不会出任何问题。

实际插件的行为:

刚才我们讲述的是理论部分,现在我们看下,实际插件在运行时候,是如何来区别对待scope=compile和scope=provided的情况的。

做一个实验就可以很容易发现,当我们用maven install生成最终的构件包ProjectABC.war后,在其下的WEB-INF/lib中,会包含我们被标注为scope=compile的构件的jar包,而不会包含我们被标注为scope=provided的构件的jar包。这也避免了此类构件当部署到目标容器后产生包依赖冲突。

今天开发web的时候,需要用到servlet-api,于是在pom.xml中添加依赖

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
<dependency>
  <groupId>javax.servlet</groupId>
  <artifactId>servlet-api</artifactId>
  <version>3.0-alpha-1</version>
 </dependency>

通过插件启动tomcat的时候,报错,里面有一段是这样的:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
Caused by: java.lang.LinkageError: loader constraint violation: loader (instance of org/apache/catalina/loader/WebappClassLoader) previously initiated loading for a different type with name "javax/servlet/ServletContext"
 at java.lang.ClassLoader.defineClass1(Native Method)
 at java.lang.ClassLoader.defineClass(ClassLoader.java:800)
 at java.security.SecureClassLoader.defineClass(SecureClassLoader.java:142)
 at java.net.URLClassLoader.defineClass(URLClassLoader.java:449)
 at java.net.URLClassLoader.access$100(URLClassLoader.java:71)
 at java.net.URLClassLoader$1.run(URLClassLoader.java:361)
 at java.net.URLClassLoader$1.run(URLClassLoader.java:355)

产生的原因是:tomcat中也有servlet-api包,这样,发生了冲突

解决方法:添加provided,因为provided表明该包只在编译和测试的时候用,所以,当启动tomcat的时候,就不会冲突了,完整依赖如下:

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
<dependency>
  <groupId>javax.servlet</groupId>
  <artifactId>servlet-api</artifactId>
  <version>3.0-alpha-1</version>
  <scope>provided</scope>
 </dependency>
本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2022/03/25 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
暂无评论
推荐阅读
编辑精选文章
换一批
Maven的依赖管理 - 引入依赖
导入依赖坐标,无需手动导入jar包就可以引入jar。在pom.xml中使用<dependency>标签引入依赖。
Devops海洋的渔夫
2022/01/17
1.9K0
Maven的依赖管理 - 引入依赖
Maven依赖Scope选项详解
在一个maven项目中,如果存在编译需要而发布不需要的jar包,可以用scope标签,值设为provided。 如下: <dependency> <groupId>javax.servlet.jsp</groupId> <artifactId>jsp-api</artifactId> <version>2.3</version> <scope>provided</scope> </dependency> Scope的其他参数如下: compile:默认的scope,表示
飞奔去旅行
2019/06/13
1.5K0
Maven的依赖管理的体系设计
在Maven的生命周期中,存在编译、测试、运行等过程,那么有些依赖只用于测试,比如junit;有些依赖编译用不到,只有运行的时候才能用到,比如mysql的驱动包在编译期就用不到(编译期用的是JDBC接口),而是在运行时用到的;还有些依赖,编译期要用到,而运行期不需要提供,因为有些容器已经提供了,比如servlet-api在tomcat中已经提供了,我们只需要的是编译期提供而已。
用户7737280
2021/11/10
5130
Maven中optional和scope元素的使用,你弄明白了?
在梳理项目的过程中发现很多开发同学对Maven依赖文件的配置并不了解,特别是对Maven的optional元素和scope元素的使用也非常随意。这就会导致发布的jar包或war包非常“胖”、编译速度慢,而且还很容易生产jar冲突等问题。本篇文章从optional和scope的使用场景入手,让项目实现一波瘦身。
程序新视界
2020/12/03
7.7K0
Maven中optional和scope元素的使用,你弄明白了?
Maven的基本使用
Maven就是Apache下的一个开源项目。它是用纯java开发的。是一个项目管理工具。使用Maven对java项目进行构建、依赖管理。
不愿意做鱼的小鲸鱼
2022/09/24
6730
Maven的基本使用
Maven精选系列--依赖范围、传递、排除
今天讲讲如何管理依赖,及依赖的范围、传递性等特征。 添加依赖 下面我添加了一个spring-web的依赖,maven就会去下载spring-web的jar包及它依赖的一些jar包。 <dependencies> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-web</artifactId> <version>4.2.5.RELEASE</version> <scope>compile</scope
Java技术栈
2018/03/30
1.2K0
站住,Maven依赖的scope作用域,还记得几个?
在POM中,<dependency>引入了<scope>,它主要管理依赖的部署。目前<scope>可以使用5个值:
程序员小明
2019/05/31
7500
Maven系列第3篇:详解maven解决依赖问题
maven是apache软件基金会组织维护的一款自动化构件工具,专注服务于java平台的项目构件和依赖管理。
路人甲Java
2019/11/14
2K0
Maven系列第3篇:详解maven解决依赖问题
SpringBoot依赖scope为provided时,IDEA运行报错
所有scope为 provided 的依赖都是不会被加入到 classpath 中的,目前该bug尚未被修复(bug report)。如果你的web应用是部署到容器中的,那么这个bug不会影响使用,因为web应用中provided的依赖在容器运行时会被提供。如果你做Spring Boot开发,有带provided的依赖时,直接在IDE中运行项目会导致ClassNotFound异常
試毅-思伟
2020/04/09
1.4K0
maven项目 porm.xml中Dependency Scope属性「建议收藏」
依赖范围控制哪些依赖在哪些classpath 中可用,哪些依赖包含在一个应用中。让我们详细看一下每一种范围:
全栈程序员站长
2022/09/07
5010
Maven(六)之依赖管理
前面讲了maven一些关于Maven的简单知识,今天我给大家分享一些Maven的依赖管理。我相信用过maven的人都知道,它很重要的功能就是通过依赖来添加jar包。 让我们领略一下Maven是怎么管理我们的jar包的。 一、Maven坐标 1.1、数学中的坐标   在平面上,使用 X 、Y 两个向量可以唯一的定位平面中的任何一个点   在空间中,使用 X、Y、Z 三个向量可以唯一的定位空间中的任意一个点 1.2、Maven 中的坐标   俗称 gav:使用下面三个向量子仓库中唯一定位一个 Maven 工程
用户1195962
2018/01/18
8880
Maven(六)之依赖管理
Maven工程开发
groupId一般定义项目组名,命名规则使用反向域名。例如com.itbaizhan
会洗碗的CV工程师
2022/11/29
5920
Maven工程开发
Maven教程3(依赖管理)
  Maven项目,依赖,构建配置,以及构件:所有这些都是要建模和表述的对象。这些对象通过一个名为项目对象模型(Project Object Model, POM)的XML文件描述。这个POM告诉Maven它正处理什么类型的项目,如何修改默认的行为来从源码生成输出。同样的方式,一个Java Web应用有一个web.xml文件来描述,配置,及自定义该应用,一个Maven项目则通过一个 pom.xml文件定义。该文件是Maven中一个项目的描述性陈述;也是当Maven构建项目的时候需要理解的一份“地图”。
用户4919348
2019/04/02
7260
Maven教程3(依赖管理)
Maven 的 Scope 区别,你知道吗?
默认scope为compile,表示为当前依赖参与项目的编译、测试和运行阶段,属于强依赖。打包之时,会达到包里去
好好学java
2020/03/20
2.5K0
Maven中常用命令以及idea中使用maven指南
compile 是maven 工程的编译命令,作用是将src/main/java 下的文件编译为class 文件输出到target 目录下。
共饮一杯无
2022/11/24
1.3K0
Maven中常用命令以及idea中使用maven指南
更快 Maven 来袭,性能大幅提升!
相信作为Java开发者的你早已经受够了maven的编译缓慢,但是又由于历史包袱、使用习惯等问题暂时切换不了其他更快的构建工具,这里笔者将给你介绍一款更快的maven——maven-mvnd。
路人甲Java
2022/02/24
7160
更快 Maven 来袭,性能大幅提升!
java对象转map_java中实现map与对象相互转换的几种实现
public static Object mapToObject(Map map, Class> beanClass)
全栈程序员站长
2022/08/18
2.1K0
Maven中pom.xml中的scope讲解
一、compile:编译范围 compile是默认的范围;如果没有提供一个范围,编译范围依赖在所有的classpath 中可用,同时它们也会被打包。而且这些dependency会传递到依赖的项目中。
全栈程序员站长
2022/07/01
7070
IDEA中scope 为 provided的问题
下面是启动异常: java.lang.IllegalStateException: ApplicationEventMulticaster not initialized - call 'refresh' before multicasting events via the context: org.springframework.context.annotation.AnnotationConfigApplicationContext@30e868be: startup date [Thu Jan 18
小小明童鞋
2018/06/13
2.2K0
【maven】什么是坐标(依赖)继承与模块、web项目启动&访问
   <dependencies>        <dependency>            <groupId>com.czxy</groupId>            <artifactId>itcast-tools</artifactId>            <version>1.5.7</version>        </dependency>    </dependencies>
陶然同学
2023/02/24
1.1K0
【maven】什么是坐标(依赖)继承与模块、web项目启动&访问
相关推荐
Maven的依赖管理 - 引入依赖
更多 >
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
本文部分代码块支持一键运行,欢迎体验
本文部分代码块支持一键运行,欢迎体验