【问题标题】:Maven: How to check if an artifact exists?Maven:如何检查工件是否存在?
【发布时间】:2011-06-16 02:32:02
【问题描述】:

如果本地存储库中已存在工件,我如何从 Mojo 中检查?

我正在将大型二进制文件安装到本地 Maven 存储库中,在尝试下载它们之前我需要知道它们是否已经存在。

【问题讨论】:

    标签: maven-2 mojo


    【解决方案1】:

    http://docs.codehaus.org/display/MAVENUSER/Mojo+Developer+Cookbook的帮助下解决了

    /**
     * The local maven repository.
     *
     * @parameter expression="${localRepository}"
     * @required
     * @readonly
     */
    @SuppressWarnings("UWF_UNWRITTEN_FIELD")
    private ArtifactRepository localRepository;
    /**
     * @parameter default-value="${project.remoteArtifactRepositories}"
     * @required
     * @readonly
     */
    private List<?> remoteRepositories;
    /**
     * Resolves Artifacts in the local repository.
     * 
     * @component
     */
    private ArtifactResolver artifactResolver;
    /**
     * @component
     */
    private ArtifactFactory artifactFactory;
    [...]
    Artifact artifact = artifactFactory.createArtifactWithClassifier(groupId, artifactId, version, packagingType, classifier);
    boolean artifactExists;
    try
    {
      // Downloads the remote artifact, if necessary
      artifactResolver.resolve(artifact, remoteRepositories, localRepository);
      artifactExists = true;
    }
    catch (ArtifactResolutionException e)
    {
      throw new MojoExecutionException("", e);
    }
    catch (ArtifactNotFoundException e)
    {
      artifactExists = false;
    }
    if (artifactExists)
      System.out.println("Artifact found at: " + artifact.getFile());
    

    如果您想在不下载的情况下检查远程工件是否存在,可以使用Aether library 执行以下操作(基于http://dev.eclipse.org/mhonarc/lists/aether-users/msg00127.html):

    MavenDefaultLayout defaultLayout = new MavenDefaultLayout();
    RemoteRepository centralRepository = new RemoteRepository.Builder("central", "default", "http://repo1.maven.org/maven2/").build();
    URI centralUri = URI.create(centralRepository.getUrl());
    URI artifactUri = centralUri.resolve(defaultLayout.getPath(artifact));
    HttpURLConnection connection = (HttpURLConnection) artifactUri.toURL().openConnection();
    connection.setRequestMethod("HEAD");
    connection.connect();
    boolean artifactExists = connection.getResponseCode() != 404;
    

    具有以下依赖项:org.eclipse.aether:aether-util:0.9.0.M2 和以下导入:

    import java.net.HttpURLConnection;
    import java.net.URI;
    
    import org.eclipse.aether.artifact.Artifact;
    import org.eclipse.aether.artifact.DefaultArtifact;
    import org.eclipse.aether.repository.RemoteRepository;
    import org.eclipse.aether.util.repository.layout.MavenDefaultLayout;
    

    【讨论】:

    • 我将留下这个答案,以防有人想在不实际下载的情况下查找工件。
    • 我不喜欢的部分是您实际上不仅在尝试,而且实际上您正在下载工件。我怀疑这就是你想对大型工件做的事情。看看我的回答。
    • @carlspring,你是对的。解析工件会导致它被下载。
    • @carlspring,我更新了答案,解释了如何在不下载工件的情况下检查工件是否存在。
    • 我建议尝试将Wagon 注入你的mojo,然后是我在下面展示的示例。但是您的代码也应该这样做。只是...不是 Maven 方式,但是...是的,它应该可以工作。
    【解决方案2】:

    由于被接受为正确的答案不再指向有效的 URL-s,并且因为我知道更好的方法,因此我发布了一个新答案。

    wagon-maven-plugin,它有一个exist 目标。文档有点不准确,但您可以使用它。

    代码方面,你可以看看DefaultWagonDownload类的exists方法:

    /**
     * 
     * @param wagon - a Wagon instance
     * @param resource - Remote resource to check
     * @throws WagonException
     */
    public boolean exists( Wagon wagon, String resource )
        throws WagonException
    {
        return wagon.resourceExists( resource );
    }
    

    【讨论】:

    • 我修复了已接受答案中的断开链接。至于这个答案,我不清楚我会以resource 传递什么。我将如何从 groupId:artifactId:classifier:version 转到使用此 API?
    • 当然,资源将是相应工件的 URL。您需要有一个方法来接收 ArtifactArtifactRepository 并返回一个 URL。
    • 为了清楚起见,GAV 实际上是像groupId:artifactId:version:type:classifier 这样订购的。
    【解决方案3】:

    如果您希望您的工件存在于远程 maven 存储库中,我建议您只需使用 copy mojo of the maven-dependency-plugin

    它将使用正常的 maven 解析机制来检索工件,因此不会下载本地存储库中已经存在的东西。

    在插件中,当使用 maven 2(不确定 maven3)时,您可以使用 mojo executor 从您的代码中轻松调用 mojo。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-10-13
      • 2011-11-01
      • 1970-01-01
      相关资源
      最近更新 更多