可能吗 ?
是的,当然了。过去,我有一些这样的项目,希望在这里能有所帮助。
您将使用Maven的两个主要功能将事物编织在一起:
分而治之
您将需要将您的项目拆分为多个独立的项目。这里所说的独立是指对项目外部代码的所有引用都是通过Maven中的依赖关系完成的,而不是直接合并源代码树。
根据源代码树的状态,这可能需要进行大量工作。那就是说,您不是在为Maven拔腿而做,而是作为结构化和清理代码库的一种手段。将其视为您的工具集,在这里更容易找到它们:
比这里:
Maven高度依赖约定,因此您的资料越有条理,Maven就可以为您提供更多帮助。就是说,可能需要您重新组织以更好地适应它自己的约定,并且如果我在这里不得不提出一个建议,那就是更改内容以适合Maven的约定要比尝试配置Maven容易得多。了解您的约定。
如果这些项目可以在主应用程序之外使用,那么它们可以作为真正的独立库运行,并包含maven依赖项。它们应位于自己的存储库中(而不是在应用程序源树中),并且不应依赖于主应用程序的任何部分。
应用程序的核心部分(一旦拆分为项目)可以放在一起作为模块。通常,您会将它们放置为应用程序主源文件夹的子文件夹。
同样,您的应用程序的父POM将包含模块声明。您还将在其中放置应用程序的所有常见依赖关系,并声明大多数构建插件及其配置。我在这里也建议您放置一组属性,例如可以在模块中重用的应用程序版本等。当所有版本具有相同版本并将版本放在一个位置时,这将更容易管理。
工装
如果您的团队规模大于1,我也强烈建议您为Maven依赖项安装一个存储库。看看Artifactory,Nexus或Archiva。您可以将POM文件配置为直接安装到这些文件,因此一旦运行它就不会有太大的开销,但是可以节省您的团队大量时间,用正确的jar来解决依赖关系。
关于工具,下一步的逻辑步骤是一个持续集成系统(Jenkins,还有更多)。它将负责构建运行测试的源代码并推送至工件,所有这些都只需编写代码,其余代码即可工作。
由于您将应用打包为战争专家,因此无需合并jar文件或其他类似的工作,即可处理战争并将所有依赖项放置在适当的位置,因此不必担心。
例
我可以在这里继续更长的时间,但是没有什么比一个好的榜样更好了。在github上查找类似规模的项目,并查看它们如何构建pom文件和文件夹层次结构。观察不止一种,有些会比其他更适合您的设置,没有什么能真正体现出真相,但您应该找到足够的力量来激发关于如何完成它的想法。
以詹金斯为例:
您可以看到他们的父POM相当广泛。
它们确实使用模块,如您在本节中所见:
<modules>
<module>core</module>
<module>war</module>
<module>test</module>
<module>cli</module>
</modules>
每个模块对应一个具有相同名称的子文件夹,该子文件夹还包含一个POM。您可以像这样嵌套任意数量,尽管可以将其保持在合理水平内;)。
从小开始
如果您从未使用过Maven,我建议您不要立即开始使用模块。慢慢来,先说一个您可能拥有的较简单的库,然后使其成为Maven项目。然后将您的主应用程序变成一个简单的maven项目。一旦完成,开始添加简单的依赖关系,然后拆分第一个模块,依此类推。
Maven是一个很棒的工具,但是它也可能会给脖子带来极大的痛苦,尤其是当事情进展不顺利时。从您第一次尝试的整个过程开始,就是灾难的根源(对我而言!)。
如果事情有点怪异,您可以始终使用mvn help:effective-pom
命令查看Maven实际理解的内容。
外挂程式
从您的评论中,我可以更好地理解您想要实现的目标。在这种情况下,我会选择插件方法。创建一个项目,该项目公开要隔离工作的扩展点的API。然后,您可以将其用作将要实现它的新项目中的依赖项。在您的主应用程序中,只需为这些实现添加适当的依赖项(这次不使用Maven模块),那么您应该一切顺利。最终,主应用程序项目几乎不会携带任何源代码,这些代码都是在外部项目中完成并通过依赖项加载的。
但是,您将需要使用这种方法重新部署整个应用程序,而不管内核是否更改,因为战争是从依赖关系静态构建的,更改其中一个依赖关系意味着重新构建整个事物。听起来比实际情况更糟。实际上,实际上只会构建新的更改,其余的基本上是以前的jar的副本。但是由于所有内容都在war文件中,因此将需要重新构建它,并且需要停止并重新启动服务器。
如果您需要更进一步,事情会变得有些复杂,尽管并非没有可能。我建议您研究OSGI ,尽管还有其他实现,但是Apache Felix可以帮助您入门。这将允许您将外部jar放入适当的插件中。您将获得对组件运行时生命周期的更多控制,从而为动态重新加载和更新打开了方便之门。但是,这将需要对核心进行重大更改,因此,这可能不是一个好的起点。但是,一旦您的项目被很好地分隔开并且所有部分都按照您想要的方式隔离开了,那么如果在更新时启动和停止应用程序是一个主要问题,那么下一步就很自然了。
模块和依赖项之间的基本区别是:
- 模块将作为主文件夹位于与主应用程序相同的源代码树中。
- 依赖关系可以在任何地方。
你可以在这里找到圣经。
希望这有帮助,祝你好运。