Como você lida com instantâneos do MAVEN-3 com eficiência com o Timestamped?

StackOverflow https://stackoverflow.com/questions/4275466

  •  28-09-2019
  •  | 
  •  

Pergunta

Agora que o maven-3 fez soltar suporte para ou003CuniqueVersion> falsou003C/uniqueVersion> Para artefatos instantâneos, parece que você realmente precisa usar instantâneos de registro de data e hora. Especialmente m2eclipse, que usa o Maven 3, internamente, parece ser afetado por ele, o Update-Snapshots não funciona quando os instantâneos não são únicos.

Parecia melhor Pratique antes Para definir todos os instantâneos como Uniqueversion = false

Agora, parece que não é um grande problema mudar para a versão com registro de data e hora, afinal, eles são gerenciados por um repositório central do Nexus, que é capaz de excluir instantâneos antigos em intervalos regulares.

O problema são as estações de trabalho do desenvolvedor local. Seu repositório local rapidamente cresce muito grande com instantâneos exclusivos.

Como lidar com esse problema?

No momento, vejo as possíveis soluções possíveis:

  • Peça aos desenvolvedores que limpem o repositório em intervalos regulares (o que leva a muita fustração, pois leva muito tempo para excluir e ainda mais para baixar tudo o que é necessário)
  • Configure um script que exclua tudo INSTANTÂNEO Diretórios do repositório local e pedem aos desenvolvedores que executem esse script de tempos em tempos (melhor que o primeiro, mas ainda demoram algum tempo para executar e baixar instantâneos atuais)
  • Use a dependência: o plug-in de repositório-local-local (tem problemas quando executado do eclipse, devido a arquivos abertos, precisa ser executado de cada projeto)
  • Configure o Nexus em todas as estações de trabalho e configure um trabalho para limpar os instantâneos antigos (melhor resultado, mas não quero manter mais de 50 servidores Nexus, além de a memória sempre é apertada nas estações de trabalho do desenvolvedor)
  • pare de usar instantâneos

Qual é a melhor maneira de impedir que seu repositório local preencha seu espaço no disco rígido?

Atualizar:

Para verificar o beaviour e fornecer mais informações, configurei um pequeno servidor Nexus, construo dois projetos (A e B) e tente::

uma:

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
  <modelVersion>4.0.0</modelVersion>
  <groupId>de.glauche</groupId>
  <artifactId>a</artifactId>
  <version>0.0.1-SNAPSHOT</version>
  <distributionManagement>
    <snapshotRepository>
        <id>nexus</id>
        <name>nexus</name>
        <url>http://server:8081/nexus/content/repositories/snapshots</url>
    </snapshotRepository>
  </distributionManagement>

</project>

B:

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
  <modelVersion>4.0.0</modelVersion>
  <groupId>de.glauche</groupId>
  <artifactId>b</artifactId>
  <version>0.0.1-SNAPSHOT</version>
    <distributionManagement>
    <snapshotRepository>
        <id>nexus</id>
        <name>nexus</name>
        <url>http://server:8081/nexus/content/repositories/snapshots/</url>
    </snapshotRepository>
  </distributionManagement>
 <repositories>
    <repository>
        <id>nexus</id>
        <name>nexus</name>
        <snapshots>
            <enabled>true</enabled>
        </snapshots>
        <url>http://server:8081/nexus/content/repositories/snapshots/</url>
    </repository>
 </repositories>
  <dependencies>
    <dependency>
        <groupId>de.glauche</groupId>
        <artifactId>a</artifactId>
        <version>0.0.1-SNAPSHOT</version>
    </dependency>
  </dependencies>
</project>

Agora, quando eu uso o maven e o "implantar" em "a", eu terei

a-0.0.1-SNAPSHOT.jar
a-0.0.1-20101204.150527-6.jar
a-0.0.1-SNAPSHOT.pom
a-0.0.1-20101204.150527-6.pom

no repositório local. Com uma nova versão de registro de data e hora toda vez que executo o destino de implantação. O mesmo acontece quando tento atualizar instantâneos do servidor Nexus (fechar o projeto "A", excluí -lo do repositório local, construir "B")

Em um ambiente em que muitos instantâneos são construídos (pense no servidor Hudson ...), a reposióia local se enche com versões antigas velozes

Atualização 2:

Para testar como e por que isso está falhando, fiz mais alguns testes. Cada teste é executado contra tudo limpo (de/glauche é excluído de máquinas e Nexus)

  • MVN Implante com o Maven 2.2.1:

repositório local na máquina A contém instantâneos.jar + instantânea-timestamp.jar

Mas: apenas um frasco de registro de data e hora no Nexus, os metadados dizem:

<?xml version="1.0" encoding="UTF-8"?>
<metadata>
  <groupId>de.glauche</groupId>
  <artifactId>a</artifactId>
  <version>0.0.1-SNAPSHOT</version>
  <versioning>
    <snapshot>
      <timestamp>20101206.200039</timestamp>

      <buildNumber>1</buildNumber>
    </snapshot>
    <lastUpdated>20101206200039</lastUpdated>
  </versioning>
</metadata>
  • Execute as dependências de atualização (na máquina B) no M2eclipse (Final M3 incorporado) -> O repositório local possui instantâneo.jar + instantâneo -timestamp.jar :(
  • Execute a meta do pacote com o Maven externo 2.2.1 -> O repositório local possui instantâneo.jar + snapshot -timestamp.jar :(

Ok, em seguida, tente com o MAVEN 3.0.1 (depois de remover todos os vestígios do projeto A)

  • Repositório local na máquina A parece melhor, apenas um frasco sem timestal

  • Apenas um frasco de registro de data e hora em Nexus, os metadados dizem:

    De.Glauche a 0.0.1-Snapshot

    <snapshot>
      <timestamp>20101206.201808</timestamp>
      <buildNumber>3</buildNumber>
    </snapshot>
    <lastUpdated>20101206201808</lastUpdated>
    <snapshotVersions>
      <snapshotVersion>
        <extension>jar</extension>
        <value>0.0.1-20101206.201808-3</value>
        <updated>20101206201808</updated>
      </snapshotVersion>
      <snapshotVersion>
        <extension>pom</extension>
        <value>0.0.1-20101206.201808-3</value>
        <updated>20101206201808</updated>
      </snapshotVersion>
    </snapshotVersions>
    

  • Execute as dependências de atualização (na máquina B) no M2eclipse (Final M3 incorporado) -> O repositório local possui instantâneo.jar + instantâneo -timestamp.jar :(

  • Execute a meta do pacote com o Maven externo 2.2.1 -> O repositório local possui instantâneo.jar + snapshot -timestamp.jar :(

Portanto, para recapitular: a meta "implantar" no MAVEN3 funciona melhor do que em 2.2.1, o repositório local na máquina de criação parece bem. Mas, o receptor sempre acaba com muitas versões de time -timested ...

O que estou fazendo errado ?

Atualização 3

Também testei várias outras configurações, primeiro substituo o Nexus por Artifactory -> Mesmo comportamento. Em seguida, use clientes Linux Maven 3 para baixar os instantâneos do Repository Manager -> Repositório local ainda possui instantâneos de registro de data e hora :(

Foi útil?

Solução

o <uniqueVersion> Configuração aplicada a artefatos que foram implantados (via MVN implantar) em um repositório maven, como o Nexus.

Para removê -los do Nexus, você pode criar facilmente um trabalho automatizado para limpar o repositório de instantâneos todos os dias. Ele pode ser configurado para manter um certo número de shapes ou mantê -los por um certo período de tempo. É super fácil e funciona muito bem.

Os artefatos no repositório local em uma máquina de desenvolvedor chegam lá da meta "Instalação" e não usam esses registros de data e hora ... eles continuam substituindo a única versão do Snapshot, a menos que você também esteja aumentando o número da revisão (por exemplo, 1.0.0- Instantâneo para 1.0.1-Snapshot).

Outras dicas

Este plug -in remove os artefatos do projeto do repositório local. Útil para manter apenas uma cópia do grande instantâneo local.

<plugin>         
    <groupId>org.codehaus.mojo</groupId>         
    <artifactId>build-helper-maven-plugin</artifactId>         
    <version>1.7</version>         
    <executions>           
        <execution>             
            <id>remove-old-artifacts</id>             
            <phase>package</phase>             
            <goals>               
                <goal>remove-project-artifact</goal>             
            </goals>            
            <configuration>  
                <removeAll>true</removeAll><!-- When true, remove all built artifacts including all versions. When false, remove all built artifacts of this project version -->             
            </configuration>          
        </execution>         
    </executions>       
</plugin>

Bem, eu não gostei de nenhuma das soluções propostas. A exclusão do cache do Maven geralmente aumenta significativamente o tráfego da rede e diminui o processo de construção. O Build-Helper-Maven-Plugin ajuda apenas com um artefato, eu queria uma solução que possa purgar todos os artefatos de instantâneos com registro de registro no registro de registro de registro de registro do cache local em um comando simples. Após alguns dias de pesquisa, desisti e decidi escrever um pequeno programa. O programa final parece estar funcionando muito bem em nosso ambiente. Por isso, decidi compartilhá -lo com outras pessoas que podem precisar dessa ferramenta. Fontes podem ser retiradas do Github: https://github.com/nadestin/tools/tree/master/mavencachecleanup

Quanto à parte do repositório remoto disso, acho que as respostas anteriores que discutem uma purga de instantâneos em um intervalo regular funcionarão. Mas ninguém abordou a parte de sincronização da estação de trabalho de desenvolvedor local da sua pergunta.

Ainda não começamos a usar o MAVEN3, então ainda não vemos instantâneos começando a acumular máquinas locais.

Mas tivemos problemas diferentes com o M2eclipse. Quando temos a "resolução do espaço de trabalho" ativada e o projeto existe em nosso espaço de trabalho, as atualizações de origem geralmente nos mantêm na borda do sangramento. Mas achamos que é muito difícil fazer com que o M2eclipse se atualize com artefatos publicados recentemente no Nexus. Estamos enfrentando problemas semelhantes em nossa equipe e é particularmente problemático porque temos um gráfico de projeto muito grande ... Existem muitas dependências que não estarão no seu espaço de trabalho, mas estarão publicando instantâneos com frequência.

Tenho certeza de que isso volta a um problema no M2eclipse, onde não lida com os instantâneos exatamente como deveria. Você pode ver no console Maven no Eclipse, onde o M2eclipse diz que está pulando a atualização de um instantâneo publicado recentemente porque tem uma versão em cache. Se você fizer um -u a partir de uma configuração de execução ou da linha de comando, Maven Aceitará a mudança de metadados. Mas uma seleção de "instantâneos de atualização ..." deve dizer ao M2eclipse para que o MAVEN expire este cache. Não parece estar sendo repassado. Parece haver um bug por aí que é arquivado para isso se você estiver interessado em votar nele:https://issues.sonatype.org/browse/mngeclipse-2608

Você mencionou isso em um comentário em algum lugar.

A melhor solução alternativa para esse problema parece estar fazendo com que desenvolvedores limpem suas estações de trabalho locais quando as coisas começam a quebrar de dentro do M2eclipse. Solução semelhante a um problema diferente ... Outros relataram problemas com o MAVEN 2.2.1 e 3 backing m2eclipse, e eu já vi o mesmo.

Espero que, se você estiver usando o MAVEN3, pode configurá -lo apenas para puxar o instantâneo mais recente e cache isso pela quantidade de tempo que o repositório diz (ou até que você o expire manualmente). Espero que você não precise ter um monte de instantâneos sentados no seu repositório local.

Isto é, a menos que você esteja falando de um servidor de construção que está fazendo manualmente um mvn install neles. Quanto a como impedir que os instantâneos se acumulem em um ambiente como um servidor de construção, nós meio que evitamos essa bala ao fazer com que cada construção use seu próprio espaço de trabalho e repositório local (embora, no MAVEN 2.2.1, certas coisas como como Os POMs parecem sempre sair do ~/.m2/repositório), os instantâneos extras realmente permanecem apenas para uma única construção e depois são descartados (e baixados novamente do zero). Então, vimos essa abordagem acabar consumindo mais espaço para começar, mas tende a permanecer mais estável do que ter tudo resolvido em um único repositório. Esta opção (no Hudson) é chamada de "Use o repositório de Maven Private" e está sob o botão avançado da seção Build nas configurações do projeto quando você selecionou para construir com o MAVEN. Aqui está a descrição de ajuda para essa opção:

Normalmente, Hudson usa o repositório local do Maven, conforme determinado pelo MAVEN - o processo exato parece não documentado, mas é ~/.m2/repositório e pode ser substituído por ~/.m2/Settings.xml (consulte a referência para obter mais detalhes .) Isso normalmente significa que todos os trabalhos executados no mesmo nó compartilham um único repositório Maven. A vantagem disso é que você pode salvar o espaço do disco, mas a desvantagem disso é que, às vezes, essas compilações podem interferir entre si. Por exemplo, você pode acabar tendo construções incorretamente, apenas porque você tem todas as dependências no seu repositório local, apesar do fato de que nenhum dos repositórios no POM pode tê -los.

Existem também alguns problemas relatados em relação a ter processos Maven simultâneos tentando usar o mesmo repositório local.

Quando essa opção for verificada, o Hudson dirá ao Maven para usar $ workspace/.repository como o repositório Maven local. Isso significa que cada trabalho receberá seu próprio repositório de maven isolado apenas por si. Ele corrige os problemas acima, às custas do consumo adicional de espaço em disco.

Ao usar esta opção, considere a configuração de um gerente de artefato Maven para que você não precise atingir repositórios remotos do Maven com muita frequência.

Se você preferir ativar esse modo em todos os trabalhos do Maven executados no Hudson, consulte a técnica descrita aqui.

Espero que isso ajude - se não resolver seu problema, deixe -me saber onde eu perdi.

Em groovy, excluindo arquivos de registro de data e hora como artifact-0.0.1-20101204.150527-6.jar pode ser muito simples:

root = 'path to your repository'

new File(root).eachFileRecurse {
  if (it.name.matches(/.*\-\d{8}\.\d{6}\-\d+\.[\w\.]+$/)) {
    println 'Deleting ' + it.name
    it.delete()
  }
}

Instalar Groovy, salve o script em um arquivo e agende a execução a cada semana, inicie, logon, o que for adequado a você.

Ou, você pode até conectar a execução na construção do Maven, usando GMAVENPLUS-PLUGIN. Observe, como é o local do repositório definido por Maven na propriedade settings.localRepository e depois bateu através da configuração em variável repository:

  <plugin>
    <groupId>org.codehaus.gmavenplus</groupId>
    <artifactId>gmavenplus-plugin</artifactId>
    <version>1.3</version>
    <executions>
      <execution>
        <phase>install</phase>
        <goals>
          <goal>execute</goal>
        </goals>
      </execution>
    </executions>
    <configuration>
      <properties>
        <property>
          <name>repository</name>
          <value>${settings.localRepository}</value>
        </property>
      </properties>
      <scripts>
        <script><![CDATA[
          new File(repository).eachFileRecurse {
            if (it.name.matches(/.*\-\d{8}\.\d{6}\-\d+\.[\w\.]+$/)) {
              println 'Deleting snapshot ' + it.getAbsolutePath()
              it.delete()
            }
          }
        ]]></script>
      </scripts>
    </configuration>
    <dependencies>
      <dependency>
        <groupId>org.codehaus.groovy</groupId>
        <artifactId>groovy-all</artifactId>
        <version>2.3.7</version>
        <scope>runtime</scope>
      </dependency>
    </dependencies>
  </plugin>  

Adicione o seguinte parâmetro no seu arquivo POM

Pom

<configuration>
<outputAbsoluteArtifactFilename>true</outputAbsoluteArtifactFilename>
</configuration>

https://maven.apache.org/plugins/maven-dependency-plugin/copy-mojo.html

Exemplo de pom

<plugins>
      <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-dependency-plugin</artifactId>
        <version>2.10</version>
        <executions>
          <execution>
            <id>copy</id>
            <phase>package</phase>
            <goals>
              <goal>copy</goal>
            </goals>
            <configuration>
              <artifactItems>
                <artifactItem>
                  <groupId>junit</groupId>
                  <artifactId>junit</artifactId>
                  <version>3.8.1</version>
                  <type>jar</type>
                  <overWrite>false</overWrite>
                  <outputDirectory>${project.build.directory}/alternateLocation</outputDirectory>
                  <destFileName>optional-new-name.jar</destFileName>
                </artifactItem>
              </artifactItems>
              **<outputAbsoluteArtifactFilename>true</outputAbsoluteArtifactFilename>**
              <outputDirectory>${project.build.directory}/wars</outputDirectory>
              <overWriteReleases>false</overWriteReleases>
              <overWriteSnapshots>true</overWriteSnapshots>
            </configuration>
          </execution>
        </executions>
      </plugin>
    </plugins>
  </build>

Configure em Jenkins:

// copy artifact 
copyMavenArtifact(artifact: "commons-collections:commons-collections:3.2.2:jar", outputAbsoluteArtifactFilename: "${pwd()}/target/my-folder/commons-collections.jar")
Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top