Soul网关源码学习06

Soul网关源码学习06

Soul插件

在soul网关中每个请求,都会通过责任链的方式执行相匹配的插件,所以插件也是soul网关的核心,soul网关的插件是可插拔的,并且是插件之间依赖关系是松耦合且插件的功能实现高聚合,其次用户可根据需求定制插件满足自己的需求。

SoulConfiguration

soul插件配置类,使用 spring.factories 加载该配置。

@Bean("webHandler")
public SoulWebHandler soulWebHandler(final ObjectProvider<List<SoulPlugin>> plugins) {
    List<SoulPlugin> pluginList = plugins.getIfAvailable(Collections::emptyList);
    //对所有插件进行排序
    final List<SoulPlugin> soulPlugins = pluginList.stream()
            .sorted(Comparator.comparingInt(SoulPlugin::getOrder)).collect(Collectors.toList());
    //输出所有加载的插件
    soulPlugins.forEach(soulPlugin -> log.info("load plugin:[{}] [{}]", soulPlugin.named(), soulPlugin.getClass().getName()));
    return new SoulWebHandler(soulPlugins);
}

1、ObjectProvider 使用更宽松的方式注入SoulPlugin。
2、对所有插件进行排序,输出所有加载的插件。
3、创建SoulWebHandler对接,构造方法传递所有插件。

SoulPlugin

所有的插件实现SoulPlugin类,并重载对应的方法。

//执行插件
Mono<Void> execute(ServerWebExchange exchange, SoulPluginChain chain);
//排序
int getOrder();
//插件名
default String named() {
    return "";
}
//是否终止
default Boolean skip(ServerWebExchange exchange) {
    return false;
}

//Hystrix 插件配置
@Bean
public SoulPlugin hystrixPlugin() {
return new HystrixPlugin();
}
//WebSocket插件配置
@Bean
public SoulPlugin webSocketPlugin(WebSocketClient webSocketClient, WebSocketService webSocketService) {
return new WebSocketPlugin(webSocketClient, webSocketService);
}
//dubbo插件
@Bean
public SoulPlugin apacheDubboPlugin(ObjectProvider<DubboParamResolveService> dubboParamResolveService) {
    return new ApacheDubboPlugin(new ApacheDubboProxyService(dubboParamResolveService.getIfAvailable()));
}

SoulWebHandler

执行插件通过责任链的方式。

@Override
public Mono<Void> handle(@NonNull final ServerWebExchange exchange) {
    MetricsTrackerFacade.getInstance().counterInc(MetricsLabelEnum.REQUEST_TOTAL.getName());
    Optional<HistogramMetricsTrackerDelegate> startTimer = 	MetricsTrackerFacade.getInstance().histogramStartTimer(MetricsLabelEnum.REQUEST_LATENCY.getName());
    //责任链调用插件
    return new DefaultSoulPluginChain(plugins).execute(exchange).subscribeOn(scheduler).doOnSuccess(t -> startTimer.ifPresent(time -> MetricsTrackerFacade.getInstance().histogramObserveDuration(time)));
}

public Mono<Void> execute(final ServerWebExchange exchange) {
    return Mono.defer(() -> {
        if (this.index < plugins.size()) {
            //从集合中获取当前插件
            SoulPlugin plugin = plugins.get(this.index++);
            Boolean skip = plugin.skip(exchange);
            //判断是否中断本次执行
            if (skip) {
                return this.execute(exchange);
            }
            return plugin.execute(exchange, this);
        }
        return Mono.empty();
    });
}
已标记关键词 清除标记
相关推荐
©️2020 CSDN 皮肤主题: 编程工作室 设计师:CSDN官方博客 返回首页