SpringCloud中怎么利用Feign传输date类型参数

SpringCloud中怎么利用Feign传输date类型参数,很多新手对此不是很清楚,为了帮助大家解决这个难题,下面小编将为大家详细讲解,有这方面需求的人可以来学习下,希望你能有所收获。

创新互联自2013年起,是专业互联网技术服务公司,拥有项目做网站、成都网站建设网站策划,项目实施与项目整合能力。我们以让每一个梦想脱颖而出为使命,1280元猇亭做网站,已为上家服务,为猇亭各地企业和个人服务,联系电话:13518219792

一、Java Date类型的时差问题

请看下边这段代码

public static void main(String[] args) throws Exception {
    Date date1 = new Date();
    System.out.println("date1: " + date1.toString());
    Date date2 = new Date(date1.toString());
    System.out.println("date2: " + date2.toString());
}

执行结果如下

date1: Mon Jul 22 08:47:19 CST 2019
date2: Mon Jul 22 22:47:19 CST 2019

当前时间是2019年7月22日8点48分,CST是中国的时区China Standard Time的简称,但是可以看到date2的输入比实际时间多了14个小时。

CTS代表的时区其实有四个(Central Standard Time (USA) UT-6:00、Central Standard Time (Australia) UT+9:30、China Standard Time UT+8:00、Cuba Standard Time UT-4:00),同时表示美国,澳大利亚,中国,古巴四个国家的标准时间。

原因

new Date(date1.toString())

这个方法会调用Date.parse(String)方法,它传的参数是Mon Jul 22 08:47:19 CST 2019,这个方法上有一段注释

  • Any word that matches EST, CST, MST, or PST, *     ignoring case, is recognized as referring to the time zone in *     North America that is five, six, seven, or eight hours west of *     Greenwich, respectively. Any word that matches EDT, CDT, *     MDT, or PDT, ignoring case, is recognized as *     referring to the same time zone, respectively, during daylight *     saving time.

  • 可以看到CST会被当作美国中部的时区Central Standard Time,即JVM认为你传入的时间是美国中部的时间,而当date2调用toString方法的时候,它会检测到系统的时区是中国,就会自动加14个小时(东八区与西六区的时差),就变成了Mon Jul 22 22:47:19 CST 2019

    解决方法

    这个问题其实如果自己写代码的话很难出现,因为所有的Java书籍都不会这么教,大多数都是通过SimpleDateFormat,进行Date和String的转换,毕竟new Date(date1.toString())这个方法已经标注为废弃了

    二、Feign客户端的问题

    Feign客户端在进行通信时,会调用Date的toString方法转为String类型,服务端在接受的时候,使用的就是new Date(String)这个方法,这里就会发生前边介绍的问题,产生14个小时的时差

    解决方法

    在客户端添加代码,规定Feign在将Date参数转化成String参数的格式:

    import lombok.extern.slf4j.Slf4j;
    import org.springframework.cloud.openfeign.FeignFormatterRegistrar;
    import org.springframework.core.convert.converter.Converter;
    import org.springframework.format.FormatterRegistry;
    import org.springframework.stereotype.Component;
    
    import java.text.SimpleDateFormat;
    import java.util.Date;
    
    @Slf4j
    @Component
    public class FeignDateFormatRegister implements FeignFormatterRegistrar {
    
        @Override
        public void registerFormatters(FormatterRegistry registry) {
            registry.addConverter(Date.class, String.class, new Date2StringConverter());
        }
    
        private class Date2StringConverter implements Converter {
            @Override
            public String convert(Date source) {
                SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
                return sdf.format(source);
            }
    
        }
    }

    在服务端添加代码,规定SpringContext在String和Date时的用的转化器,让转化器知道我们在客户端配置的参数格式:

    import lombok.extern.slf4j.Slf4j;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.context.annotation.Configuration;
    import org.springframework.core.convert.converter.Converter;
    import org.springframework.core.convert.support.GenericConversionService;
    import org.springframework.web.bind.support.ConfigurableWebBindingInitializer;
    import org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter;
    
    import javax.annotation.PostConstruct;
    import java.text.ParseException;
    import java.text.SimpleDateFormat;
    import java.util.Date;
    
    @Slf4j
    @Configuration
    public class FeignConfiguration {
    
        @Autowired
        private RequestMappingHandlerAdapter handlerAdapter;
    
        /**
         *  增加字符串转日期的功能       
         */
        @PostConstruct
        public void initEditableValidation() {
            ConfigurableWebBindingInitializer initializer = (ConfigurableWebBindingInitializer) handlerAdapter.getWebBindingInitializer();
            if (initializer.getConversionService() != null) {
                GenericConversionService genericConversionService = (GenericConversionService) initializer.getConversionService();
                genericConversionService.addConverter(String.class, Date.class, new String2DateConverter());
            }
        }
    
        class String2DateConverter implements Converter {
            @Override
            public Date convert(String source) {
                SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
                try {
                    return simpleDateFormat.parse(source);
                } catch (ParseException e) {
                    log.error("", e);
                }
                return null;
            }
        }
    }

    看完上述内容是否对您有帮助呢?如果还想对相关知识有进一步的了解或阅读更多相关文章,请关注创新互联行业资讯频道,感谢您对创新互联的支持。


    分享标题:SpringCloud中怎么利用Feign传输date类型参数
    标题来源:http://pwwzsj.com/article/gioeci.html