Skip to content

The ClassCastException for org.springframework.http.HttpHeaders instance in feign.Contract #655

Description

@Alykoff

Hello,
I updated my project to Spring Boot 2. Feign library was migrated from version 9.5.0 to 9.5.1 in Spring Boot 2. And now my feign version is 9.5.1 and my spring boot app failed.

I'm using org.springframework.http.HttpHeaders class and have ClassCastException.
If change HttpHeaders to java.util.Map everything is ok.

Stacktrace:

Caused by: java.lang.ClassCastException: java.lang.Class cannot be cast to java.lang.reflect.ParameterizedType
	at feign.Contract$BaseContract.checkMapString(Contract.java:137) ~[feign-core-9.5.1.jar:na]
	at feign.Contract$BaseContract.parseAndValidateMetadata(Contract.java:124) ~[feign-core-9.5.1.jar:na]
	at org.springframework.cloud.openfeign.support.SpringMvcContract.parseAndValidateMetadata(SpringMvcContract.java:133) ~[spring-cloud-openfeign-core-2.0.0.M1.jar:2.0.0.M1]
	at feign.Contract$BaseContract.parseAndValidatateMetadata(Contract.java:66) ~[feign-core-9.5.1.jar:na]
	at feign.hystrix.HystrixDelegatingContract.parseAndValidatateMetadata(HystrixDelegatingContract.java:34) ~[feign-hystrix-9.5.1.jar:na]
	at feign.ReflectiveFeign$ParseHandlersByName.apply(ReflectiveFeign.java:146) ~[feign-core-9.5.1.jar:na]
	at feign.ReflectiveFeign.newInstance(ReflectiveFeign.java:53) ~[feign-core-9.5.1.jar:na]
	at feign.Feign$Builder.target(Feign.java:218) ~[feign-core-9.5.1.jar:na]

The problem appeared from that commit a029afd

feign.Contract.java:
// 137 line
Type[] parameterTypes = ((ParameterizedType) genericType).getActualTypeArguments();

My app:

public interface GraphQLClient {
    @RequestMapping(value = "/graphql/d", method = RequestMethod.POST)
    ExecutionResultWrapper execute(@RequestBody QueryWrapper queryWrapper, @RequestHeader HttpHeaders httpHeaders);
}
import own.DefaultFeignConfiguration;
import own.CustomErrorDecoder;
import feign.Client;
import feign.Target;
import feign.hystrix.HystrixFeign;
import feign.slf4j.Slf4jLogger;
import org.springframework.beans.factory.ObjectFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.http.HttpMessageConverters;
import org.springframework.cloud.netflix.ribbon.SpringClientFactory;
import org.springframework.cloud.openfeign.ribbon.CachingSpringLoadBalancerFactory;
import org.springframework.cloud.openfeign.ribbon.LoadBalancerFeignClient;
import org.springframework.cloud.openfeign.support.ResponseEntityDecoder;
import org.springframework.cloud.openfeign.support.SpringDecoder;
import org.springframework.cloud.openfeign.support.SpringEncoder;
import org.springframework.cloud.openfeign.support.SpringMvcContract;
import org.springframework.stereotype.Component;

@Component
public class ClientBuilder {
    // ...
    public <T> T buildClient(Class<T> targetInterface, String prefix, String url) {
        Target<T> custom = new Target.HardCodedTarget<>(targetInterface, url, prefix + url);
        T target = HystrixFeign.builder()
                .contract(new SpringMvcContract())
                .options(feignConfig.options())
                .logger(new Slf4jLogger())
                .logLevel(feignConfig.level())
                .client(
                        new LoadBalancerFeignClient
                                (new Client.Default(null, null), cachingFactory, clientFactory)
                )
                .decoder(new ResponseEntityDecoder(new SpringDecoder(messageConverters)))
                .encoder(new SpringEncoder(messageConverters))
                .errorDecoder(customErrorDecoder)
                .target(custom); // failed in this method
        return target;
    }
}

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Fields

    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions