Как использовать ivy для создания войны без копирования jar-файлов в каталог lib

Моя цель состоит в том, чтобы мой скрипт сборки ant создал военный файл и включил в него jar-файлы, от которых, как известно ivy, зависит этот проект. Лучший код, который я мог придумать на данный момент, это следующий

<mkdir dir="dist/lib"/>
<ivy:retrieve pattern="dist/lib/[artifact].[ext]" sync="true"/>
<war destfile="dist/${ivy.module}.war" basedir="build" includes="**/*.class"
    webxml="${war.webxml}">
    <fileset dir="${war.web}"/>
    <lib dir="dist/lib"/>
</war>

Проблема с этим кодом в том, что он дважды копирует банки. Один раз в моем каталоге dist/lib и снова в войне, когда она будет создана. Это работает, но я не могу избавиться от ощущения, что есть лучший способ.

То, что я хотел бы сделать, это что-то вроде следующего

<ivy:cachepath pathid="locpathref.classpath"/>
<war destfile="dist/${ivy.module}.war" basedir="build" includes="**/*.class"
    webxml="${war.webxml}">
    <fileset dir="${war.web}"/>
    <lib refid="locpathref.classpath"/>
</war>

Проблема в том, что тег lib не принимает никаких refid. Любые идеи или я застрял с дополнительным набором копий файлов?


person AmaDaden    schedule 16.01.2010    source источник
comment
Используйте ‹ivy:cachefileset setid=locpathref.classpath conf=runtime/›, тогда тег lib будет работать должным образом.   -  person Mark O'Connor    schedule 25.03.2010


Ответы (2)


Проблема здесь в том, что тег lib является пользовательским набором файлов, который направляет свои файлы в подкаталог lib военного архива. Можно было бы написать пользовательскую задачу war, но я не думаю, что это стоит усилий.

Если вы хотите улучшить способ, которым ivy управляет зависимостями вашей войны, могу ли я предложить использовать конфигурации?

Создайте конфигурацию, описывающую зависимости времени выполнения:

    <ivy-module version="2.0">
    <info organisation="apache" module="hello-ivy"/>
    <configurations>
        <conf name="build" description="Libraries needed to for compilation"/>
        <conf name="war" extends="build" description="Libraries that should be included in the war file" />
    </configurations>
    <dependencies>
        <dependency org="commons-lang" name="commons-lang" rev="2.0" conf="build->*,!sources,!javadoc"/>
        <dependency org="commons-cli" name="commons-cli" rev="1.0" conf="build->*,!sources,!javadoc"/>
    </dependencies>
</ivy-module>

После этого вы извлекаете их в специальный каталог (используя шаблон), который можно просто включить с помощью тега lib задачи war:

    <ivy:retrieve pattern="${lib.dir}/[conf]/[artifact].[ext]"/>

    <war destfile="${war.file}" webxml="${resources.dir}/web.xml">
        <fileset dir="${resources.dir}" excludes="web.xml"/>
        <lib dir="${lib.dir}/war"/>
    </war>

Преимущество этого подхода заключается в том, что вы используете атрибут ivy conf каждой зависимости проекта, чтобы в конечном итоге решить, включать ли банку в военный файл или нет. Файл сборки больше не заботит.

В заключение я понимаю, что смысл вашего поста заключался в беспокойстве о нескольких копиях ваших файлов jar... Использование моего предложенного подхода приведет к дальнейшему увеличению количества ваших копий, но я бы сказал, что это не проблема, если у вас есть чистый цель, чтобы удалить их впоследствии.

person Mark O'Connor    schedule 23.01.2010
comment
Я согласен, что это лучшее решение, чем то, что я делаю, но оно по-прежнему не удаляет лишнюю копию файла, как мне бы хотелось. Чем больше я смотрю на это, тем больше я думаю, что, как вы сказали, единственный реальный способ исправить это — создать пользовательскую военную задачу или даже новую пользовательскую задачу библиотеки для военной задачи. В идеальном мире эта новая задача могла бы стать частью Айви или Муравья. - person AmaDaden; 24.01.2010
comment
Решение, которое вам нужно, — это использовать задачу ivy cachefileset вместо cachepath. Тогда параметр refid для тега lib warfile будет работать, как и ожидалось. - person Mark O'Connor; 25.03.2010

Если вы используете Ant 1.8, вы можете использовать метод, описанный здесь: http://www.beilers.com/2010/06/ivy-dependency-management-lessons-learned-and-ant-1-8-mapped-resources/

ПРИМЕР:

<war destfile="${war.full.path}" webxml="WebContent/WEB-INF/web.xml" manifest="${manifest.path}">
    <fileset dir="WebContent">
     </fileset>
    <classes dir="${build.dir}"/>

    <mappedresources>
      <restrict>
        <path refid="classpath.CORE"/>
        <type type="file"/>
      </restrict>
      <chainedmapper>
        <flattenmapper/>
        <globmapper from="*" to="WEB-INF/lib/*"/>
      </chainedmapper>
    </mappedresources>

    <zipfileset dir="src" prefix="WEB-INF/classes">
         <include name="**/resources/**/*.properties" />
         <include name="**/resources/**/*.xml" />
    </zipfileset>
</war>
person Snekse    schedule 11.03.2011
comment
Очень интересно... Попробую и отчитаюсь! - person Jan Galinski; 15.03.2011