With all these drawbacks, why using Converters ? Am I missing something ? Are there other tricks that I am not aware of ?
No, I think you have very comprehensively described both PropertyEditor and Converter, how each one is declared and registered.
In my mind, PropertyEditors are limited in scope - they help convert String to a type, and this string typically comes from UI, and so registering a PropertyEditor using @InitBinder and using WebDataBinder makes sense.
Converter on the other hand is more generic, it is intended for ANY conversion in the system - not just for UI related conversions(String to target type). For eg, Spring Integration uses a converter extensively for converting a message payload to a desired type.
I think for UI related flows PropertyEditors are still appropriate especially for the case where you need to do something custom for a specific command property. For other cases, I would take the recommendation from Spring reference and write a converter instead(for eg, to convert from a Long id to an entity say, as a sample).
The simplest (assuming that you are using a persistence framework), but not the perfect way is to implement a generic entity converter via ConditionalGenericConverter
interface that will convert entities using their metadata.
For example, if you are using JPA, this converter may look if the specified class has @Entity
annotation, and use @Id
annotated field to extract information and perform the lookup automatically using the supplied String value as an Id for lookup.
public interface ConditionalGenericConverter extends GenericConverter {
boolean matches(TypeDescriptor sourceType, TypeDescriptor targetType);
}
ConditionalGenericConverter
is an "ultimate weapon" of Spring convertion API, but being implemented once it will be able to process most of entity convertions, saving developer time - it's a great relief when you just specify entity classes as parameters of your controller and never think about implementing a new converter(except for custom and non-entity types, of course).
You can sort of work around the need for having two separate Converter classes by implementing the two Converters as static inner classes.
public class FooConverter {
public static class BarToBaz implements Converter<Bar, Baz> {
@Override public Baz convert(Bar bar) { ... }
}
public static class BazToBar implements Converter<Baz, Bar> {
@Override public Bar convert(Baz baz) { ... }
}
}
You would still need to register both of them separately, but at least this cuts down on the number of files you need to modify if you make any changes.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With