跨服务HTTP请求和响应

一次HTTP请求过程

  1. 构建请求对象:远程连接、网络请求等
  2. 执行远程调用:异常处理、状态码控制等
  3. 处理响应结果:数据结构转换

创建RestTemplate

RestTemplate优势:相较于传统Apache中的HttpClient客户端工具类,RestTemplate对于编码的简便性以及异常的处理等方面都做了很多改进。

无参构造函数

@Bean
public RestTemplate restTemplate(){

    return new RestTemplate();

}

有参构造函数

    @Bean
    RestTemplate customRestTemplate(){
        HttpComponentsClientHttpRequestFactory httpComponentsClientHttpRequestFactory = new HttpComponentsClientHttpRequestFactory();
        httpComponentsClientHttpRequestFactory.setConnectionRequestTimeout(3000);
        httpComponentsClientHttpRequestFactory.setConnectTimeout(3000);
        httpComponentsClientHttpRequestFactory.setReadTimeout(3000);
    }

RestTemplate 方法组 

  1. Get:getForObject/getForEntity
  2. Post: postForLocation/postForObject/postForEntity
  3. Put: put
  4. Delete: delete
  5. Header: headForHeaders
  6. 不限:exchange/execute

使用RestTemplate - get方法组

    @Nullable
    <T> T getForObject(String var1, Class<T> var2, Object... var3) throws RestClientException;

    @Nullable
    <T> T getForObject(String var1, Class<T> var2, Map<String, ?> var3) throws RestClientException;

    @Nullable
    <T> T getForObject(URI var1, Class<T> var2) throws RestClientException;

    <T> ResponseEntity<T> getForEntity(String var1, Class<T> var2, Object... var3) throws RestClientException;

    <T> ResponseEntity<T> getForEntity(String var1, Class<T> var2, Map<String, ?> var3) throws RestClientException;

    <T> ResponseEntity<T> getForEntity(URI var1, Class<T> var2) throws RestClientException;

getForEntity方法的返回值是一个ResponseEntity对象,在这个对象中还包含了HTTP消息头等信息,而getForObject方法返回的则是业务对象本身,这是两个方法组的主要区别。 

 使用RestTemplate - post方法组

 使用RestTemplate - exchange方法组

RestTemplate 技巧 

指定消息转换器:用于在获取返回结果时的数据转换

    @Bean
    RestTemplate customRestTemplate(){
        HttpComponentsClientHttpRequestFactory httpComponentsClientHttpRequestFactory = new HttpComponentsClientHttpRequestFactory();
        httpComponentsClientHttpRequestFactory.setConnectionRequestTimeout(3000);
        httpComponentsClientHttpRequestFactory.setConnectTimeout(3000);
        httpComponentsClientHttpRequestFactory.setReadTimeout(3000);
        RestTemplate restTemplate = new RestTemplate(httpComponentsClientHttpRequestFactory);
        ArrayList<HttpMessageConverter<?>> httpMessageConverters = new ArrayList<>();
        httpMessageConverters.add(new GsonHttpMessageConverter());
        restTemplate.setMessageConverters(httpMessageConverters);
        return restTemplate;
    }

 设置拦截器

@Bean
@ConditionalOnMissingBean
public RestTemplateCustomizer restTemplateCustomizer(

  //这段代码来自Spring Cloud 的 LoadBalanceAutoConfiguration
  //通过@LoadBalanced 注解为RestTemplate 自动添加负载均衡机制
  final LoadBalancerInterceptor loadBalancerInterceptor) {

    return restTemplate -> {

       List<ClientHttpRequestInterceptor> list = new ArrayList<>(restTemplate.getInterceptor());
       list.add(loadBalancerInterceptor);
        restTemplate.setInterceptors(list);

     }

}

通过实现ClientHttpRequestInterceptor接口,并调用setInterceptors方法可以将任意定义的拦截器注入到RestTemplate的拦截器列表中。 

处理异常

  @Bean
    RestTemplate customRestTemplate(){
        HttpComponentsClientHttpRequestFactory httpComponentsClientHttpRequestFactory = new HttpComponentsClientHttpRequestFactory();
        httpComponentsClientHttpRequestFactory.setConnectionRequestTimeout(3000);
        httpComponentsClientHttpRequestFactory.setConnectTimeout(3000);
        httpComponentsClientHttpRequestFactory.setReadTimeout(3000);
        RestTemplate restTemplate = new RestTemplate(httpComponentsClientHttpRequestFactory);
        ArrayList<HttpMessageConverter<?>> httpMessageConverters = new ArrayList<>();
        httpMessageConverters.add(new GsonHttpMessageConverter());
        restTemplate.setMessageConverters(httpMessageConverters);
        ResponseErrorHandler responseErrorHandler = new ResponseErrorHandler() {
            @Override
            public boolean hasError(ClientHttpResponse clientHttpResponse) throws IOException {
                return true;
            }

            @Override
            public void handleError(ClientHttpResponse clientHttpResponse) throws IOException {
                //添加定制化的异常
            }
        };
        restTemplate.setErrorHandler(responseErrorHandler);
        return restTemplate;
    }

在RestTemplate中,默认情况下当请求状态码不是返回200时就会抛出异常并中断接下来的操作,如果要排除这个处理过程就需要覆盖默认的ResponseErrorHandler。 

重试

 @Retryable(value = RestClientException.class,maxAttempts = 5,backoff = @Backoff(multiplier = 2,delay = 2000))
    public void learning(){

        restTemplate.getForObject("localhost:8080/helloword",String.class,1);
    }

需引入模块

 <dependency>
     <groupId>org.springframework.retry</groupId>
     <artifactId>spring-retry</artifactId>
 </dependency>

 主程序入口

@SpringBootApplication
@EnableRetry
public class LeariningApplication {

    public static void main(String[] args) {
        SpringApplication.run(LeariningApplication.class, args);
    }

}

使用示例

   @Retryable(value = RestClientException.class,maxAttempts = 5,backoff = @Backoff(multiplier = 2,delay = 2000))
    public void learning(){

        restTemplate.getForObject("localhost:8080/helloword",String.class,1);
    }
  • @Retryable注解的方法在发生异常时会重试,参数说明:
    • value:当指定异常发生时会进行重试 ,HttpClientErrorException是RestClientException的子类。
    • include:和value一样,默认空。如果 exclude也为空时,所有异常都重试 
    • exclude:指定异常不重试,默认空。如果 include也为空时,所有异常都重试 
    • maxAttemps:最大重试次数,默认3 
    • backoff:重试等待策略,默认空
  • @Backoff注解为重试等待的策略,参数说明:
    • delay:指定重试的延时时间,默认为1000毫秒
    • multiplier:指定延迟的倍数,比如设置delay=2000,multiplier=2时,第一次重试为2秒后,第二次为4秒,第三次为8秒。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
在Linux下使用C语言实现HTTP服务器,解析POST请求的过程可以分为以下几个步骤: 1. 接收客户端发送的HTTP请求:使用socket函数创建服务器套接字,并使用bind函数将套接字与服务器IP地址和端口号绑定,使用listen函数监听客户端的连接请求,使用accept函数接受客户端连接请求并返回一个新的套接字用于与客户端通信。 2. 解析HTTP请求报文:读取客户端发送的HTTP请求报文,根据请求报文的方法字段判断该请求是GET还是POST请求,如果是POST请求,需要解析请求头中的Content-Length字段获取HTTP请求体的长度。 3. 接收HTTP请求体:使用read函数读取HTTP请求体,需要循环读取直到读取到Content-Length指定的长度为止。 4. 解析HTTP请求体:根据Content-Type字段判断HTTP请求体的类型,如果是application/x-www-form-urlencoded类型,则需要解析请求体中的键值对;如果是multipart/form-data类型,则需要解析请求体中的文件数据。 5. 处理HTTP请求:根据请求的路径和参数等信息,调用相应的处理函数进行处理,并生成HTTP响应报文。 6. 发送HTTP响应:使用write函数将HTTP响应报文发送给客户端,关闭套接字,结束本次HTTP请求处理过程。 需要注意的是,解析POST请求时需要注意处理请求体的长度和类型,以及对不同类型的请求体进行正确的解析。此外,还需要防范POST请求中的恶意攻击,如SQL注入、站脚本攻击等。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值