以下面dependency为例

1 <dependency>
2 <groupId>javax.servlet</groupId>
3 <artifactId>javax.servlet-api</artifactId>
4 <version>3.1.0</version>
5 <scope>provided</scope>
6 </dependency>

当子工程中引入某个依赖时,可见其设置<scope>provided</scope>,那么后续依赖该工程的所有项目会可能出现找不到这个依赖,原因是:

1.provided是没有传递性的。即,如果你依赖的某个jar包,它的某个jar的范围是provided,那么该jar不会在你的工程中依靠jar依赖传递加入到你的工程中。

2.provided具有继承性,上面的情况,如果需要统一配置一个组织的通用的provided依赖,可以使用parent,然后在所有工程中继承

比如:我现在有个工程结构图如下:

假设GranParent中的pom.xml是个超级pom.xml文件,

Parent继承GranParent

 <modelVersion>4.0.0</modelVersion>
<groupId>com.alice</groupId>
<artifactId>Parent</artifactId>
<version>1.0.0-SNAPSHOT</version> <parent>
<groupId>com.alice</groupId>
<artifactId>GrandParent</artifactId>
<version>1.0.0</version>
</parent> <modules>
<module>childA</module>
<module>childB</module>
<module>childB</module>
</modules>
<packaging>pom</packaging>

childA的pom.xml

 <parent>
<groupId>com.alice</groupId>
<artifactId>Parent</artifactId>
<version>1.0.0-SNAPSHOT</version>
</parent>
<artifactId>childA</artifactId> <name>childA</name>
<packaging>jar</packaging> <dependencies>
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
<version>3.1.0</version>
<scope>provided</scope>
</dependency>
<dependencies>

childB的pom.xml,其中依赖childA

 <modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.alice</groupId>
<artifactId>Parent</artifactId>
<version>1.0.0-SNAPSHOT</version>
</parent>
<artifactId>childB</artifactId> <name>childB</name>
<packaging>jar</packaging> <dependencies>
<dependency>
<groupId>com.alice</groupId>
<artifactId>childA</artifactId>
<version>1.0.0-SNAPSHOT</version>
</dependency>
</dependencies>

childC的pom.xml,其中依赖childB

 1 <modelVersion>4.0.0</modelVersion>
2 <parent>
3 <groupId>com.alice</groupId>
4 <artifactId>Parent</artifactId>
5 <version>1.0.0-SNAPSHOT</version>
6 </parent>
7 <artifactId>childC</artifactId>
8
9 <name>childC</name>
10 <packaging>jar</packaging>
11
12 <dependencies>
13 <dependency>
14 <groupId>com.alice</groupId>
15 <artifactId>childB</artifactId>
16 <version>1.0.0-SNAPSHOT</version>
17 </dependency>
18 </dependencies>

从上面的pom文件可知,

在childA中,javax.servlet的scope为provided

首先解释下为啥设置为provided:

  因为是tomcat中也有servlet-api包,如果默认为compile,即项目在编译,测试,运行阶段都需要这个artifact对应的jar包在classpath中,那么在使用tomcat运行时就会发生了冲突,由于provided只影响编译和测试阶段,在编译测试阶段,我们需要这个artifact对应的jar包在classpath中,而在运行阶段,假定目标的容器(比如我们这里的tomcat容器)已经提供了这个jar包,所以无需我们这个artifact对应的jar包了,那么在实际发布时会默认使用第三方web服务器中提供的jar包,而不会使用本jar包。

由于childB直接依赖childA,所以childB在测试编译阶段可引入servlet-api包,程序可以正常跑通,

但是childC依赖B,而childC也是需要childA中的servlet-api包,但是由于provided没有传递性,scope在不指明情况下默认为copmpile,所以childC和childA是间接依赖关系,所以childC无法引用servlet-api包,导致运行报错,此时需要单独在childC中加servlet-api依赖包,

 1 <modelVersion>4.0.0</modelVersion>
2 <parent>
3 <groupId>com.alice</groupId>
4 <artifactId>Parent</artifactId>
5 <version>1.0.0-SNAPSHOT</version>
6 </parent>
7 <artifactId>childC</artifactId>
8
9 <name>childC</name>
10 <packaging>jar</packaging>
11
12 <dependencies>
13 <dependency>
14 <groupId>com.alice</groupId>
15 <artifactId>childB</artifactId>
16 <version>1.0.0-SNAPSHOT</version>
17 </dependency>
18 <dependency>
19 <groupId>javax.servlet</groupId>
20 <artifactId>javax.servlet-api</artifactId>
21 <version>3.1.0</version>
22 <scope>test</scope>
23 </dependency>
24 </dependencies>

什么是传递性依赖(https://blog.csdn.net/lewky_liu/article/details/78145211)
有时候我们在pom.xml文件中引入的依赖,其本身就需要依赖于其他的依赖,这时候我们不需要去考虑这些依赖,Maven会解析各个直接依赖的pom,将那些必要的间接依赖,以传递性依赖的形式引入到当前的项目中。

通过传递性依赖,我们可以在pom.xml文件中少写不少的依赖配置

传递性依赖的依赖范围
假如当前项目为A,A依赖于B,B依赖于C。此时称A对于B是第一直接依赖,B对于C是第二直接依赖,而A对于C是传递性依赖。只要知道B在A项目中的scope,就可以知道C在A中的scope。其依赖范围如下:

表格的第一列是B在A中的依赖范围,第一行是C在B中的依赖范围,交叉的格子是C在A中的依赖范围

当C在B中的scope为test时,A不依赖C,C直接被丢弃
当C在B中的scope为provided时,只有当B在A中的scope也是provided时,A才会依赖C,这时候C在A的scope是provided
当C在B中的scope为compile或runtime时,A依赖C,此时C在A中的scope继承自B在A的scope。注意,如果C的scope是runtime,B的scope是compile,此时C在A的scope是runtime,而不是compile

参考https://blog.csdn.net/u013704227/article/details/46460913

https://blog.csdn.net/lewky_liu/article/details/78145211

scope为provided的更多相关文章

  1. Maven的scope的值

    Maven的依赖范围 在pom.xml文件中,有个元素是scope,用来表示依赖的范围.之所以会有依赖范围,是因为Maven在编译.测试和运行项目时会各自使用一套classpath,依赖范围就是用来控 ...

  2. mvn scope (转)

    策略一: 对于容器提供的(如:servlet-api-2.3等)和测试需要时的(如:junit-3.81等),可以直接在pom.xml中去掉. maven的dependency中有一个tag是< ...

  3. Maven pom文件中dependency scope用法

    在Maven中依赖的域有:compile.provided.runtime.system.test.import 一.compile(默认) 当依赖的scope为compile的时候,那么当前这个依赖 ...

  4. Maven中依赖的scope的依赖范围

    在Maven中依赖的域有这几个:import.provided.runtime.compile.system.test 1compile 的范围 当依赖的scope为compile的时候,那么当前这个 ...

  5. spring boot 项目添加maven依赖时provided

    spring boot 项目是自带tomcat 的,但是我们有时候是需要把项目打包成war 然后放到独立的tomcat中运行的,这个时候我们就需要将它自带的tomcat给排除开,这时候我们就可以使用& ...

  6. maven学习(下)利用Profile构建不同环境的部署包

    接上回继续,项目开发好以后,通常要在多个环境部署,象我们公司多达5种环境:本机环境(local).(开发小组内自测的)开发环境(dev).(提供给测试团队的)测试环境(test).预发布环境(pre) ...

  7. Maven安装配置使用

    Maven介绍 Maven是一个项目管理工具,它包含了一个项目对象模型 (Project Object Model),一组标准集合,一个项目生命周期(Project Lifecycle),一个依赖管理 ...

  8. Maven下java.lang.NoClassDefFoundError

    本文转载自:http://blog.csdn.net/qqhjqs/article/details/51491516 使用maven管理web项目中jar包之间的依赖,非常的方便好用,但是有时也会出现 ...

  9. [Maven]Apache Maven 入门篇

    作者:George Ma 上 写这个 maven 的入门篇是因为之前在一个开发者会的动手实验中发现挺多人对于 maven 不是那么了解,所以就有了这个想法.这个入门篇分上下两篇.本文着重动手,用 ma ...

随机推荐

  1. Vue的事件修饰符

    转载于:https://www.cnblogs.com/xuqp/p/9406971.html 事件处理 如果需要在内联语句处理器中访问原生DOM事件.可以使用特殊变量$event,把它传入到meth ...

  2. Yet Another Number Sequence——[矩阵快速幂]

    Description Everyone knows what the Fibonacci sequence is. This sequence can be defined by the recur ...

  3. 1134 最长上升子序列 (序列型 DP)

    思路: 由于一般的动态规划时间复杂度是O(n^2)(哈哈哈哈 第一次用的就是这个!)用在这里由于n最大为50000 所以会超时 到这里我们可以用一个数组来动态维护这个最长上升的子序列,将你要输入的子序 ...

  4. Qt4与Qt3的主要不同

    Qt4与Qt3的主要不同 1)QT4 中提供了大量新控件,虽然它也保持了旧的控件,并命名为Qt3XXX,但是这样的控件没准在今后的哪个QT版本中就不被支持了,所以还是换吧,控件替换的 工作是巨大的,这 ...

  5. JDK、JRE、JVM、Android SDK、Android Studio

    ===================================================== 参考链接: JDK\JRE\JVM:https://www.cnblogs.com/bola ...

  6. JMeter FTP测试计划

    为了演示测试目的,我们将使用公共可用的FTP位置,可以使用它来测试文件的下载. 您可以使用市场上现有的任何可用的演示FTP位置.我们使用URL下的FTP位置: https://dlptest.com/ ...

  7. python类方法、类属性和静态方法

    class Game(object): #类属性 num = 0 #实例方法 def __init__(self): #实例属性 self.name = "laowang" #类方 ...

  8. word HTML文件与Markdwon互相转换的几种方式

    Tip:word文件与Markdwon转换往往是可逆的.无论使用哪种方式,要想完美转换,必须要预先处理掉markdown与word不兼容的格式,如word文件对象,带边框的代码块等等 方法一:借助pa ...

  9. TCP/IP||ICMP

    1.概述 ICMP为IP组成部分之一,传递差错报文并返回用户进程,在IP数据报内部被传输 类型字段可以有15个不同的值,以描述特定类型的ICMP报文,检验和字段覆盖整个ICMP报文. 2.报文类型 在 ...

  10. appium工作流程解析

    为什么选择appium ​ app自带测试框架,为什么要选择appium这个测试框架呢? Ios9.3以前使用的是UIAutomation,Ios9.3以后使用XCUITest.如果只使用Apple的 ...