springfox原理

启动执行
springfox-spring-web


springfox大致原理
springfox的大致原理就是,在项目启动的过种中,spring上下文在初始化的过程,框架自动跟据配置加载一些swagger相关的bean到当前的上下文中,并自动扫描系统中可能需要生成api文档那些类,并生成相应的信息缓存起来。如果项目MVC控制层用的是springMvc那么会自动扫描所有Controller类,跟据这些Controller类中的方法生成相应的api文档。

第一个ApiListingBuilderPlugin,它有两个实现类,分别是ApiListingReader和SwaggerApiListingReader。其中ApiListingReader会自动跟据Controller类型生成api列表,而SwaggerApiListingReader会跟据有@Api注解标识的类生成api列表。OperationBuilderPlugin插件就是用来生成具体api文档的,这个类型的插件,有很多很多实现类,他们各自分工,各做各的事情,具体我没有仔细去看,只关注了其中一个实现类:OperationParameterReader,这个类是用于读取api参数的Plugin。它依赖于ModelAttributeParameterExpander工具类,可以将Controller中接口方法参数中非简单类型的命令对像自动解析它内部的属性得出包含所有属性的参数列表(这里存在一个可能会出现无限递归的坑,下文有介绍)。而ExpandedParameterBuilderPlugin插件,主要是用于扩展接口参数的一些功能,比如判断这个参数的数据类型以及是否为这个接口的必须参数等等。总体上说,整个springfox-swagger内部其实是由这一系列的plug转运起来的。他们在系统启动时,就被调起来,有些用来扫描出接口列表,有些用来读取接口参数等等。他们共同的目地就是把系统中所有api接口都扫描出来,并缓存起来供用户查看。那么,这一系列表plug到底是如何被调起来的,它们的执行入口倒底在哪?

我们把注意点放到上文SpringfoxWebMvcConfiguration这个类代码头部的ComponentScan注解内容上来,这一段注解中扫描了一个叫springfox.documentation.spring.web.plugins的package,这个package在springfox-spring-web-2.6.1.jar中可以找到。
这个package下,我们发现有两个非常核心的类,那就是DocumentationPluginsManager和DocumentationPluginsBootstrapper。对于第一个DocumentationPluginsManager,它是一个没有实现任何接口的bean,但它内部有诸多PluginRegistry类型的属性,而且都是通过@Autowired注解把属性值注入进来的。接合它的类名来看,很容易想到,这个就是管理所有plug的一个管理器了。很好理解,因为ComponentScan注解的配置,所有的plug实例都会被spring实例化成一个bean,然后被注入到这个DocumentationPluginsManager实例中被统一管理起来。在这个package中的另一个重要的类DocumentationPluginsBootstrapper,看名字就可以猜到,他可能就是plug的启动类了。点进去看具体时就可以发现,他果然是一个被@Component标识了的组件,而且它的构造方法中注入了刚刚描述的DocumentationPluginsManager实例,而且最关键的,它还实现了SmartLifecycle接口。对spring bean生命周期有所了解的人的都知道,这个组件在被实例化为一个bean纳入srping context中被管理起来的时候,会自动调用它的start()方法。点到start()中看代码时就会发现,它有一行代码scanDocumentation(buildContext(each));就是用来扫描api文档的。进一步跟踪这个方法的代码,就可以发现,这个方法最终会通过它的DocumentationPluginsManager属性把所有plug调起一起扫描整个系统并生成api文档。扫描的结果,缓存在DocumentationCache这个类的一个map属性中。


srpingMvc整合springfox的大致原理。
它主要是通过EnableSwagger2注解,向spring context注入了一系列bean,并在系统启动的时候自动扫描系统的Controller类,生成相应的api信息并缓存起来。
此外,它还注入了一些被@Controller注解标识的Controller类,作为ui模块访问api列表的入口。比如springfox-swagger2-2.6.1.jar包中的Swagger2Controller类。这个Controller就是ui模块中用来访问api列表的界面地址。
在访问http://127.0.0.1:8080/jadDemo/swagger-ui.html这个地址查看api列表时,通过浏览器抓包就可以看到,它是通过类似于http://127.0.0.1:8080/jadDemo/v2/api-docs?group=sysGroup这样的地址异步获得api信息(Json格式)并显示到界面上,这个地址后台对应的Controller入口就是上文的Swagger2Controller类,这个类收到请求后,直接从事先初始化好的缓存中的取出api信息生成json字符串返回。

原文地址:https://www.cnblogs.com/wueryuan/p/14931002.html