如何在Eclipse Helios中引用另一个项目中的库?

6
我在工作中遇到了一个问题,涉及到我们在代码中引用多个项目。 我们有一个名为Leviathan的产品,它有很多其他版本,每个版本都是我们在Eclipse中维护的单独项目。 作为开发人员,我们通常同时在Eclipse中打开多个项目(多个版本),因为我们会收到关于旧版本的帮助电话(同时开发多个版本)。
我们还有测试代码,每个Leviathan版本都有一个不同的项目。 我将我的项目命名为Leviathan_<branch name>。 因此,在我的Eclipse工作区中,我可能会有像以下这样的项目:
Leviathan_scott\(我的分支)
Leviathan_9.2\
Leviathan_9.3\
Leviathan_10.0\
Leviathan_10.1\
Test_scott\
Test_10.0
我的分支是我们主干的副本,因此我们可以将其视为最活跃的开发线。
问题在于,我们在测试代码中引用Leviathan\lib中的一些库。 每个开发人员可能会略微不同地命名他们的项目。 因此,在开发测试项目的.classpath时,我们引用Leviathan\(没有添加)。 这个项目的classpath(已经检入我们的源代码控制系统)可能看起来像:
<?xml version="1.0" encoding="UTF-8"?>
<classpath>
    <classpathentry excluding="**/*.MySCMServerInfo" kind="src" path="src"/>
    <classpathentry kind="lib" path="lib/abbot-1.0.2/abbot.jar"/>
    <classpathentry kind="lib" path="lib/abbot-1.0.2/costello.jar"/>
    <classpathentry kind="lib" path="lib/dbunit-2.4.8/dbunit-2.4.8.jar"/>
    <classpathentry kind="lib" path="lib/easymock-3.0/easymock-3.0.jar" sourcepath="lib/easymock-3.0/easymock-3.0-sources.jar">
        <attributes>
            <attribute name="javadoc_location" value="jar:platform:/resource/Test/lib/easymock-3.0/easymock-3.0-javadoc.jar!/"/>
        </attributes>
    </classpathentry>
    <classpathentry kind="lib" path="lib/objenesis-1.2/objenesis-1.2.jar"/>
    <classpathentry kind="lib" path="lib/privilegedAccessor-1.0.2/privilegedAccessor_1.0.2.jar"/>
    <classpathentry kind="lib" path="lib/unitils-3.1/unitils-core/unitils-core-3.1.jar" sourcepath="lib/unitils-3.1/unitils-core/src"/>
    <classpathentry kind="lib" path="lib/unitils-3.1/unitils-database/unitils-database-3.1.jar"/>
    <classpathentry kind="lib" path="lib/unitils-3.1/unitils-dbmaintainer/unitils-dbmaintainer-3.1.jar"/>
    <classpathentry kind="lib" path="lib/unitils-3.1/unitils-dbunit/unitils-dbunit-3.1.jar" sourcepath="lib/unitils-3.1/unitils-dbunit/src"/>
    <classpathentry kind="lib" path="lib/unitils-3.1/unitils-inject/unitils-inject-3.1.jar"/>
    <classpathentry kind="lib" path="lib/unitils-3.1/unitils-mock/unitils-mock-3.1.jar" sourcepath="lib/unitils-3.1/unitils-mock/src"/>
    <classpathentry kind="lib" path="lib/unitils-3.1/unitils-orm/unitils-orm-3.1.jar"/>
    <classpathentry kind="lib" path="lib/unitils-3.1/unitils-spring/unitils-spring-3.1.jar" sourcepath="lib/unitils-3.1/unitils-spring/src"/>
    <classpathentry kind="lib" path="lib/unitils-3.1/unitils-testng/unitils-testng-3.1.jar" sourcepath="lib/unitils-3.1/unitils-testng/src"/>
    <classpathentry kind="lib" path="data"/>
    <classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER"/>
    <classpathentry kind="lib" path="lib/unitils-3.1/unitils-core/lib/ognl-2.6.9.jar"/>
    <classpathentry kind="lib" path="lib/testng-5.14.1/testng-5.14.1.jar" sourcepath="lib/testng-5.14.1/testng-5.14.1-src.zip"/>
    <classpathentry combineaccessrules="false" kind="src" path="/Leviathan"/>
    <classpathentry kind="lib" path="/Leviathan/lib/slf4j-api-1.6.1.jar"/>
    <classpathentry kind="lib" path="/Leviathan/lib/hibernate3.jar" sourcepath="/Leviathan/lib/src/hibernate-3.6.0-src.zip"/>
    <classpathentry kind="output" path="classes"/>
</classpath>

当开发人员将Test项目加载到他/她的Eclipse工作区时,需要通过转到Preference->Java Build Path->Projects并添加Leviathan_scott项目来将项目链接到原始Leviathan项目。
问题在于,这当然不会更改任何引用“Leviathan \ lib”的条目。因此,我们必须做以下两件事之一:
1.使用文本编辑器查找/替换将我的.classpath中的所有引用从Leviathan更改为Leviathan_<branch name>。
2.从Java Build Path中删除对Leviathan * .jar的所有引用,并重新添加Leviathan_scott * .jar中的jars。
这些的问题在于每次更改.classpath时都需要执行操作,这使得这两个选项都不是理想的选择。我们的类路径不是经常更改,但我想说每两周更改一次。我希望能够链接我的项目,并且只需执行一个步骤即可链接这些项目。
似乎我们可以在Eclipse中设置环境变量,并将其添加到.classpath条目中。但是,现在我们有一个问题,因为如果我们在工作区中有多个要编译的测试项目,则这将无法正常工作。两个测试项目的.classpath条目都将引用同一个环境变量,这当然只能指向一个超级项目位置。
我觉得我应该能够做到这一点,但我不知道如何在Eclipse中实现它。非常感谢任何想法。
~Scott

Apache Maven像魔术一样轻松解决这类问题。 - Boris Pavlović
同意,但是让20个开发人员转换到新的构建系统很困难...如果我们绝对必须这样做,我可能能够为此辩护,但如果可以不这样做,那么我希望以这种方式完成。 - jwir3
3个回答

2
尝试使用Eclipse的“类路径变量”。
Window->Preferences->Java->Build Path->Classpath Variables

定义一个或多个变量,比如“Leviathan_under_test”,并将其指向您想要测试的版本。 然后,在项目构建路径中更改库引用以包括该变量。

当您更改要测试的Leviathan版本时,只需更改该变量并进行测试即可。如果需要,甚至可以为经常测试的版本设置多个变量,例如“LEVIATHAN_LATEST”或“LEVIATHAN_PROBLEM_CHILD”等。


这就是我所说的环境变量的意思。问题在于,如果我想要下载Test_10.0和Test_scott,并让它们在同一个工作区编译,我仍然需要更改构建路径。我需要至少在两个Test项目中的.classpath文件中更改变量。理想情况下,我们希望避免这种情况,因为这并不比目前的情况好多少——需要将Leviathan更改为Leviathan_scott或类似的名称。 - jwir3
实际上,一旦变量在.classpath文件中,你就不需要改变它;至少在$LEVIATHAN的情况下是这样。构建过程使用你在工作区设置的类路径变量值。你可以将其指向不同的目标,而无需编辑项目中的文件。 - Kelly S. French
不完全是这样。如果我在我的工作区中同时打开了Leviathan_10.0、Leviathan_Test_10、Leviathan_scott和Leviathan_test_scott,我想让Leviathan_test_scott指向Leviathan_scott,而Leviathan_test_10指向Leviathan_10.0,我该怎么解决这个问题? - jwir3
理论上的解决方法是使用多个工作区,因为每个工作区都可以有自己的环境变量值。如果您想将所有这些项目版本加载到一个工作区中,您将不得不创建多个变量,具有明确的名称,“LEVIATHAN_TEST_SCOTT”和“LEVIATHAN_10.0”,供每个项目使用。实际上,这与直接维护每个项目的类路径并没有太大的区别。您有一个高级的构建配置问题(挑战),因此您需要查看更强大的构建工具。http://en.wikipedia.org/wiki/Continuous_integration - Kelly S. French

2
这是一个依赖管理的问题,有很多事实标准工具可以帮助解决!我强烈建议你使用 ANTIvy's 依赖管理或使用 Maven(或任何其他具有依赖关系管理功能的构建工具)。

无论你使用哪个工具,我都会使用像 Nexus 或 Artifactory 这样的工件库管理器,这样你就有了内部构建工件的唯一真实来源。

这样,你将始终拥有你想要的库的规范版本,以及你想要的时间。


1

如果您不想使用外部工具来管理各种项目依赖项,可以尝试进入单个Leviathan项目的构建路径属性,在“顺序和导出”选项卡中勾选您需要运行测试的库。

这样,您就不需要在测试项目中导入库,并且通过切换测试项目,您可以自动更新库。


嗯...这看起来很有前途。所以,你的意思是说,不是在测试项目中单独导入所有库,而是从原始的leviathan项目中导出它们,然后我只需要将leviathan项目导入测试项目? - jwir3

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接