Mor*_*hai 12 java java-9 java-module module-info
Java的ServiceLoader类现在已经被正式编入Java语言.META-INF/services现在可以使用.而不是在寻找提供商
provides <spiClass> with <providerClass>
Run Code Online (Sandbox Code Playgroud)
我无法理解的是,uses在服务加载模块声明中的使用:
uses <spiClass>
Run Code Online (Sandbox Code Playgroud)
引用模块系统的状态
模块系统可以通过扫描模块工件中的类文件来识别
ServiceLoader::load方法的调用来识别服务的使用 ,但这既缓慢又不可靠.模块使用特定服务是该模块定义的一个基本方面,因此为了效率和清晰度,我们在模块的声明中用uses子句表示:module java.sql { requires transitive java.logging; requires transitive java.xml; exports java.sql; exports javax.sql; exports javax.transaction.xa; uses java.sql.Driver; }
为什么模块系统了解特定服务的使用是否至关重要,尤其是如何引入效率?是不是懒洋洋地加载服务?为什么服务加载器不能直接寻找提供商?
引用Java 9 javadoc的ServiceLoader(重点是我添加的):
应用程序通过调用 ServiceLoader 的静态方法之一来获取给定服务的服务加载器
load。如果应用程序是一个模块,那么它的模块声明必须有一个uses指令来指定服务;这有助于找到提供商并确保他们可靠地执行。另外,如果服务不在应用程序模块中,则模块声明必须有一个requires指令来指定导出该服务的模块。
为什么模块系统知道特定服务的使用是至关重要的......
因为依赖性解析. 模块系统的状态在示例中说出了引用文本上方的几行:
为了使
java.sql模块能够使用这个驱动程序,ServiceLoader该类必须能够通过反射实例化驱动程序类; 要实现这一点,模块系统必须将驱动程序模块添加到模块图并解决其依赖关系......
关键是反射用于进行实例化.它发生在模块解析后......以及应用程序开始运行之后.
......特别是如何引入效率?
扫描所有呼叫的代码库ServiceLoader::load是很昂贵的.仅知道调用方法是不够的(可以通过分析类文件依赖性来完成).您还需要知道使用了哪些参数来确定要加载的类.而且(正如SotMS文件所指出的那样)会容易出错; 例如,如果参数是运行时表达式而不是编译时常量表达式.
他们采用的解决方案是提供一种显式声明对反射加载类的依赖的方法.
当JVM启动时,模块系统解析依赖关系并构建模块图.只有运行时才能进入图表的模块(即使其他模块可以观察到).如果通过服务正确地解耦模块,那么提供模块很可能不是初始模块的传递依赖性.因此,如果没有进一步的努力,服务提供者模块通常不会进入模块图,因此在模块尝试使用服务时不能在运行时使用.
为了使
java.sql模块能够使用该驱动程序,模块系统必须将驱动程序模块添加到模块图并解决其依赖性[...].
因此,对于正常工作的服务,提供者模块必须将其放入模块图中,即使它们不是初始模块中的传递要求.但是,模块系统如何识别需要哪些模块作为服务提供商?所有使用provides条款?那会有点太多了.不,只应解决实际需要的服务提供商.
这使得有必要识别服务使用.正如其他人所指出的那样,字节码分析速度慢且不可靠,因此需要更明确的机制来保证效率和正确性:uses条款.只有使用它们,模块系统才能可靠,高效地使所有服务提供商模块可用.
如果应用程序是一个模块,那么它的模块声明必须有一个
uses指定服务的指令; 这有助于找到提供者并确保他们可靠地执行.
如果使用标志启动基于服务的应用程序,则可以观察到此行为--show-module-resolution:
root monitor
monitor requires monitor.observer
[...]
monitor binds monitor.observer.beta
monitor binds monitor.observer.alpha
Run Code Online (Sandbox Code Playgroud)
模块监视器 绑定模块monitor.observer.alpha,monitor.observer.beta即使它不依赖于它们中的任何一个.
(行情来自模块系统的状态 ;强调我的.)
| 归档时间: |
|
| 查看次数: |
1131 次 |
| 最近记录: |