SpringBoot访问HTTP链接:java.lang.IllegalStateException: No instances available for......

使用RestTemplate访问带有完整参数的外部GET链接,出现以下报错。

java.lang.IllegalStateException: No instances available for **********
at org.springframework.cloud.netflix.ribbon.RibbonLoadBalancerClient.execute(RibbonLoadBalancerClient.java:79)
at org.springframework.cloud.client.loadbalancer.LoadBalancerInterceptor.intercept(LoadBalancerInterceptor.java:46
at org.springframework.http.client.InterceptingClientHttpRequest$InterceptingRequestExecution.execute(InterceptingClientHttpRequest.java:86) 
at org.springframework.http.client.InterceptingClientHttpRequest.executeInternal(InterceptingClientHttpRequest.java:70) 

往上查了很多资料,说是RestTemplate,调用到了内网,如下


import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.client.RestTemplate;

/**
 * 描述: 
 * @since 2019年11月29日 下午10:20:04
 */
@Configuration
public class RestConfig {
    
    @Bean(name="defineRestTemplate")
    //@LoadBalanced //加上代表是在Eureka上去找服务,不能调用外网,也不能调用本地如:127.0.0.1
    public RestTemplate restTemplate() {
        return new RestTemplate();
    }

}

注入及使用:

    @Autowired
    @Qualifier(value = "defineRestTemplate") // 月一定要加上,不然找不到
    private RestTemplate restTemplate;

    public void test() {
		
        Object forObject = restTemplate.getForObject("完整的外部get链接,条件都已经拼凑好,返回为json", Object.class);

        System.out.println(forObject);

    }

调试时,又出现了403:Bad Request。

换下一个方式:使用使用feign调用的方式,由于完整的链接,连服务名称都找不到,自然是不行的。

最后还是Apache上找到了解决办法,Apache家族和Spring家族相比,就好比俄罗斯武器和西方国家武器,一个粗犷耐操,一个精细实用。同样的功能,肯定是优先使用Spring,Spring不行了再使用Apache。


            //(GET) 访问url,并返回结果Request:org.apache.http.client.fluent.Request
            String str = Request.Get(url).connectTimeout(Constant.NUMBER_1500).socketTimeout(Constant.NUMBER_1500).execute().returnContent().asString();

GET访问使用:

// Execute a GET with timeout settings and return response content as String.
Request.Get("http://somehost/")
        .connectTimeout(1000)
        .socketTimeout(1000)
        .execute().returnContent().asString();

POST访问时:

// Execute a POST with the 'expect-continue' handshake, using HTTP/1.1,
// containing a request body as String and return response content as byte array.
Request.Post("http://somehost/do-stuff")
        .useExpectContinue()
        .version(HttpVersion.HTTP_1_1)
        .bodyString("Important stuff", ContentType.DEFAULT_TEXT)
        .execute().returnContent().asBytes();

POST代理访问:

// Execute a POST with a custom header through the proxy containing a request body
// as an HTML form and save the result to the file
Request.Post("http://somehost/some-form")
        .addHeader("X-Custom-header", "stuff")
        .viaProxy(new HttpHost("myproxy", 8080))
        .bodyForm(Form.form().add("username", "vip").add("password", "secret").build())
        .execute().saveContent(new File("result.dump"));

对身份验证进行缓存访问:

Executor executor = Executor.newInstance()
        .auth(new HttpHost("somehost"), "username", "password")
        .auth(new HttpHost("myproxy", 8080), "username", "password")
        .authPreemptive(new HttpHost("myproxy", 8080));

executor.execute(Request.Get("http://somehost/"))
        .returnContent().asString();

executor.execute(Request.Post("http://somehost/do-stuff")
        .useExpectContinue()
        .bodyString("Important stuff", ContentType.DEFAULT_TEXT))
        .returnContent().asString();

Apache的东西真是让人又爱又恨,明明能够做出别人做不出来的东西,可偏偏不好好做。

需要访问外网API,若遇到问题可以参考以下Apache专门为HTTP访问开发的工具包,包名:org.apache.http.client.fluent.Request
使用方法及地址

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值