安辰

stay hungry stay foolish

JShell是什么?

引入JDK官方的Summary

Provide an interactive tool to evaluate declarations, statements, and expressions of the Java programming language, together with an API so that other applications can leverage this functionality.

上两篇已经深入分析了Java9新特性系列(深入理解模块化),以及Java9新特性系列(module&maven&starter),有读者又提到了与模块化相关的spi,本篇将进行分析。

SPI是什么?

提到SPI呢,就不得不提一下API:

API:Application Programming Interface,即应用程序编程接口,在程序外部进行调用

SPI:Service Provider Interface,服务提供商接口

SPI核心思想是什么?

我们知道,一个系统中会有很多模块,比如数据库模块、日志模块、调度模块、各种业务模块等等,每一类的模块都有很多种实现,
数据库可以用mysql、oracle等,日志可以用log4j、logback等,那么对于不同的场景有不同的选型,如何能做到可插拔呢,那就是SPI了。

可插拔原则可以理解为系统与插件的关系,系统提供了一些接口,第三方插件进行实现。

面向接口编程,不绑定实现,为了在模块装配的时候不在代码中动态去指定具体的实现,就需要去发现具体的实现,即服务发现,其实就类似于回调,只不过回调的时候需要找到具体的实现,spi就帮我们做了去寻找实现的工作。

这一思想在模块化设计中尤为重要。

SPI实现方式?

SPI具体的实现方式分两种:

  • 应用系统自身提供默认实现
  • 第三方提供实现

上篇已经深入分析了Java9中的模块化,有读者又提到了module与starter是什么关系?本篇将进行分析。

首先先回顾下module与maven/gradle的关系:

module与maven/gradle是什么关系?

模块化的依赖关系,很容易让人联想到mven和gradle,这个在上篇中也提及,后来有读者也提出module和maven是什么关系?解答如下:

Maven 有两个主要的特征:依赖管理和构建管理。
依赖管理即可以决定库中的版本并从仓库中下载下来。
构建管理即管理开发过程中的任务,包括初始化、编译、测试、打包等。

Module是系统内置用于表述组件之间的关系,对于版本的管理还是处于最原始的状体,管理一种强制的依赖关系。

总结一下:Maven还是主要负责构建管理,Modules 对于像Maven这样的构建工具(build tools)来说扮演的是辅助补充的角色。因为这些构建工具在构建时建立的依赖关系图谱和他们版本可以根据Module来创建,Module强制确定了module和artifacts之间的依赖关系,而Maven对于依赖并非是强制的。
具体可参考StackOverflow上的一篇问答:Project Jigsaw vs Maven on StackOverflow

前两篇文章介绍了Java9新特性系列JDK与JRE以及模块化系统: Jigsaw->Modularity,本篇我们将深入理解模块化。

模块化如何体现?

如下图所示,Jdk8与Jdk9的目录结构,这个在之前的jdk与jre的文章已经提及。

从上面两张图对比可以发现:
JDK8:
在Jdk8中有两个重要的jar,即rt.jar与tools.jar:

在Jdk8中有jre,在jre/lib目录中有一个rt.jar(大小约64M),即rutime,提供了运行环境所用到的一些类库;在lib目录有一个tools.jar(大小约17M),是java中最基本的包,里面包含了从java中最重要的lang包到各种高级功能如可视化swing的包。

JDK9:
JDK9中没有jre,没有rt.jar,没有tools.jar,都是一个一个模块

总结:Java8其实是一个单体模式,一个简单的HelloWorld,都需要100多M的JRE环境,Java9引入模块后,模块之间依赖关系更加清晰,只需引用需要的模块。

模块化的前时代

Ant时代
相信大家对Ant都不陌生,Ant是任务型的,定义了一系列的任务dir/compile/jar等等,缺点是操作文件
Maven时代
Maven/Gradle相对于Ant,增加了groupId/artifactId,版本管理,依赖管理
OSGI时代
OSGI用的比较少,估计大家比较陌生,其实我们用的Eclipse及插件都是OSGI编译的

那么问题来了:当代码库越来越大,怎么管理类库交叉依赖,以及类重复的问题呢?

0%