FormatterRegistry接口和Converter和ConverterFactory的作用

1.FormatterRegistry接口

Spring框架提供了一个FormatterRegistry接口,用于注册自定义的Formatter和Converter,以支持更灵活的数据格式化和转换。通过实现Formatter或Converter接口,我们可以自定义数据的格式化和转换规则,并将其注册到FormatterRegistry中。
下面是一个使用addFormatters方法注册自定义Formatter的示例:

@Configuration
public class WebConfig implements WebMvcConfigurer {

    @Override
    public void addFormatters(FormatterRegistry registry) {
        // 注册自定义的DateFormatter
        registry.addFormatter(new DateFormatter("yyyy-MM-dd"));
        
        // 注册自定义的StringToEnumConverter
        registry.addConverter(new StringToEnumConverter());
    }
}

我们定义了一个WebConfig类,并实现了WebMvcConfigurer接口。通过重写addFormatters方法,我们可以访问FormatterRegistry对象,并使用addFormatter和addConverter方法注册自定义的Formatter和Converter。

  1. 注册自定义的DateFormatter:
    • 我们创建了一个DateFormatter对象,并指定了日期格式为"yyyy-MM-dd"。
    • 通过registry.addFormatter方法,将DateFormatter注册到FormatterRegistry中。
    • 这样,当Spring框架需要格式化或解析日期字符串时,就会使用我们自定义的DateFormatter。
  2. 注册自定义的StringToEnumConverter:
    • 我们创建了一个StringToEnumConverter对象,用于将字符串转换为枚举类型。
    • 通过registry.addConverter方法,将StringToEnumConverter注册到FormatterRegistry中。
    • 这样,当Spring框架需要将字符串转换为枚举类型时,就会使用我们自定义的StringToEnumConverter。

一旦我们注册了自定义的Formatter和Converter,Spring框架就会在需要进行数据格式化和转换时自动使用它们。例如,当我们使用@RequestParam注解接收日期参数时,Spring会使用我们注册的DateFormatter来解析日期字符串。

2.Converter

Converter是一个用于在不同数据类型之间进行转换的工具类或接口。它的主要作用是将一种数据类型转换为另一种数据类型,以满足不同场景下的需求。在Java中,Converter通常用于以下几个方面:

  1. 数据绑定:在将数据从一个对象绑定到另一个对象时,如果两个对象的属性类型不同,可以使用Converter进行类型转换。例如,将字符串类型的属性转换为整数类型。
    假设我们有一个User类,其中有一个age属性,类型为Integer。但是在前端表单提交数据时,age是以字符串的形式提交的。这时,我们可以使用Converter将字符串转换为Integer类型。
    public class StringToIntegerConverter implements Converter<String, Integer> {
        @Override
        public Integer convert(String source) {
            return Integer.valueOf(source);
        }
    }

  2. 数据格式化:Converter可以将数据格式化为特定的字符串表示形式,或者将字符串解析为特定的数据类型。例如,将日期对象转换为指定格式的字符串,或将字符串解析为日期对象。
    public class StringToDateConverter implements Converter<String, Date> {
        private static final SimpleDateFormat DATE_FORMAT = new SimpleDateFormat("yyyy-MM-dd");
    
        @Override
        public Date convert(String source) {
            try {
                return DATE_FORMAT.parse(source);
            } catch (ParseException e) {
                throw new IllegalArgumentException("无效的日期格式: " + source);
            }
        }
    }

  3. 数据校验:Converter可以在转换数据的同时进行数据校验,确保转换后的数据符合特定的约束条件。例如,将字符串转换为整数时,可以检查字符串是否为有效的整数格式。
    public class GradeConverter implements Converter<String, Double> {
        @Override
        public Double convert(String source) {
            if (source.equals("A+")) {
                return 4.0;
            } else if (source.equals("A")) {
                return 4.0;
            } else if (source.equals("B+")) {
                return 3.5;
            } else if (source.equals("B")) {
                return 3.0;
            } else {
                throw new IllegalArgumentException("无效的分数: " + source);
            }
        }
    }

  4. 国际化支持:Converter可以根据不同的语言环境对数据进行转换和格式化,以支持国际化和本地化。例如,将数字格式化为不同国家的货币格式。
    public class CurrencyConverter implements Converter<Double, String> {
        private final NumberFormat currencyFormat;
    
        public CurrencyConverter(Locale locale) {
            currencyFormat = NumberFormat.getCurrencyInstance(locale);
        }
    
        @Override
        public String convert(Double source) {
            return currencyFormat.format(source);
        }
    }

    3.Converterfactory

Spring框架提供了ConverterFactory接口,用于创建一组相关的Converter实例。当我们需要将多个相似的类型进行转换时,可以使用ConverterFactory来生成对应的Converter实例,而不需要为每个类型单独创建Converter。 
ConverterFactory接口定义如下:

public interface ConverterFactory<S, R> {
    <T extends R> Converter<S, T> getConverter(Class<T> targetType);
}

其中,S表示源类型,R表示目标类型的基类或接口。getConverter方法接受一个目标类型的Class对象,并返回一个能够将源类型转换为目标类型的Converter实例。

public class StringToEnumConverterFactory implements ConverterFactory<String, Enum> {
    @Override
    public <T extends Enum> Converter<String, T> getConverter(Class<T> targetType) {
         return new StringToEnumConverter<>(targetType);
    }

    private static class StringToEnumConverter<T extends Enum> implements Converter<String, T> {
        private final Class<T> enumType;

        public StringToEnumConverter(Class<T> enumType) {
            this.enumType = enumType;
        }

        @Override
        public T convert(String source) {
            return Enum.valueOf(enumType, source.toUpperCase());
        }
    }
}

我们定义了一个StringToEnumConverterFactory类,它实现了ConverterFactory接口。

  1. getConverter方法:
    • 接受一个目标枚举类型的Class对象作为参数。
    • 返回一个StringToEnumConverter实例,该实例能够将字符串转换为指定的枚举类型。
  2. StringToEnumConverter类:
    • 是一个内部类,实现了Converter接口。
    • 构造函数接受一个目标枚举类型的Class对象,并将其存储在enumType字段中。
    • convert方法将字符串转换为对应的枚举值,使用Enum.valueOf方法实现转换。

使用ConverterFactory的好处是,我们只需要定义一个工厂类,就可以生成多个相关的Converter实例。在上面的示例中,StringToEnumConverterFactory可以生成任意枚举类型的Converter,而不需要为每个枚举类型单独创建Converter。要将ConverterFactory注册到Spring框架中,可以使用FormatterRegistry的addConverterFactory方法:

@Configuration
public class WebConfig implements WebMvcConfigurer {
    @Override
    public void addFormatters(FormatterRegistry registry) {
        registry.addConverterFactory(new StringToEnumConverterFactory());
    }
}

 通过注册StringToEnumConverterFactory,Spring框架就可以在需要将字符串转换为枚举类型时,自动使用相应的Converter实例进行转换。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值