OSGi(JSR 8)工作组成立于 1997 年,主要关注嵌入式 Java,以支持嵌入式软件的模块化升级。在成功解决了 Eclipse 插件不可避免的依赖关系之后, OSGi 成为主流。大概在 2005 年,好几种方法都开始利用装配机制和定义良好的依赖关系在企业Java 中引入更进一步的模块化,其中包括 Spring 和服务组件体系架构,而 EJB 却慢慢消失了。现在,大多数企业 Java 厂商都在 OSGi 的基础上重写了他们的中间件。
但 OSGi 技术也让很多人觉得懊恼,MuleSource 的创始人 Ross Mason 前几天就在他的博客上毫不掩饰地对此发表了议论。
OSGi 想要改变一切,依赖关系会完全隔离(不再受制于冲突的依赖关系版本),而且会严格要求 Bundle 彼此可见。和很多人一样,我就这样买了 OSGi 的账,让我们的工程人员改造 Mule、让它支持 OSGi。
我们的团队有好几个月都在 Manifest 上扯皮、打包自己的 Bundle、无休止地摆弄构建,OSGi 的优势在这之后变得越来越弱。我们认同“不劳无获”,但后来这却成了作茧自缚。
Ross 的工程团队不知道如何向中间件开发人员隐藏 OSGi 的复杂性。他认为这个问题是由 OSGi 的起源——嵌入式——造成的。
OSGi 对中间件厂商来说是个很棒的规范,……但 OSGi 绝不是为了应用开发人员的需求才创建的。它的起因是,在用户不干预的情况下远程更新部署在机顶盒里的软件。OSGi 对这类软件的部署来说是个很好的规范,因为只有中间件厂商才需要处理 Bundle 的部署。
模块化和版本化是中间件项目的两个核心问题。服务实现经常会发生变化(有时每个季度就会改变一次),而大型组织过去也常把所有的服务部署在一个 ear 文件中,每过三个月,就算 ear 中的很多内容从未发生变化、也不依赖于新的或更新过的服务,消费者和服务提供者还是要进行一次大规模的同步,更别说还要一直测试所有的服务了。有人可能会说, 缺少模块化和版本化正是 SOA 失败的原因所在。Ross 补充说:
OSGi 承诺会对软件堆栈进行模块化,并让中间件基础设施即插即用。遗憾的是,有些 Bundle 就没有兑现这样的承诺,这些 Bundle 跨容器之后就不能以相同的方式正常运行了。
Ross 认为 OSGi 背后的原则正好适用于永久异构的堆栈。但他说:
既然 OSGi 现在主要针对普通的应用开发,那就要重新思考一下它的用户交互部分。从实际情况来说,不用 OSGi 也可能在 JVM 上做到模块化和热部署,但 OSGi 日常开发的痛苦却比它具备的优势多多了。
Neil Bartlett 对 Ross 作出了如下的回应:
bnd 之类的工具已经对开发人员隐藏了 OSGi 的细节。我认为现在的问题是,基于 OSGi 进行开发的替代方法和工具过于泛滥。我仍然相信,不用 OSGi 进行日常 JVM 开发会比任何短期利益都要痛苦……你上次手工编写.class 文件是什么时候呢?也许你永远没手工写过,只是编译 Java 源文件来生成。OSGi 的 MANIFEST 也是类似的内容,它应该是类编译器工具的输出。
Joe Sampson 从测试和构建的角度分享了他使用 OSGi 的经验,这些经验都是他发现不太容易使用的部分。Hani Suleiman 指出:
OSGi 在概念层次上是个很好的模型,只是被那些本身不支持它的语言给拖累了。大家不愿意使用不支持 OSGi 的语言,这就意味着 OSGi 永远都是个令人讨厌的笨拙的框架,没有人会真正喜欢用它(据我所知,如果你经常使用 OSGi,那你的体验显然会不一样)。
Richard S. Hall 也提出了一点儿忠告:
如果你开始使用 OSGi,期望所有遗留的 JAR 包都能正常工作,还想尝到模块化的甜头,那你还不如不尝试。这跟二十世纪八十年从 C 切换到 C++ 有几分相像,那时人们希望所有内容都能自动变成面向对象的。
WSO2 的 CTO Paul Fremantle 在给Ross 的回应中解释到,WSO2 Carbon 不仅是基于OSGi 构建的,还完全向开发人员隐藏了OSGi 的细节。Paul 承认这并不容易,但用自己的构建方式实现模块化、版本化和配置却要更难一些。
你对OSGi 持什么看法?你有没有遇到什么困难?OSGi 对你来说是透明的么?你的中间件是否充分模块化,且支持一流的版本控制策略?就像Hani 所指出的,现代架构的核心问题往往是缺少语义、架构的语义与底层编程语言的语义不匹配,难道我们就要因此将这个架构打入地狱么?
评论