Is your feature request related to a problem? Please describe.
There are dozens of clients in our project to access resources of other services, we use FeignClient to manage these clients.but some services have special rules,I'm always frustrated when a uri like this:
/api/v3/method?created_after=1990-10-23T07:20:42%2B0800
was encoded to
/api/v3/method?created_after=1990-10-23T07%3A20%3A42%252B0800
since server expect /api/v3/method?created_after=1990-10-23T07:20:42%2B0800, and will return 404 if the url encoded.
Describe the solution you'd like I traced the code stack and found that the UriTemplate is constructed with EncodingOptions.REQUIRED
private UriTemplate(String template, boolean encodeSlash, Charset charset) {
super(template, ExpansionOptions.REQUIRED, EncodingOptions.REQUIRED, encodeSlash, charset);
}
thus, there has no way to change the UriTemplate.
so i'd like a solution that the UriTemplate constuctor with EncodingOptions can be configured.
Describe alternatives you've considered there are other alternatives to avoid the problem.but not very elegant. 1.since uri was encoded defaultly,I have to decode the special words back in a RequestInterceptor of the configuration class.
public void apply(RequestTemplate template) {
String url = template.url();
String s = url.replaceAll("%3A", ":").replaceAll("%25", "%");
//...if there are more
template.uri(s);
}
2.try another way,use spring RestTemplate with. But It's inconsistent with my other clients.
DefaultUriBuilderFactory factory = new DefaultUriBuilderFactory();
factory.setEncodingMode(DefaultUriBuilderFactory.EncodingMode.NONE);
factory.expand(url);
Comment From: cbezmen
Hi @yinwuzhe ,
I think you can solve your problem with request interceptor. Please check the code below
@Configuration
public class CustomConfiguration {
@Bean
public RequestInterceptor customInterceptor() {
return template -> {
// Do your custom encoding/decoding to solve your problem.
};
}
}
@FeignClient(name = "testClient", configuration = CustomConfiguration.class)
public interface TestClient {
}
Comment From: OlgaMaciaszek
@yinwuzhe That UriTemplate constructor is part of the Feign-Core project, not Spring Cloud OpenFeign, so we will not be able to help with this. However, the workaround provided by @cbezmen should work. Please let us know if that's helpful.
Comment From: spring-cloud-issues
If you would like us to look at this issue, please provide the requested information. If the information is not provided within the next 7 days this issue will be closed.
Comment From: spring-cloud-issues
Closing due to lack of requested feedback. If you would like us to look at this issue, please provide the requested information and we will re-open the issue.
Comment From: yinwuzhe
@yinwuzhe That
UriTemplateconstructor is part of the Feign-Core project, not Spring Cloud OpenFeign, so we will not be able to help with this. However, the workaround provided by @cbezmen should work. Please let us know if that's helpful.
got it.
Comment From: yinwuzhe
Hi @yinwuzhe ,
I think you can solve your problem with request interceptor. Please check the code below
```java @Configuration public class CustomConfiguration { @Bean public RequestInterceptor customInterceptor() { return template -> { // Do your custom encoding/decoding to solve your problem. }; } }
@FeignClient(name = "testClient", configuration = CustomConfiguration.class) public interface TestClient {
} ```
thanks. sorry I'm late . As I said,this is about UriTemplate(in the feign core), which is private and opened only with some create functions,
private UriTemplate(String template, boolean encodeSlash, Charset charset) {
super(template, ExpansionOptions.REQUIRED, EncodingOptions.REQUIRED, encodeSlash, charset);
}
public static UriTemplate create(String template, Charset charset) {
return new UriTemplate(template, true, charset);
}
Fortunately,I resolved this by some character replaces on the way like you said,but can not be elegant,just setting custom encoding/decoding. ```java class CustomConfig implements RequestInterceptor {
@Override
public void apply(RequestTemplate template) {
String url = template.url();
String s = url.replaceAll("%3A", ":").replaceAll("%25", "%");
template.uri(s);
}```