解决微服务feign调用添加token的问题

网友投稿 1661 2023-01-02

解决微服务feign调用添加token的问题

解决微服务feign调用添加token的问题

微服务feign调用添加token

1.一般情况是这么配置

具体的怎么调用就不说了 如下配置,就可以在请求头中添加需要的请求头信息。

package localdate;

import feign.RequestInterceptor;

import feign.RequestTemplate;

import lombok.extern.slf4j.Slf4j;

import org.springframework.beans.factory.annotation.Autowired;

import org.springframework.context.annotation.Configuration;

import org.springframework.stereotype.Component;

import org.springframework.web.context.request.RequestAttributes;

import org.springframework.web.context.request.RequestContextHolder;

import org.springframework.web.context.request.ServletRequestAttributes;

import javax.servlet.http.HttpServletRequest;

import java.util.Collection;

import java.util.Enumeration;

import java.util.Iterator;

import java.util.Map;

/**

* feign调用服务时,会丢失请求头信息。需要在这里把认证信息收到添加上去

* @author TRON

* @since 2019-11-23

*

*

*/

@Configuration

@Slf4j

public class FeignTokenInterceptor implements RequestInterceptor {

@Override

public void apply(RequestTemplate requestTemplate) {

log.info("======上下文中获取原请求信息======");

String token = "without token";

HttpServletRequest request = ((ServletRequestAttributes)

RequestContextHolder.getRequestAttributes()).getRequest();

Enumeration headerNames = request.getHeaderNames();

while (headerNames.hasMoreElements()) {

String headerName = headerNames.nextElement();

String HeadValue = request.getHeader(headerName);

log.info("===原请求头信息=== headName: {}, headValue: {}", headerName, HeadValue);

if (headerName.equals("X-Authorization-access_token")||headerName.equals("x-authorization-access_token")) {

token = HeadValue;

}

}

log.info("=======Feign添加头部信息start======");

// requestTemplate.header("X-Authorization-access_token", token);

requestTemplate.header("X-Authorization-access_token", "tron123456");

log.info("=======Feign添加头部信息end======");

}

}

2 .但是,当熔断开启后,原先的这么配置就不起作用了

package localdate;

import com-flix.hystrix.HystrixThreadPoolKey;

import com-flix.hystrix.strategy.HystrixPlugins;

import com-flix.hystrix.strategy.concurrency.HystrixConcurrencyStrategy;

import com-flix.hystrix.strategy.concurrency.HystrixRequestVariable;

import com-flix.hystrix.strategy.concurrency.HystrixRequestVariableLifecycle;

import com-flix.hystrix.strategy.eventnotifier.HystrixEventNotifier;

import com-flix.hystrix.strategy.executionhook.HystrixCommandExecutionHook;

import com-flix.hystrix.strategy.metrics.HystrixMetricsPublisher;

import com-flix.hystrix.strategy.properties.HystrixPropertiesStrategy;

import com-flix.hystrix.strategy.properties.HystrixProperty;

import org.slf4j.Logger;

import org.slf4j.LoggerFactory;

import org.springframework.context.annotation.Configuration;

import org.springframework.web.context.request.RequestAttributes;

import org.springframework.web.context.request.RequestContextHolder;

import java.util.concurrent.BlockingQueue;

import java.util.concurrent.Callable;

import java.util.concurrent.ThreadPoolExecutor;

import java.util.concurrent.TimeUnit;

/**

* 自定义并发策略

* 将现有的并发策略作为新并发策略的成员变量

* 在新并发策略中,返回现有并发策略的线程池、Queue

*

* hystrix.command.default.execution.isolation.strategy=THREAD

* Hystrix的默认隔离策略(官方推荐,当使用该隔离策略时,是没办法拿到 ThreadLocal 中的值的,但是RequestContextHolder 源码中,使用了两个ThreadLocal)

* hystrix.command.default.execution.isolation.strategy=SEMAPHORE (将隔离策略改为SEMAPHORE 也可以解决这个问题,但是官方并不推荐这个策略,因为这个策略对网络资源消耗比较大)

*

* 主要是解决当 Hystrix的默认隔离策略是THREAD时,不能通过RequestContextHolder获取到request对象的问题

*

*/

//@Configuration

public class FeignConfig extends HystrixConcurrencyStrategy {

private static final Logger log = LoggerFactory.getLogger(FeignConfig.class);

private HystrixConcurrencyStrategy delegate;

public FeignConfig() {

try {

this.delegate = HystrixPlugins.getInstance().getConcurrencyStrategy();

if (this.delegate instanceof FeignConfig) {

// Welcome to singleton hell...

return;

}

HystrixCommandExecutionHook commandExecutionHook =

HystrixPlugins.getInstance().getCommandExecutionHook();

HystrixEventNotifier eventNotifier = HystrixPlugins.getInstance().getEventNotifier();

HystrixMetricsPublisher metricsPublisher = HystrixPlugins.getInstance().getMetricsPublisher();

HystrixPropertiesStrategy propertiesStrategy =

HystrixPlugins.getInstance().getPropertiesStrategy();

this.logCurrentStateOfHystrixPlugins(eventNotifier, metricsPublisher, propertiesStrategy);

HystrixPlugins.reset();

HystrixPlugins.getInstance().registerConcurrencyStrategy(this);

HystrixPlugins.getInstance().registerCommandExecutionHook(commandExecutionHook);

HystrixPlugins.getInstance().registerEventNotifier(eventNotifier);

HystrixPlugins.getInstance().registerMetricsPublisher(metricsPublisher);

HystrixPlugins.getInstance().registerPropertiesStrategy(propertiesStrategy);

} catch (Exception e) {

log.error("Failed to register Sleuth Hystrix Concurrency Strategy", e);

}

}

private void logCurrentStateOfHystrixPlugins(HystrixEventNotifier eventNotifier,

HystrixMetricsPublisher metricsPublisher, HystrixPropertiesStrategy propertiesStrategy) {

if (log.isDebugEnabled()) {

log.debug("Current Hystrix plugins configuration is [" + "concurrencyStrategy ["

+ thttp://his.delegate + "]," + "eventNotifier [" + eventNotifier + "]," + "metricPublisher ["

+ metricsPublisher + "]," + "propertiesStrategy [" + propertiesStrategy + "]," + "]");

log.debug("Registering Sleuth Hystrix Concurrency Strategy.");

}

}

@Override

public Callable wrapCallable(Callable callable) {

RequestAttributes requestAttributes = RequestContextHolder.getRequestAttributes();

return new WrappedCallable<>(callable, requestAttributes);

}

@Override

public ThreadPoolExecutor getThreadPool(HystrixThreadPoolKey threadPoolKey,

HystrixProperty corePoolSize, HystrixProperty maximumPoolSize,

HystrixProperty keepAliveTime, TimeUnit unit, BlockingQueue workQueue) {

return this.delegate.getThreadPool(threadPoolKey, corePoolSize, maximumPoolSize, keepAliveTime,

unit, workQueue);

}

@Override

public BlockingQueue getBlockingQueue(int maxQueueSize) {

return this.delegate.getBlockingQueue(maxQueueSize);

}

@Override

public HystrixRequestVariable getRequestVariable(HystrixRequestVariableLifecycle rv) {

return this.delegate.getRequestVariable(rv);

}

static class WrappedCallable implements Callable {

private final Callable target;

private final RequestAttributes requestAttributes;

public WrappedCallable(Callable target, RequestAttributes requestAttributes) {

this.target = target;

this.requestAttributes = requestAttributes;

}

@Override

public T call() throws Exception {

try {

RequestContextHolder.setRequestAttributes(requestAttributes);

return target.call();

} finally {

RequestContextHolder.resetRequestAttributes();

}

}

}

}

3 .feign和熔断的配置

feign:

client:

config:

default:

connectTimeout: 5000 #连接超时3秒,连接失败时直接调用降级方法

readTimeout: 100000 #连接成功,处理数据的时间限制10秒 100000 读取时间过短会抛异常java-.SocketTimeoutException: Read timed out

loggerLevel: full #日志输出等级

hystrix:

enabled: true

hystrix:

command:

default:

execution:

isolation:

thread:

timeoutInMilliseconds: 5000 #服务连接成功,但是时间过长,降级方法调用时间 60000 5000

feign微服务的相互调用

我只是记录服务提供方、消费方的代码编写,配置什么的大家在网上搜,一大堆。

首先是服务提供方:

启动类上加上注解@EnableFeignClients,然后正常的写controller、service等业务逻辑

其次是服务的调用方:

1.首先启动类上加上注解@EnableFeignClients

2.编写服务调用接口

3.编写接口熔断处理方法

4.本人遇到的问题是需要用到调用方的请求头里面的信息,但是在提供方取不到,这时可以通过在调用方增加配置来解决

import feign.RequestInterceptor;

import feign.RequestTemplate;

import java.util.Enumeration;

import javax.servlet.http.HttpServletRequest;

import org.springframework.web.context.request.RequestContextHolder;

import org.springframework.web.context.request.ServletRequestAttributes;

/**

* @author ydf

* @date 2021/5/13

* @description:

**/

public class FeignBasicAuthRequestInterceptor implemenhttp://ts RequestInterceptor {

@Override

public void apply(RequestTemplate requestTemplate) {

ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder

.getRequestAttributes();

HttpServletRequest request = attributes.getRequest();

Enumeration headerNames = request.getHeaderNames();

if (headerNames != null) {

while (headerNames.hasMoreElements()) {

String name = headerNames.nextElement();

String values = request.getHeader(name);

requestTemplate.header(name, values);

}

}

}

}

import com.jingling-sign.applet.interceptor.FeignBasicAuthRequestInterceptor;

import feign.RequestInterceptor;

import org.springframework.context.annotation.Bean;

import org.springframework.context.annotation.Configuration;

/**

* @author ydf

* @date 2021/5/13

* @description:

**/

@Configuration

public class FeignSupportConfig {

/**

* feign请求-

*

* @return

*/

@Bean

public RequestInterceptor requestInterceptor(){

return new FeignBasicAuthRequestInterceptor();

}

}

版权声明:本文内容由网络用户投稿,版权归原作者所有,本站不拥有其著作权,亦不承担相应法律责任。如果您发现本站中有涉嫌抄袭或描述失实的内容,请联系我们jiasou666@gmail.com 处理,核实后本网站将在24小时内删除侵权内容。

上一篇:延安企业app开发(延安企业app开发)
下一篇:vue 微信小程序组件(基于vue的微信小程序)
相关文章

 发表评论

暂时没有评论,来抢沙发吧~