JPMS / Project Jigsaw对小型应用程序/库的好处

时间:2017-08-12 21:47:23

标签: java java-9 jigsaw

我了解Java平台模块系统(JPMS)对大型应用程序的好处,但有没有理由将小型库或应用程序转换为(单个)模块?如果是这样,Modular Jar Files是实现这一目标的最佳方法,还是首选的正常方法?

展望未来,模块化v。类路径程序是否会对性能产生影响?

3 个答案:

答案 0 :(得分:9)

即时性能影响包括:

  • 模块化应用程序可以选择使用jlink,以便可分发运行时的大小减少:它只使用您需要的模块。因此,如果您不需要Swing,Corba等,它不会驻留在磁盘上。 (更多信息here)。
  • 模块化应用程序使用模块图进行类加载;这个算法比类路径的线性搜索要快得多(更多信息here)。

这绝不保证您的应用会更快,但上述情况无疑具有吸引力。

长期来看,请考虑一下:

  • 虽然在JDK 9中有实验,但是有一个AOT编译器(对于Linux x64)会将java.base模块编译为本机代码。这可能是未来Java版本的发展方向。当然这将改善未来的启动时间。 (再次,更多信息here

答案 1 :(得分:3)

  

如果是这样,Modular Jar Files是实现这一目标的最佳方法,还是首选的常规方法?

我不确定“正常方法”是什么意思 - modular JARs是创建模块系统将为其创建模块的工件的“常规方法”。

  

[我]有什么理由将小型库或应用程序变成(单个)模块吗?

是的,一些:

  • 创建模块化应用程序或使用模块化库的开发人员受益于reliable configuration,他们只能在所有依赖项都存在的情况下启动他们的应用程序 - 无论应用程序/库有多大,这都是一个好处

  • 作为图书馆设计师,您可以隐藏内部。虽然strong encapsulation仅在将模块化JAR放到模块路径上时才有效,但模块描述符仍会在代码中记录您的意图,并允许您更加无意地更改代码。应用程序开发人员也会从中受益,因为他们不能再意外地依赖不受支持的实现细节。

  • 即使在小型应用程序和库中,也可以使用服务来分离功能的不同方面,并使代码更容易扩展。

  • jlink只能在运行时图像中包含“真实”模块(与自动模块相对)。不提供模块化JAR会剥夺用户对这种可能性的库。

另请注意,您永远不知道哪个小应用程序或库可能会变成更大的东西。 :)

  

展望未来,模块化v。类路径程序是否会对性能产生影响?

在构建模块图并验证模块成本时,模块系统应该使用改进的类加载策略来构建它:它记录每个模块导出哪个模块并直接从该模块加载来自该模块的类型而不是扫描整个类路径。无论哪种方式,我认为这不应该是一个决定因素。

答案 2 :(得分:0)

发现此链接提供信息 http://www.javaworld.com/article/2878952/java-platform/modularity-in-java-9.html

  

JAR文件不够模块化吗?

     

JAR文件及其运行的部署环境   改进了许多其他可用的遗留部署约定。   但JAR文件除了很少使用之外没有内在的独特性   版本号,隐藏在.jar清单中。 JAR文件和   可选的清单不用作其中的模块化约定   Java运行时环境。所以类的包名称在   文件和他们参与类路径是唯一的部分   JAR结构,为运行时环境提供模块化。

     

简而言之,JAR是模块化的一个很好的尝试,但他们没有   满足真正模块化环境的所有要求。   像Spring和OSGi这样的框架和平台使用模式和   增强JAR规范以提供环境   建立非常强大的模块化系统。然而,随着时间的推移,甚至   这些工具将屈服于JAR非常不幸的副作用   规范JAR地狱!

     

Classpath / JAR地狱

     

当Java运行时环境允许任意复杂的JAR时   加载机制,开发人员知道他们在classpath地狱或JAR   地狱。许多配置都可能导致这种情况。

     

首先,考虑Java应用程序开发人员的情况   提供应用程序的更新版本并将其打包   与旧版本完全相同的JAR文件。 Java   运行时环境不提供用于确定的验证工具   正确的JAR文件。运行时环境将简单地加载类   从它首先找到的JAR文件或满足其中一个的JAR文件   类路径规则。这最多会导致出乎意料的行为。

     

JAR地狱的另一个例子出现在两个或更多应用程序或   进程依赖于第三方库的不同版本。运用   标准的类加载工具,只有一个版本的第三方   库将在运行时可用,至少会导致错误   一个申请或流程。

     

功能齐全且高效的Java模块系统应该很方便   将代码分离成不同的,易于理解的和松散的   耦合模块。应严格明确规定依赖关系   强制执行。应该提供允许模块的设施   升级而不会对其他模块产生负面影响。模块化   运行时环境应该启用特定于的配置   特定的域或垂直市场,从而减少启动时间   和系统的环境足迹。

     

Java的模块化解决方案

     

随着迄今为止提到的模块化功能,最近的努力   再添加一些。以下功能旨在进行优化   性能并启用扩展运行时环境:

     

分段源代码:   源代码分为不同的缓存段,每个段都有   包含特定类型的编译代码。其目标包括   在垃圾清扫过程中跳过非方法代码,增量构建,   更好的记忆管理。

     

构建时强制执行:用于强制命名空间的语言构造,   版本控制,依赖关系等。

     

部署设施支持   用于根据特定需求部署扩展的运行时环境,   例如移动设备环境的那些