Apache Ivy.未检索到传递依赖项



我有以下结构的3个项目:

App
|  |
  ...
|  |
|  +--lib
|  |    |
|  |    +--...
|  |
|  +--dist
|
Lib
|  |
   ...
|  |
|  +--lib
|  |    |
|  |    +--sublib-1.0.jar
|  |
|  +--dist
|       |
|       +--lib-1.0.jar
|
SubLib
   |
  ... 
   |
   +--dist
        |
        +--sublib-1.0.jar

有以下关系:

App <-- Lib <-- SubLib

我使用apache ivy来检索AppLib的依赖项。依赖关系描述如下:ivy.xml/Lib:

<ivy-module version = "2.0">
    <info organisation = "com.test.lib" module = "lib"/>
    <dependencies>
        <dependency org = "com.test.sub.lib" name = "sublib" rev = "1.0" conf = "compile->default"/>
    </dependencies>
</ivy-module>

ivy.xml of App:

<ivy-module version = "2.0">
    <info organisation = "com.test.app" module = "App"/>
    <dependencies>
        <dependency org = "com.test.lib" name = "lib" rev = "1.0" conf = "compile->default"/>
    </dependencies>
</ivy-module>

ivysettings.xml:

<ivysettings>
    <settings defaultResolver = "local"/>    
    <resolvers>
        <filesystem name = "local">
            <artifact pattern = "${ivy.settings.dir}/SubLib/dist/[artifact]-[revision].[ext]"/>
            <artifact pattern = "${ivy.settings.dir}/Lib/dist/[artifact]-[revision].[ext]"/>
        </filesystem>
    </resolvers>    
    <modules>
        <module organisation = "com.test.ivytest" resolver = "local"/>
    </modules>
</ivysettings>

预期结果:执行ivy:retrieve后,sublib-1.0.jarlib-1.0.jar同时存在于App/lib

实际结果:只有lib-1.0.jar存在于App/lib中。为App生成的ivy-report没有提到subliblib的依赖项。在构建期间,ant + ivy日志中也没有任何类型的日志。

注意: lib-1.0.jar没有被构建为fat-jar。

我在这个配置中缺少什么?


更新

我已经做了一些思考,我得到的唯一结论是,这个问题确实是错误配置。根据没有检索到传递依赖的事实判断,我们可以肯定地说,ivy在解析lib时没有任何类型的信息。这是有道理的,因为Lib/dist文件夹可以在文件系统中的任何位置。获得传递依赖信息的唯一方法是将各自的ivy.xml放在靠近该jar的某个地方。事实并非如此。日志[ivy:retrieve] local: no ivy file found for com.test.lib#lib;1.0: using default data中的消息稍微证实了这一点。保存信息的唯一方法是在%user%/.ivy/cache中缓存数据。生成的[org]-[artifact]-[conf].xml文件确实包含依赖项信息。所以我猜为了正常工作,我将不得不在应用程序的分辨率级别上使用缓存。

这有什么意义吗?还是我又错了?

好吧,所以问题确实是糟糕的配置和我缺乏理解。下面是如何使其工作的详细解释。我不太擅长术语,所以我可能在这里用错了一些词。让我们来看看项目的配置和是什么。

Sublib将成为Lib 运行时依赖项,而CC_25 有编译时依赖项guava

SubLib
   |  `lib
   |      `guava-19.0.jar
   |
    `dist
   |    `--sublib-1.0.jar
   |
    `src
        `...
因此,我们需要在SubLib的ivy.xml: 中进行适当的配置。
<ivy-module version="2.0">
    <info organisation="com.test.sub.lib" module="sublib"/>
    <configurations>
        <conf name="runtime" visibility="public"/>
    </configurations>
    <dependencies>
        <dependency org="com.google" name="guava" rev="19.0" conf="runtime->default"/>
    </dependencies>
</ivy-module>

在这里,通过声明一个runtime配置,我们声明这个ivy.xml描述了一个运行时依赖的模块。由于番石榴没有这样的文件,我们将其描述为默认的。这很标准。现在,为了让其他人知道sublib-1.0.jar实际上依赖于guava-19.0.jar,我们需要将其发布到存储库中,以便这些信息以文件ivy-[version].xml的形式存在于jar旁边。我选择发布到build文件夹。要做到这一点,ivysettings.xml需要包含一个解析器,它可以帮助匹配发布和检索时的文件模式,当我们将从Lib解析时。

<ivysettings>
    <settings defaultResolver="filesystem-resolver"/>
    <resolvers>
        <filesystem name="sublib-resolver">
            <ivy pattern="${ivy.settings.dir}/SubLib/dist/repo/ivy-[revision].xml"/>
            <artifact pattern="${ivy.settings.dir}/SubLib/dist/repo/[artifact]-[revision].[ext]"/>
        </filesystem>
        <filesystem name="filesystem-resolver">
            <artifact pattern="${ivy.settings.dir}/SubLib/lib/[artifact]-[revision].[ext]"/>
        </filesystem>
    </resolvers>
    <modules>
        <module name="sublib" organisation="com.test.sub.lib" resolver="sublib-resolver"/>
    </modules>
</ivysettings>

sublib-resolver将允许找到相应的ivy-[revision].xml,其中包含有关jar的依赖关系和位置的信息。而filesystem-resolver将找到我们的guava依赖。现在我们只需通过调用解析器来发布sublibant:

<target name="publish">
        <ivy:publish artifactspattern="${dist.dir}/[artifact]-[revision].[ext]"
                     resolver="sublib-resolver"
                     overwrite="true"
                     pubrevision="${revision}"
        />
</target>

现在到Lib。Lib将成为App编译时依赖项,我们在ivy.xml中这样描述它,并声明SubLib运行时依赖项:

<ivy-module version="2.0">
    <info organisation="com.test.lib" module="lib"/>
    <configurations>
        <conf name="compile" visibility="public"/>
        <conf name="runtime" extends="compile" visibility="public"/>
    </configurations>
    <dependencies>
        <dependency org="com.test.sub.lib" name="sublib" rev="2.0" conf="runtime->compile"/>
    </dependencies>
</ivy-module>

这就是配置发挥作用的地方,也是我一开始不理解的地方。左边是可以理解的:sublib被声明为运行时依赖,我们在它的ivy文件中将它分配给runtime conf。在箭头的右侧,我们声明我们也需要sublib的编译时依赖项。这样配置的是guava。它将被解析器找到并检索。所以,我们也需要一个Lib的解析器,所以完整的ivysettings.xml文件看起来像这样:

<ivysettings>
    <properties file="${ivy.settings.dir}/ivysettings.properties"/>
    <settings defaultResolver="filesystem-resolver"/>
    <resolvers>
        <filesystem name="sublib-resolver">
            <ivy pattern="${ivy.settings.dir}/SubLib/dist/repo/ivy-[revision].xml"/>
            <artifact pattern="${ivy.settings.dir}/SubLib/dist/repo/[artifact]-[revision].[ext]"/>
        </filesystem>
        <filesystem name="lib-resolver">
            <ivy pattern="${ivy.settings.dir}/Lib/dist/repo/ivy-[revision].xml"/>
            <artifact pattern="${ivy.settings.dir}/Lib/dist/repo/[artifact]-[revision].[ext]"/>
        </filesystem>
        <filesystem name="filesystem-resolver">
            <artifact pattern="${ivy.settings.dir}/SubLib/lib/[artifact]-[revision].[ext]"/>
        </filesystem>
    </resolvers>
    <modules>
        <module name="sublib" organisation="com.test.sub.lib" resolver="sublib-resolver"/>
        <module name="lib" organisation="com.test.lib" resolver="lib-resolver"/>
    </modules>
</ivysettings>

并在Libbuild.xml中发布Lib:

<target name="publish">
        <ivy:publish artifactspattern="${dist.dir}/[artifact]-[revision].[ext]"
                     resolver="lib-resolver"
                     overwrite="true"
                     pubrevision="${revision}"
        />
</target>

现在讨论主要问题:传递检索。配置。在Appivy.xml中,我们需要精确地指定我们想要的传递依赖。它们存在的信息存储在repos中是不够的。必须在Appivy.xml:

中指定它。

<configurations>
    <conf name="compile" visibility="public"/>
</configurations>
<dependencies>
    <dependency org="com.test.lib" name="lib" rev="1.0" conf="compile->compile; compile->runtime"/>
</dependencies>

这里发生的事情如下:通过声明compile conf,我们声明App具有编译配置。第一个箭头链,像前面一样,声明我们(编译配置模块App)想要获得称为lib的编译配置依赖项。箭头的左右两侧。第二个箭头集表示我们(编译配置的模块App)希望获得lib运行时配置的依赖项!也就是sublib。由于它与guava一起出现,它也被检索。


一个有点混乱的解释,可能不是最优雅的解决方案,但这是我设法使它正常工作的唯一方法。如果有人知道更好的方法,我将不胜感激。

相关内容

  • 没有找到相关文章

最新更新