Pergunta

Qual é a diferença entre dependencyManagement e dependencies?Eu vi o docs no Apache Maven site.Parece que uma dependência definidos de acordo com a dependencyManagement pode ser usado em seu filho módulos sem especificar a versão.

Por exemplo:

Um projeto pai (Pro-par), define uma dependência sob a dependencyManagement:

<dependencyManagement>
  <dependencies>
    <dependency>
      <groupId>junit</groupId>
      <artifactId>junit</artifactId>
      <version>3.8</version>
    </dependency>
 </dependencies>
</dependencyManagement>

Em seguida, o filho de Pro-par, eu posso usar o junit:

  <dependencies>
    <dependency>
      <groupId>junit</groupId>
      <artifactId>junit</artifactId>
    </dependency>
 </dependencies>

No entanto, gostaria de saber se é necessário definir junit parent pom?Por que não definir diretamente nos módulos necessários?

Foi útil?

Solução

Gerenciamento De Dependência permite consolidar e centralizar o gerenciamento de dependência versões sem adição de dependências que são herdados por todas as crianças.Isto é especialmente útil quando você tem um conjunto de projetos (i.é.mais do que um) que herda de um pai comum.

Outra extremamente importante caso de uso de dependencyManagement é o controle de versões de artefatos usados nas dependências transitivas.Isto é difícil de explicar sem um exemplo.Felizmente, esta situação é ilustrada na documentação.

Outras dicas

Estou na moda daqui a essa pergunta, mas acho que vale uma resposta mais clara do que a aceita (o que está correto, mas não enfatiza a parte importante, que você precisa deduzir).

No pai POM, a principal diferença entre o <dependencies> e <dependencyManagement> é isto:

Artefatos especificados no <dependencies> A seção sempre será incluída como uma dependência do (s) módulo (s) criança (s).

Artefatos especificados no <dependencyManagement> seção, será incluída apenas no módulo infantil se eles também foram especificados no <dependencies> Seção do próprio módulo infantil. Por que é bom você perguntar? Porque você especifica a versão e/ou escopo no pai e pode deixá -los de fora ao especificar as dependências no Child Pom. Isso pode ajudá -lo a usar versões unificadas para dependências para módulos infantis, sem especificar a versão em cada módulo infantil.

o documentação No site maven é horrível. O que a DependEncyManagement faz é simplesmente mover suas definições de dependência (versão, exclusões, etc.) até o POM dos pais; depois, nas crianças que você só precisa colocar o grupo e o ArtifactID. É isso (exceto para o encadeamento de POM dos pais e similares, mas isso também não é realmente complicado - a dependência do gerenciamento de dependências vence sobre as dependências no nível dos pais - mas se tiver uma pergunta sobre isso ou importações, a documentação do MAVEN é um pouco melhor).

Depois de ler todo o lixo 'A', 'B', 'C' no site Maven e ficar confuso, reescrevi o exemplo deles. Portanto, se você tivesse 2 projetos (proj1 e proj2), que compartilham uma dependência comum (Betashared), poderá mover essa dependência para o pai. Enquanto você estiver nisso, você também pode subir outras dependências (Alpha e Charlie), mas apenas se fizer sentido para o seu projeto. Portanto, para a situação descrita nas frases anteriores, aqui está a solução com o DependencyManagement no pai POM:

<!-- ParentProj pom -->
<project>
  <dependencyManagement>
    <dependencies>
      <dependency> <!-- not much benefit defining alpha here, as we only use in 1 child, so optional -->
        <groupId>alpha</groupId>
        <artifactId>alpha</artifactId>
        <version>1.0</version>
        <exclusions>
          <exclusion>
            <groupId>zebra</groupId>
            <artifactId>zebra</artifactId>
          </exclusion>
        </exclusions>
      </dependency>
      <dependency>
        <groupId>charlie</groupId> <!-- not much benefit defining charlie here, so optional -->
        <artifactId>charlie</artifactId>
        <version>1.0</version>
        <type>war</type>
        <scope>runtime</scope>
      </dependency>
      <dependency> <!-- defining betaShared here makes a lot of sense -->
        <groupId>betaShared</groupId>
        <artifactId>betaShared</artifactId>
        <version>1.0</version>
        <type>bar</type>
        <scope>runtime</scope>
      </dependency>
    </dependencies>
  </dependencyManagement>
</project>

<!-- Child Proj1 pom -->
<project>
  <dependencies>
    <dependency>
      <groupId>alpha</groupId>
      <artifactId>alpha</artifactId>  <!-- jar type IS DEFAULT, so no need to specify in child projects -->
    </dependency>
    <dependency>
      <groupId>betaShared</groupId>
      <artifactId>betaShared</artifactId>
      <type>bar</type> <!-- This is not a jar dependency, so we must specify type. -->
    </dependency>
  </dependencies>
</project>

<!-- Child Proj2 -->
<project>
  <dependencies>
    <dependency>
      <groupId>charlie</groupId>
      <artifactId>charlie</artifactId>
      <type>war</type> <!-- This is not a jar dependency, so we must specify type. -->
    </dependency>
    <dependency>
      <groupId>betaShared</groupId> 
      <artifactId>betaShared</artifactId> 
      <type>bar</type> <!-- This is not a jar dependency, so we must specify type. -->
    </dependency>
  </dependencies>
</project>

É como você disse; dependencyManagementé usado para extrair todas as informações de dependência em um arquivo POM comum, simplificando as referências no arquivo infantil POM.

Torna -se útil quando você tem vários atributos que você não deseja reagir em vários projetos de crianças.

Finalmente, dependencyManagement pode ser usado para definir uma versão padrão de um artefato para usar em vários projetos.

Ainda há uma coisa que não é destacada o suficiente, na minha opinião, e isso é herança indesejada.

Aqui está um exemplo incremental:

Eu declaro no meu parent pom:

<dependencies>
        <dependency>
            <groupId>com.google.guava</groupId>
            <artifactId>guava</artifactId>
            <version>19.0</version>
        </dependency>
</dependencies>

estrondo! Eu tenho isso no meu Child A, Child B e Child C Módulos:

  • Implicilty herdado por POMs infantis
  • Um único lugar para gerenciar
  • Não há necessidade de redeclar nada em poms infantis
  • Eu ainda posso redelcar e substituir para version 18.0 em um Child B se eu quero.

Mas e se eu acabar não precisando de goiaba em Child C, e nem no futuro Child D e Child E módulos?

Eles ainda o herdarão e isso é indesejado!É como o cheiro do código de objeto Java God, onde você herda alguns pedaços úteis de uma classe e uma tonelada de coisas indesejadas também.

É aqui que <dependencyManagement> entra em jogo. Quando você adiciona isso aos seus pais, todos os módulos de seu filho Pare de ver. E assim você é forçado entrar em cada módulo individual que precisa e declará -lo novamente (Child A e Child B, sem a versão).

E, obviamente, você não faz isso por Child C, e, portanto, seu módulo permanece magro.

Existem algumas respostas descrevendo as diferenças entre <depedencies> e <dependencyManagement> Tags com maven.

No entanto, poucos pontos elaborados abaixo de uma maneira concisa:

  1. <dependencyManagement> Permite consolidar todas as dependências (usadas no nível da criança filho) usadas em diferentes módulos - clareza, Gerenciamento de versão de dependência central
  2. <dependencyManagement> Permite atualizar/downgrade facilmente dependências com base na necessidade, em outro cenário, isso precisa ser exercido em todos os níveis de pom infantil - consistência
  3. dependências fornecidas em <dependencies> A tag é sempre importada, enquanto as dependências fornecidas em <dependencyManagement> no pai POM será importado apenas se a criança pom tiver respectiva entrada em seu <dependencies> marcação.

Se a dependência foi definida no elemento de gerenciamento de dependência do POM de nível superior, o projeto filho não precisou listar explicitamente a versão da dependência. Se o projeto infantil definisse uma versão, ele substituiria a versão listada na seção de gerenciamento de dependência do POM de nível superior. Isto é, a versão dependência do DepeningManagement é usada apenas quando a criança não declara uma versão diretamente.

Desculpe, estou muito atrasado para a festa.

Deixe -me tentar explicar a diferença usando mvn dependency:tree comando

Considere o exemplo abaixo

Pai pom - meu projeto

<modules>
    <module>app</module>
    <module>data</module>
</modules>

<dependencies>
    <dependency>
        <groupId>com.google.guava</groupId>
        <artifactId>guava</artifactId>
        <version>19.0</version>
    </dependency>
</dependencies>

<dependencyManagement>
    <dependencies>
        <dependency>
            <groupId>org.apache.commons</groupId>
            <artifactId>commons-lang3</artifactId>
            <version>3.9</version>
        </dependency>
    </dependencies>
</dependencyManagement>

Child Pom - Módulo de dados

<dependencies>
    <dependency>
        <groupId>org.apache.commons</groupId>
        <artifactId>commons-lang3</artifactId>
    </dependency>
</dependencies>

Child Pom - Módulo de App (não tem dependência extra, portanto, deixando as dependências vazias)

 <dependencies>
</dependencies>

Na corrida mvn dependency:tree comando, obtemos o seguinte resultado

Scanning for projects...
------------------------------------------------------------------------
Reactor Build Order:

MyProject
app
data

------------------------------------------------------------------------
Building MyProject 1.0-SNAPSHOT
------------------------------------------------------------------------

--- maven-dependency-plugin:2.8:tree (default-cli) @ MyProject ---
com.iamvickyav:MyProject:pom:1.0-SNAPSHOT
\- com.google.guava:guava:jar:19.0:compile

------------------------------------------------------------------------
Building app 1.0-SNAPSHOT
------------------------------------------------------------------------

--- maven-dependency-plugin:2.8:tree (default-cli) @ app ---
com.iamvickyav:app:jar:1.0-SNAPSHOT
\- com.google.guava:guava:jar:19.0:compile

------------------------------------------------------------------------
Building data 1.0-SNAPSHOT
------------------------------------------------------------------------

--- maven-dependency-plugin:2.8:tree (default-cli) @ data ---
com.iamvickyav:data:jar:1.0-SNAPSHOT
+- org.apache.commons:commons-lang3:jar:3.9:compile
\- com.google.guava:guava:jar:19.0:compile

Google goiaba está listado como dependência em todos os módulos (incluindo pai), enquanto o Apache Commons está listado como dependência apenas no módulo de dados (nem mesmo no módulo pai)

No pai POM, a principal diferença entre o <dependencies> e <dependencyManagement> é isto:

Artefatos especificados no <dependencies> A seção sempre será incluída como uma dependência do (s) módulo (s) criança (s).

Os artefatos especificados na seção serão incluídos apenas no módulo infantil se também forem especificados na seção do próprio módulo infantil. Por que é bom você perguntar? Porque você especifica a versão e/ou escopo no pai e pode deixá -los de fora ao especificar as dependências no Child Pom. Isso pode ajudá -lo a usar versões unificadas para dependências para módulos infantis, sem especificar a versão em cada módulo infantil.

No eclipse, há mais um recurso no dependencyManagement. Quando dependencies é usado sem ele, as dependências inflexíveis são notadas no arquivo POM. Se dependencyManagement é usado, as dependências não resolvidas permanecem despercebidas no arquivo POM e os erros aparecem apenas nos arquivos Java. (importações e tal ...)

A diferença entre os dois é melhor trouxe o que parece ser necessária e suficiente a definição do dependencyManagement elemento disponível no Maven site do google docs:

dependencyManagement

"Padrão de dependência de informações para projetos que herdam a partir deste.As dependências desta seção não são resolvidos imediatamente.Em vez disso, quando um POM derivadas de declara uma dependência descrita por uma correspondência groupId e artifactld, a versão e outros valores a partir desta seção são usados para que a dependência se eles já não estivessem especificado." [ https://maven.apache.org/ref/3.6.1/maven-model/maven.html ]

Ele deve ser lido juntamente com mais algumas informações disponíveis em uma página diferente:

"..o conjunto mínimo de informações para a correspondência de uma dependência de referência contra um dependencyManagement seção é, na verdade {groupId, artifactld, tipo classificador}.Em muitos casos, essas dependências irá referir-se a jarra de artefatos com nenhum classificador.Isto permite-nos de forma abreviada a identidade do conjunto a {groupId, artifactld}, uma vez que o padrão para o tipo de campo é o frasco, e o padrão de classificação é nulo." [https://maven.apache.org/guides/introduction/introduction-to-dependency-mechanism.html ]

Assim, todos os sub-elementos (escopo, exclusões, etc.) de uma dependência elemento--outros de groupId, artifactld, tipo classificador, não apenas versão, estão disponíveis para bloqueio/padrão no ponto (e, portanto, herdada de lá em diante) especificar a dependência dentro de um dependencyElement.Se você especificou uma dependência com o tipo e o classificador de sub-elementos (ver o primeiro citado página para verificar se todos os sub-elementos) como não frasco e não nulo, respectivamente, você precisaria de {groupId, artifactld, classificador, digite} para referência (resolver) que a dependência, em qualquer ponto em uma herança originários da dependencyManagement elemento.Outra coisa, {groupId, artifactld} seria suficiente, se você não pretende substituir os padrões para classificação e tipo (jar e nulo, respectivamente).Assim, o padrão é uma boa palavra-chave nessa definição;qualquer sub-elemento(s) (que groupId, artifactld, classificação e tipo, é claro) explicitamente o valor atribuído(s) no ponto de referência de uma dependência substituir as predefinições no dependencyManagement elemento.

Assim, qualquer elemento de dependência fora do dependencyManagement, seja como uma referência para alguns dependencyManagement elemento ou como um autônomo é imediatamente resolvido (i.e.instalado o repositório local e disponível para classpaths).

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top