在两个或多个项目之间共享公共代码(例如域类)的最佳方法是什么?

我们正在开发一个由两个Eclipse项目组成的Web应用程序。 一个项目是基于HTTP的RESTful Web服务; 另一个项目是一个网站。 两者都将部署为WAR。 最初,两者都将部署在同一个应用服务器实例下,但最终它们将位于不同的盒子上。

该网站应用程序使用RESTful WS应用程序。 显然,两个项目都会有代码 – 特别是域类 – 。 例如,可能存在位于 / users的资源,该资源在User对象上公开CRUD操作; 要更新用户,网站应用程序会将XML编组的用户对象POST到 / users。 对 / users / 1执行GET将返回一个XML编组的User对象。

显然,由于各种原因,在两个项目中都有一个User类非常愚蠢。 所以我想知道最好的方法是什么? 将公共代码放在两个项目之间共享的JAR中是我过去所做的,但有更好或更简单的方法吗?

编辑:删除RESTful引用。 除了语义之外,在两个Eclipse项目之间共享公共代码的正确方法是什么?

关注点分离

实际上创建第三个项目并添加项目依赖项是最好的方法,因为关注点的分离不仅是类的原则,也是软件模块的原则。 它创造了一些优势:

  • 阅读更少的代码来学习一个项目的绳索。
  • 更好的依赖控制,因为你可以省略一些项目间的依赖关系,因此使用错误模块的类是不可能的。
  • 复制代码很糟糕。

项目结构

确保您没有创建一个大的“ 实用程序 ”项目,而是创建特定于域的项目,如用户管理地址簿

在你的情况下,它可能是

  • user-api包含用户传输对象
  • user-service提供CRUD操作
  • webapp (或用户 – 客户端 )调用用户服务。

其他构建系统

当转向持续集成时,您需要使用比Eclipse更好的构建系统,但原则是相同的。 您将创建具有最小依赖性的小模块。

最受欢迎的Java系统构建项目是Maven , Ant和Gradle 。 每种方法都有自己的方式来定义模块依赖性。

Eclipse中的项目引用

要告诉Eclipse有关项目依赖性的信息,请右键单击该项目,打开属性并切换到项目引用。 在这里,您可以标记依赖项,以便代码更改将立即生效,而无需手动复制JAR文件。

项目参考菜单

Imho,这取决于您的构建系统 ,而不是您的IDE。

所以,如果你

  • 使用纯Eclipse构建并希望保持简单,只需添加第三个项目并添加依赖项。
  • 使用osgi,你已经正确地创建了一个新的osgi项目。
  • 使用构建工具,如maven或gradle,然后设置多项目构建。

通常,您创建包含共享代码的第三个项目(例如核心共享 )。 只需从你的项目中依赖它。

您需要创建另一个项目(即共享)。 我所有的SERVER-CLIENT应用程序都是这样的。

以下是EJB应用程序的示例

Basicaly, 共享模块具有客户端使用并由ejbModule实现的EJB接口

你如何使用第三方jar子? 将您的公共代码视为第三方jar并将相同的规则应用于您的项目。 您可以使用像maven这样的依赖关系管理工具,以便按顺序保持版本控制。

如果要升级到可以部署EAR的Application Server,可以将公共代码放在jar中,这是EAR的依赖…因此,EAR中的其他WAR项目可以使用公共代码。

您也可以尝试OSGI。

如果您在RESTful系统中共享客户端和服务器之间的域类,那么您就无法实现REST。 REST约束旨在通过确保两个系统之间的唯一耦合仅限于媒体类型和链接关系,允许客户端和服务器系统独立发展。

如果你需要共享域对象,忘记REST,它会给我带来更多麻烦而不是值得。

有几种可能的方法可以做到这一点,根据您的具体情况和要求,有些可能比其他方法更好。

在所有情况下,我强烈推荐一个了解版本号的系统。

一个经典的方法是使用maven。 此外,它非常好地集成在eclipse中,您可以将模块构建为一个父项目的一部分,例如:

project-parent project-website1 project-website2 project-controllers project-model [...] 

在内部,这些模块可以相互依赖。 你可以将接口与实现分开:

 project-parent project-website1 project-website2 project-api project-api-impl [...] 

然后大部分时间取决于api模块。 maven还有一些处理WAR文件的机制。

这种(单项目)方法可能是非常小的开发团队的理想选择。 主要的缺点是单独发布内容是非常不切实际的 – 实现中只有影响website2的错误修正也需要发布website1。

此外,这种分离往往不那么清晰,这使得将东西移动到不应该存在的共享模块中可能太容易了。

另一种模式是:

  project1-parent project1-webapp project1-specifics [...] project2-parent project2-webapp project2-specifics [...] common-parent common-api common-impl common-model [...] 

这使分离更清晰,您可以单独发布。 另外(虽然在正常情况下可能不建议这样做),project1-webapp可能依赖于比project2-webapp更旧或更新版本的通用模块。 maven可以在这里找到:

 https://maven.apache.org/ 

另一个可以帮助您处理版本控制的工具集是:

 https://gradle.org/ 

为了充分利用这些,您可能还需要考虑使用git和gitflow:

 http://git-scm.com/ https://www.atlassian.com/git/tutorials/comparing-workflows/gitflow-workflow/ 

并了解如何使用它来处理版本控制和发布。

就个人而言,我刚开始时发现它非常混乱 – 但现在这一切都很有意义。