【Spring】Spring Framework Reference Documentation中文版8

9. Validation, Data Binding, and Type Conversion

验证、数据绑定和类型转换

 

9.1 Introduction

介绍

 

JSR-303/JSR-349 Bean Validation

JSR-303/JSR-349bean验证

 

Spring Framework 4.0 supports Bean Validation 1.0 (JSR-303) and Bean Validation 1.1 (JSR-349) in terms of setup support, also adapting it to Springs Validator interface.

spring框架4支持bean验证1.0JSR303)和bean验证1.1JSR349),同时适用于spring的验证接口。

 

An application can choose to enable Bean Validation once globally, as described in Section 9.8, Spring Validation, and use it exclusively for all validation needs.

应用可以选择是否开启全局的bean验证,在9.8节中描述的“spring验证”,将其用于所有验证的需要。

 

An application can also register additional Spring Validator instances per DataBinder instance, as described in Section 9.8.3, Configuring a DataBinder. This may be useful for plugging in validation logic without the use of annotations.

一个应用可以注册额外的spring验证实例对于每个数据绑定实例,在9.8.3节中描述的“配置一个数据绑定”。这对不使用注解而实现验证逻辑的插件化处理很有用。

 

There are pros and cons for considering validation as business logic, and Spring offers a design for validation (and data binding) that does not exclude either one of them. Specifically validation should not be tied to the web tier, should be easy to localize and it should be possible to plug in any validator available. Considering the above, Spring has come up with a Validator interface that is both basic and eminently usable in every layer of an application.

将验证作为业务逻辑,spring提供一个设计用于验证(和数据绑定)包括全部。明确的验证不应该和web层绑定,应该易于局部化并且可以在需要验证时以插件的方式使用。考虑到上面的几点,spring提供了一个验证器接口可以用于一个应用的每一层。

 

Data binding is useful for allowing user input to be dynamically bound to the domain model of an application (or whatever objects you use to process user input). Spring provides the so-called DataBinder to do exactly that. The Validator and the DataBinder make up the validation package, which is primarily used in but not limited to the MVC framework.

数据绑定是有用的允许读者动态输入绑定应用的对象模型(或你需要处理用户输入的object)。spring提供了这样的DataBinder用于处理这些。验证器和数据绑定器组成了验证的包,主要用于但是不限制于MVC的框架中。

 

The BeanWrapper is a fundamental concept in the Spring Framework and is used in a lot of places. However, you probably will not have the need to use the BeanWrapper directly. Because this is reference documentation however, we felt that some explanation might be in order. We will explain the BeanWrapper in this chapter since, if you were going to use it at all, you would most likely do so when trying to bind data to objects.

BeanWrapperspring框架的基本内容用在很多的位置。然而,你不需要直接使用BeanWrapper。因为这是一个参考文档,然而我们会提供一些解释。我们将会这一节解释BeanWrapper,如果你决定使用它,当你试图将数据绑定到object时会用到。

 

Springs DataBinder and the lower-level BeanWrapper both use PropertyEditors to parse and format property values. The PropertyEditor concept is part of the JavaBeans specification, and is also explained in this chapter. Spring 3 introduces a "core.convert" package that provides a general type conversion facility, as well as a higher-level "format" package for formatting UI field values. These new packages may be used as simpler alternatives to PropertyEditors, and will also be discussed in this chapter.

springDataBingder和低级的BeanWrapper都使用了PropertyEditors来解析和格式化属性值。PropertyEditorJavaBean定义的一部分,并且在这节中得到解释。spring3介绍了一个core.conver包用于提供通用的类型转换方法,在formate包中由于格式化UI属性值。这些新的包将可以简单的使用PropertyEditors来替代,并且将会这节中讲解。

 

9.2 Validation using Springs Validator interface

使用spring的验证接口进行验证

 

Spring features a Validator interface that you can use to validate objects. The Validator interface works using an Errors object so that while validating, validators can report validation failures to the Errors object.

你可以使用spring的验证器接口的来验证object。验证器接口使用一个Errorsobject来工作用于完成验证,验证器可以对验证失败的object提供验证报告。

 

Lets consider a small data object:

让我们考虑一个小的object

 

public class Person {

 

    private String name;

    private int age;

 

    // the usual getters and setters...

// 通常的getset方法

}

 

Were going to provide validation behavior for the Person class by implementing the following two methods of the org.springframework.validation.Validator interface:

我们通过实现org.springframework.validation.Validator接口中的两个方法用于对Person类添加验证行为。

 

    supports(Class) - Can this Validator validate instances of the supplied Class?

验证器验证的实例是否是提供的类的实例?

    validate(Object, org.springframework.validation.Errors) - validates the given object and in case of validation errors, registers those with the given Errors object

验证给定的object是否是由于验证的error,注册在给定的Errorsobject

 

Implementing a Validator is fairly straightforward, especially when you know of the ValidationUtils helper class that the Spring Framework also provides.

直接实现Valiator接口,尤其是当你知道spring框架提供了一个ValidationUtils的工具类时。

 

public class PersonValidator implements Validator {

 

    /**

     * This Validator validates *just* Person instances

 * 这个验证器只适用于Person实例

     */

    public boolean supports(Class clazz) {

        return Person.class.equals(clazz);

    }

 

    public void validate(Object obj, Errors e) {

        ValidationUtils.rejectIfEmpty(e, "name", "name.empty");

        Person p = (Person) obj;

        if (p.getAge() < 0) {

            e.rejectValue("age", "negativevalue");

        } else if (p.getAge() > 110) {

            e.rejectValue("age", "too.darn.old");

        }

    }

}

 

As you can see, the static rejectIfEmpty(..) method on the ValidationUtils class is used to reject the 'name' property if it is null or the empty string. Have a look at the ValidationUtils javadocs to see what functionality it provides besides the example shown previously.

你看到了,ValidationUtils中的静态rejectIfEmpty方法用于拒绝当如果name属性是null或者是一个空字符串。可以查看ValidationUtilsjavadocs来查看之前的例子是如何工作的。

 

While it is certainly possible to implement a single Validator class to validate each of the nested objects in a rich object, it may be better to encapsulate the validation logic for each nested class of object in its own Validator implementation. A simple example of a 'rich' object would be a Customer that is composed of two String properties (a first and second name) and a complex Address object. Address objects may be used independently of Customer objects, and so a distinct AddressValidator has been implemented. If you want your CustomerValidator to reuse the logic contained within the AddressValidator class without resorting to copy-and-paste, you can dependency-inject or instantiate an AddressValidator within your CustomerValidator, and use it like so:

可以单独实现一个简单的Validator类用于验证每个富object中的内置object,最好将对于内置object的验证逻辑压缩到一个自有的Validator实现中。一个富object的简单例子可以是由两个字符串属性组成的Customer(一个姓,一个名)和一个复杂的AddressobjectAddressobject可以独立于Customerobject,因此可以实现一个AddressValidator。如果你需要你的CustomerValidator来服用逻辑包括在AddressValidator不需要复制和粘贴,你可以独立注入或在CustomerValidator中使用AddressValidator,你可以使用如下:

 

public class CustomerValidator implements Validator {

 

    private final Validator addressValidator;

 

    public CustomerValidator(Validator addressValidator) {

        if (addressValidator == null) {

            throw new IllegalArgumentException("The supplied [Validator] is " +

                "required and must not be null.");

        }

        if (!addressValidator.supports(Address.class)) {

            throw new IllegalArgumentException("The supplied [Validator] must " +

                "support the validation of [Address] instances.");

        }

        this.addressValidator = addressValidator;

    }

 

    /**

     * This Validator validates Customer instances, and any subclasses of Customer too

 * 这个验证器验证Customer实例和Customer的子类实例

     */

    public boolean supports(Class clazz) {

        return Customer.class.isAssignableFrom(clazz);

    }

 

    public void validate(Object target, Errors errors) {

        ValidationUtils.rejectIfEmptyOrWhitespace(errors, "firstName", "field.required");

        ValidationUtils.rejectIfEmptyOrWhitespace(errors, "surname", "field.required");

        Customer customer = (Customer) target;

        try {

            errors.pushNestedPath("address");

            ValidationUtils.invokeValidator(this.addressValidator, customer.getAddress(), errors);

        } finally {

            errors.popNestedPath();

        }

    }

}

 

Validation errors are reported to the Errors object passed to the validator. In case of Spring Web MVC you can use <spring:bind/> tag to inspect the error messages, but of course you can also inspect the errors object yourself. More information about the methods it offers can be found in the javadocs.

Validation错误用于报告封装于验证器中的错误object。在springmvc中你可以使用<spring:bing/>标签来检查错误信息,但是你也可以自行注入错误object。更多有关方法的信息见给定的javadocs

 

9.3 Resolving codes to error messages

拆解错误信息和代码的对应

 

Weve talked about databinding and validation. Outputting messages corresponding to validation errors is the last thing we need to discuss. In the example weve shown above, we rejected the name and the age field. If were going to output the error messages by using a MessageSource, we will do so using the error code weve given when rejecting the field ('name' and 'age' in this case). When you call (either directly, or indirectly, using for example the ValidationUtils class) rejectValue or one of the other reject methods from the Errors interface, the underlying implementation will not only register the code youve passed in, but also a number of additional error codes. What error codes it registers is determined by the MessageCodesResolver that is used. By default, the DefaultMessageCodesResolver is used, which for example not only registers a message with the code you gave, but also messages that include the field name you passed to the reject method. So in case you reject a field using rejectValue("age", "too.darn.old"), apart from the too.darn.old code, Spring will also register too.darn.old.age and too.darn.old.age.int (so the first will include the field name and the second will include the type of the field); this is done as a convenience to aid developers in targeting error messages and suchlike.

我们讨论一下数据绑定和验证。输出的信息和相关的验证错误是我们最后需要讨论的问题。在上面的例子,我们拒绝了nameage属性。如果我们通过使用MessageSource来输出错误信息,我们可以使用错误码当我们在决绝属性时(上面例子中的nameage)。当你调用(无论是直接或间接的使用ValidationUtils类)rejectValue或其他reject方法从Error接口中,其中不只会传递你提供的代码,也包括一些其他的错误代码。这些被注册的错误代码由使用的MessageCodesResolver来决定。默认的,会使用DefaultMessageCodesResolver,不只会注册一个你给定的错误信息,也包括你传递给reject方法的属性名。因此你可以通过使用rejectValue("age", "too.darn.old")来决绝一个field而区分与too.darn.old代码,spring 将会注册too.darn.old.agetoo.darn.old.age.int(因此首先包括field名,另一个会包括field的类型),这样会方便开发者用于定位错误信息

 

More information on the MessageCodesResolver and the default strategy can be found online in the javadocs of MessageCodesResolver and DefaultMessageCodesResolver, respectively.

MessageCodesResolver的更多信息和默认策略可以分别查看MessageCodesResolverDefaultMessageCodesResolverjavadocs

 

9.4 Bean manipulation and the BeanWrapper

bean操作和BeanWrapper

 

The org.springframework.beans package adheres to the JavaBeans standard provided by Oracle. A JavaBean is simply a class with a default no-argument constructor, which follows a naming convention where (by way of an example) a property named bingoMadness would have a setter method setBingoMadness(..) and a getter method getBingoMadness(). For more information about JavaBeans and the specification, please refer to Oracles website ( javabeans).

org.springframework.beans包和oracle提供的javabean标准绑定。一个javabean就是一个简单的类,有一个默认的无参构造器,按照一定的参数命名规范,如有个属性名字为bingoMadness,则有set方法setBingoMadnessget方法getBingoMadness。更多有关javabean和定义的信息请参考oracle的官网。

 

One quite important class in the beans package is the BeanWrapper interface and its corresponding implementation ( BeanWrapperImpl). As quoted from the javadocs, the BeanWrapper offers functionality to set and get property values (individually or in bulk), get property descriptors, and to query properties to determine if they are readable or writable. Also, the BeanWrapper offers support for nested properties, enabling the setting of properties on sub-properties to an unlimited depth. Then, the BeanWrapper supports the ability to add standard JavaBeans PropertyChangeListeners and VetoableChangeListeners, without the need for supporting code in the target class. Last but not least, the BeanWrapper provides support for the setting of indexed properties. The BeanWrapper usually isnt used by application code directly, but by the DataBinder and the BeanFactory.

bean包中很重要的类是BeanWrapper接口和他的相关实现(BeanWrapperImpl)。引用在javadocsBeanWrapper提供了设置和获取属性值的功能(单个或批量)、获得属性描述、查询属性来确定是否是可读或可写的。BeanWrapper也提供支持对内置的属性、允许无限制深度的设置属性的子属性。BeanWrapper支持添加JavaBeans PropertyChangeListenersVetoableChangeListeners,不需要目标类的代码支持。BeanWrapper支持索引属性的设置。BeanWrapper通常不会再应用代码中直接使用,但是会在DataBinderBeanFactory中使用。

 

The way the BeanWrapper works is partly indicated by its name: it wraps a bean to perform actions on that bean, like setting and retrieving properties.

BeanWrapper工作方式和名字暗示的一部分:他处理bean的行为,类似于设置和获得属性。

 

9.4.1 Setting and getting basic and nested properties

设置或获得基本和内置属性

 

Setting and getting properties is done using the setPropertyValue(s) and getPropertyValue(s) methods that both come with a couple of overloaded variants. Theyre all described in more detail in the javadocs Spring comes with. Whats important to know is that there are a couple of conventions for indicating properties of an object. A couple of examples:

设置和获得属性由setPropertyValuegetPropertyValue方法来实现,有几个重载的方法。详细描述在javadocs中。重要的知道有一些方法用于声明object的属性。例子:

 

Table 9.1. Examples of properties

属性的例子

Expression

表达式

Explanation

解释

name

Indicates the property name corresponding to the methods getName() or isName() and setName(..)

声明属性name相关的方法是getName()isName()setName()

account.name

Indicates the nested property name of the property account corresponding e.g. to the methods getAccount().setName() or getAccount().getName()

声明account属性的name属性相对应的是getAccount().setName()getAccount().getName()

account[2]

Indicates the third element of the indexed property account. Indexed properties can be of type array, list or other naturally ordered collection

声明是account的第三个元素。属性是数组类型、列表或其他有序的collection

account[COMPANYNAME]

Indicates the value of the map entry indexed by the key COMPANYNAME of the Map property account

声明map类型的account属性中keyCOMPANYNAME的值

Below youll find some examples of working with the BeanWrapper to get and set properties.

下面你会发现一些使用BeanWrapper来获得或设置属性的例子

 

(This next section is not vitally important to you if youre not planning to work with the BeanWrapper directly. If youre just using the DataBinder and the BeanFactory and their out-of-the-box implementation, you should skip ahead to the section about PropertyEditors.)

(下面的内容不是很重要如果在你并不想直接使用BeanWrapper的情况下。如果你只是使用DataBinderBeanFactory和他们的实现,你可以跳过有关PropertyEditors的内容)

 

Consider the following two classes:

考虑下面两个类:

 

public class Company {

 

    private String name;

    private Employee managingDirector;

 

    public String getName() {

        return this.name;

    }

 

    public void setName(String name) {

        this.name = name;

    }

 

    public Employee getManagingDirector() {

        return this.managingDirector;

    }

 

    public void setManagingDirector(Employee managingDirector) {

        this.managingDirector = managingDirector;

    }

}

 

public class Employee {

 

    private String name;

 

    private float salary;

 

    public String getName() {

        return this.name;

    }

 

    public void setName(String name) {

        this.name = name;

    }

 

    public float getSalary() {

        return salary;

    }

 

    public void setSalary(float salary) {

        this.salary = salary;

    }

}

 

The following code snippets show some examples of how to retrieve and manipulate some of the properties of instantiated Companies and Employees:

下面的代码片段展示了一些例子是如果操纵CompanyEmployee实例的属性值。

 

BeanWrapper company = new BeanWrapperImpl(new Company());

// setting the company name..

// 设置companyname

company.setPropertyValue("name", "Some Company Inc.");

// ... can also be done like this:

// 也可以是如下的样子

PropertyValue value = new PropertyValue("name", "Some Company Inc.");

company.setPropertyValue(value);

 

// ok, let's create the director and tie it to the company:

// 好,我们创建director并和company绑定

BeanWrapper jim = new BeanWrapperImpl(new Employee());

jim.setPropertyValue("name", "Jim Stravinsky");

company.setPropertyValue("managingDirector", jim.getWrappedInstance());

 

// retrieving the salary of the managingDirector through the company

// 通过company获得managingDirectorsalary

Float salary = (Float) company.getPropertyValue("managingDirector.salary");

 

9.4.2 Built-in PropertyEditor implementations

内置的PropertyEditor实现

 

Spring uses the concept of PropertyEditors to effect the conversion between an Object and a String. If you think about it, it sometimes might be handy to be able to represent properties in a different way than the object itself. For example, a Date can be represented in a human readable way (as the String '2007-14-09'), while were still able to convert the human readable form back to the original date (or even better: convert any date entered in a human readable form, back to Date objects). This behavior can be achieved by registering custom editors, of type java.beans.PropertyEditor. Registering custom editors on a BeanWrapper or alternately in a specific IoC container as mentioned in the previous chapter, gives it the knowledge of how to convert properties to the desired type. Read more about PropertyEditors in the javadocs of the java.beans package provided by Oracle.

spring使用PropertyEditors来影响object和字符串的转换。如果你这样考虑,有时会比较简单以不同的方式代表属性而不是object本身。例如,一个日期可以以易于读的方式来展示(例如字符串'2007-14-09'),当我们试图从原始日期类型转换为易于读取的形式(或者将任意日期转化为易于阅读的形式)。这种行为可以通过注册自定义的编辑器,类型是java.beans.PropertyEditor来实现。注册自定义编辑器在BeanWrapper上火替代之前章节中提到的特定的IOC容器,用于实现属性和目标类型的转换。详见PropertyEditorsjavadocs

 

A couple of examples where property editing is used in Spring:

spring中的一些例子中使用了属性编辑

 

    setting properties on beans is done using PropertyEditors. When mentioning java.lang.String as the value of a property of some bean youre declaring in XML file, Spring will (if the setter of the corresponding property has a Class-parameter) use the ClassEditor to try to resolve the parameter to a Class object.

使用PropertyEditors来设置bean的属性。如果你在xml文件中指定某个bean的属性是java.lang.String类型,spring会(如果相应属性的set方法有一个Class-parameter)使用ClassEditor来试图处理一个Class object的参数。

    parsing HTTP request parameters in Springs MVC framework is done using all kinds of PropertyEditors that you can manually bind in all subclasses of the CommandController.

解析springmvc框架中的http请求参数是通过使用各种的PropertyEditors来实现的,你可以手动绑定所有CommandController的子类。

 

Spring has a number of built-in PropertyEditors to make life easy. Each of those is listed below and they are all located in the org.springframework.beans.propertyeditors package. Most, but not all (as indicated below), are registered by default by BeanWrapperImpl. Where the property editor is configurable in some fashion, you can of course still register your own variant to override the default one:

spring有一些内置的PropertyEditors来简化处理。每个PropertyEditors都列在下面的表中都在org.springframework.beans.propertyeditors包中。大部分不是全部(下面提到的)都是通过BeanWrapperImpl默认被注册的。当属性编辑器被设置后,你依然可以注册自定义的编辑器来覆盖默认值:

 

Table 9.2. Built-in PropertyEditors

内置的PropertyEditors

Class

Explanation

解释

ByteArrayPropertyEditor

Editor for byte arrays. Strings will simply be converted to their corresponding byte representations. Registered by default by BeanWrapperImpl.

byte数组的编辑器。字符串会转化为相应的字节。默认由BeanWrapperImpl注册

ClassEditor

Parses Strings representing classes to actual classes and the other way around. When a class is not found, an IllegalArgumentException is thrown. Registered by default by BeanWrapperImpl.

解析字符串指向实际的类和其他。如果类没有被找到会抛出IllegalArgumentException异常。默认由BeanWrapperImpl注册

CustomBooleanEditor

Customizable property editor for Boolean properties. Registered by default by BeanWrapperImpl, but, can be overridden by registering custom instance of it as custom editor.

可定制的属性编辑器用于boolean属性。默认由BeanWrapperImpl注册但是可以通过自定义编辑器来覆盖。

CustomCollectionEditor

Property editor for Collections, converting any source Collection to a given target Collection type.

用于Collections的属性编辑器,将任何元结合转化为给定的集合类型

CustomDateEditor

Customizable property editor for java.util.Date, supporting a custom DateFormat. NOT registered by default. Must be user registered as needed with appropriate format.

可定制属性编辑器用于java.util.Data,支持自定义日期格式。默认没有被注册。必须根据需要使用适当的格式来手动注册

CustomNumberEditor

Customizable property editor for any Number subclass like Integer, Long, Float, Double. Registered by default by BeanWrapperImpl, but can be overridden by registering custom instance of it as a custom editor.

可定制属性编辑器用于Number的子类例如IntegerLongFloatDouble。默认由BeanWrapperImpe注册但是可以被自定义的属性编辑器覆盖

FileEditor

Capable of resolving Strings to java.io.File objects. Registered by default by BeanWrapperImpl.

处理java.io.Fileobject的字符串。默认由BeanWrapperImplementation注册

InputStreamEditor

One-way property editor, capable of taking a text string and producing (via an intermediate ResourceEditor and Resource) an InputStream, so InputStream properties may be directly set as Strings. Note that the default usage will not close the InputStream for you! Registered by default by BeanWrapperImpl.

单向属性编辑器,可以获得文本字符串和产生输入流(通过ResourceEditorResource作为辅助),因此输入流可以直接设置为字符串。注意默认使用中将不会替你关闭输入流。默认由BeanWrapperImpl注册

LocaleEditor

Capable of resolving Strings to Locale objects and vice versa (the String format is [country][variant], which is the same thing the toString() method of Locale provides). Registered by default by BeanWrapperImpl.

处理本地object的字符串,反之亦然(字符串类型是[country][variant]和本地提供的toString方法一样)。默认由BeanWrapperImpl注册

PatternEditor

Capable of resolving Strings to java.util.regex.Pattern objects and vice versa.

将字符串转化为java.util.regex.Pattern,反之亦然

PropertiesEditor

Capable of converting Strings (formatted using the format as defined in the javadocs of the java.util.Properties class) to Properties objects. Registered by default by BeanWrapperImpl.

可以将字符串转化为Properties,(使用定义在java.util.Propertiesjavadocs说明的格式进行格式化)。默认由BeanWrapperImpl注册

StringTrimmerEditor

Property editor that trims Strings. Optionally allows transforming an empty string into a null value. NOT registered by default; must be user registered as needed.

属性编辑器可选对字符串去空格并允许转化空字符串和null值。默认没有被注册。根据需要手动注册

URLEditor

Capable of resolving a String representation of a URL to an actual URL object. Registered by default by BeanWrapperImpl.

用于处理字符串来代表URL或实际的URLobject。默认由BeanWrapperImpl注册。

Spring uses the java.beans.PropertyEditorManager to set the search path for property editors that might be needed. The search path also includes sun.bean.editors, which includes PropertyEditor implementations for types such as Font, Color, and most of the primitive types. Note also that the standard JavaBeans infrastructure will automatically discover PropertyEditor classes (without you having to register them explicitly) if they are in the same package as the class they handle, and have the same name as that class, with 'Editor' appended; for example, one could have the following class and package structure, which would be sufficient for the FooEditor class to be recognized and used as the PropertyEditor for Foo-typed properties.

spring使用java.beans.PropertyEditorManger来设置搜索路径用于属性编辑器根据需要。搜索路径也包括sun.bean.editors,包括PropertyEditor的实现为了其他类型,如FontColor和大部分原始类型。注意编著的JavaBean架构可以自动发现PropertyEditor类(不需要你来手动注册)如果在相同的包中作为类来处理,或有相同的类名,然后以Editor结尾,例如,可以有如下的类和包结构将足够对于FooEditor类来识别用于Foo类型属性的属性编辑。

 

com

  chank

    pop

      Foo

      FooEditor // the PropertyEditor for the Foo class

 

Note that you can also use the standard BeanInfo JavaBeans mechanism here as well (described in not-amazing-detail here). Find below an example of using the BeanInfo mechanism for explicitly registering one or more PropertyEditor instances with the properties of an associated class.

注意你也可以使用标准的BeanInfo JavaBean的策略(。。。)。见下面这个使用BeanInfo策略的例子用于注册一个或多个属性编辑器实例相对于相关类。

 

com

  chank

    pop

      Foo

      FooBeanInfo // the BeanInfo for the Foo class

 

Here is the Java source code for the referenced FooBeanInfo class. This would associate a CustomNumberEditor with the age property of the Foo class.

这是java源代码参考FooBeanInfo类。下面的例子会将CustomNumberEditorFoo类的age属性联系在一起。

 

public class FooBeanInfo extends SimpleBeanInfo {

 

    public PropertyDescriptor[] getPropertyDescriptors() {

        try {

            final PropertyEditor numberPE = new CustomNumberEditor(Integer.class, true);

            PropertyDescriptor ageDescriptor = new PropertyDescriptor("age", Foo.class) {

                public PropertyEditor createPropertyEditor(Object bean) {

                    return numberPE;

                };

            };

            return new PropertyDescriptor[] { ageDescriptor };

        }

        catch (IntrospectionException ex) {

            throw new Error(ex.toString());

        }

    }

}

 

Registering additional custom PropertyEditors

注册额外的自定义属性编辑器

 

When setting bean properties as a string value, a Spring IoC container ultimately uses standard JavaBeans PropertyEditors to convert these Strings to the complex type of the property. Spring pre-registers a number of custom PropertyEditors (for example, to convert a classname expressed as a string into a real Class object). Additionally, Javas standard JavaBeans PropertyEditor lookup mechanism allows a PropertyEditor for a class simply to be named appropriately and placed in the same package as the class it provides support for, to be found automatically.

当设置一个bean的属性为字符串时,springioc容器会使用基本的JavaBean属性编辑器来将字符串转化为复杂的属性类型。spring会事先注册一些自定义的属性编辑器(例如,将一个类名表达为一个字符串设置到实际的classobject中)。此外,java的标砖JavaBeans属性编辑器的查询策略允许一个类的属性编辑器简单被命名并并在同一个包中定义,以便可以自动被发现。

 

If there is a need to register other custom PropertyEditors, there are several mechanisms available. The most manual approach, which is not normally convenient or recommended, is to simply use the registerCustomEditor() method of the ConfigurableBeanFactory interface, assuming you have a BeanFactory reference. Another, slightly more convenient, mechanism is to use a special bean factory post-processor called CustomEditorConfigurer. Although bean factory post-processors can be used with BeanFactory implementations, the CustomEditorConfigurer has a nested property setup, so it is strongly recommended that it is used with the ApplicationContext, where it may be deployed in similar fashion to any other bean, and automatically detected and applied.

如果需要注册其他的自定义属性编辑器则有一些策略可用。其中最手动的方法不是很方便也不被推荐使用,就是简单的使用ConfigurableBeanFactory接口的registerCustomEditor方法,假设你有一个BeanFactory的引用。另外,稍微有些方便的策略是使用特定bean工厂后处理器名为CustomEditorConfigurer。尽管bean工厂后处理器可以用于BeanFactory的实现,CustomEditorConfigurer有一个内置属性的设置,因此强烈推荐可以使用在ApplicationContext中,可以和其他bean一样以相似的方式部署并可以自动被探测和应用。

 

Note that all bean factories and application contexts automatically use a number of built-in property editors, through their use of something called a BeanWrapper to handle property conversions. The standard property editors that the BeanWrapper registers are listed in the previous section. Additionally, ApplicationContexts also override or add an additional number of editors to handle resource lookups in a manner appropriate to the specific application context type.

注意所有的bean工厂和应用上下文自动使用一定数量的内置属性编辑器,尽管他们使用的一些叫BeanWrapper用于处理属性转换。BeanWrapper注册的标准的属性编辑器在前一节中已经列出。此外应用上下文也可以覆盖和添加额外的编辑器用于处理资源的查找在管理以适应特定的应用上下文类型。

 

Standard JavaBeans PropertyEditor instances are used to convert property values expressed as strings to the actual complex type of the property. CustomEditorConfigurer, a bean factory post-processor, may be used to conveniently add support for additional PropertyEditor instances to an ApplicationContext.

标准的JavaBeans属性编辑器实例可以用于将属性值表达为字符串用于实际复杂的属性类型中。bean的工厂后处理器,CustomEditorConfigurer可以方便用于支持应用上下文中的属性编辑器实例。

 

Consider a user class ExoticType, and another class DependsOnExoticType which needs ExoticType set as a property:

考虑一个用户类ExoticType和另一个类DependsOnExoticType需要ExoticType作为属性:

 

package example;

 

public class ExoticType {

 

    private String name;

 

    public ExoticType(String name) {

        this.name = name;

    }

}

 

public class DependsOnExoticType {

 

    private ExoticType type;

 

    public void setType(ExoticType type) {

        this.type = type;

    }

}

 

When things are properly set up, we want to be able to assign the type property as a string, which a PropertyEditor will behind the scenes convert into an actual ExoticType instance:

当被正确的设置好,我们希望指定属性的类型是字符串,PropertyEditor在后面会将其转化为ExoticType实例。

 

<bean id="sample" class="example.DependsOnExoticType">

    <property name="type" value="aNameForExoticType"/>

</bean>

 

The PropertyEditor implementation could look similar to this:

PropertyEditor实现看上去是这样的:

 

// converts string representation to ExoticType object

// 转化字符串为ExoticTypeobject

package example;

 

public class ExoticTypeEditor extends PropertyEditorSupport {

 

    public void setAsText(String text) {

        setValue(new ExoticType(text.toUpperCase()));

    }

}

 

Finally, we use CustomEditorConfigurer to register the new PropertyEditor with the ApplicationContext, which will then be able to use it as needed:

最后,我们使用应用上下文的CustomEditorConfigurer来注册新的属性编辑器,可以根据需要来使用:

 

<bean class="org.springframework.beans.factory.config.CustomEditorConfigurer">

    <property name="customEditors">

        <map>

            <entry key="example.ExoticType" value="example.ExoticTypeEditor"/>

        </map>

    </property>

</bean>

 

Using PropertyEditorRegistrars

使用PropertyEditorRegistrars

 

Another mechanism for registering property editors with the Spring container is to create and use a PropertyEditorRegistrar. This interface is particularly useful when you need to use the same set of property editors in several different situations: write a corresponding registrar and reuse that in each case. PropertyEditorRegistrars work in conjunction with an interface called PropertyEditorRegistry, an interface that is implemented by the Spring BeanWrapper (and DataBinder). PropertyEditorRegistrars are particularly convenient when used in conjunction with the CustomEditorConfigurer (introduced here), which exposes a property called setPropertyEditorRegistrars(..): PropertyEditorRegistrars added to a CustomEditorConfigurer in this fashion can easily be shared with DataBinder and Spring MVC Controllers. Furthermore, it avoids the need for synchronization on custom editors: a PropertyEditorRegistrar is expected to create fresh PropertyEditor instances for each bean creation attempt.

spirng容器中其他注册属性编辑器的策略是创建和使用PropertyEditorRegistrar。当你需要在不同的环境中使用相同的一些属性编辑器时还是很有用的接口:创建一个相关的注册者然后在每个类中重复使用。PropertyEditorRegistrarsPropertyEditorRegistry接口同时使用,一个接口的实现是springBeanWrapper(和DataBinder)。PropertyEditorRegistrars当和CustomEditorConfigurer一起使用时是很方便的(在这里介绍),暴露了一个属性名为setPropertyEditorRegistrarsPropertyEditorRegistrarsCustomEditorConfigurer结合使用可以简单的在DataBinderspringMVC控制之间共享。进一步说,他避免了自定义编辑器对于同步的使用:PropertyEditorRegistrar试图对每个bean创建PropertyEditor的实例。

 

Using a PropertyEditorRegistrar is perhaps best illustrated with an example. First off, you need to create your own PropertyEditorRegistrar implementation:

使用PropertyEditorRegistrar或许是最好的方法在这个例子中。首先,你需要创建你自己的PropertyEditorRegistrar实现:

 

package com.foo.editors.spring;

 

public final class CustomPropertyEditorRegistrar implements PropertyEditorRegistrar {

 

    public void registerCustomEditors(PropertyEditorRegistry registry) {

 

        // it is expected that new PropertyEditor instances are created

// 创建一个新的PropertyEditor实例

        registry.registerCustomEditor(ExoticType.class, new ExoticTypeEditor());

 

        // you could register as many custom property editors as are required here...

// 你可以注册许多自定义属性编辑器根据要求

    }

}

 

See also the org.springframework.beans.support.ResourceEditorRegistrar for an example PropertyEditorRegistrar implementation. Notice how in its implementation of the registerCustomEditors(..) method it creates new instances of each property editor.

也可参考org.springframework.beans.support.ResourceEditorRegistrar作为一个PropertyEditorRegistrar实现的例子。注意实现中的registerCustomEditors方法创建每个属性编辑器的新实例。

 

Next we configure a CustomEditorConfigurer and inject an instance of our CustomPropertyEditorRegistrar into it:

下面我们配置一个CustomEditorConfigurer并且注入一个我们自己的CustomPropertyEditorRegistrar实例:

 

<bean class="org.springframework.beans.factory.config.CustomEditorConfigurer">

    <property name="propertyEditorRegistrars">

        <list>

            <ref bean="customPropertyEditorRegistrar"/>

        </list>

    </property>

</bean>

 

<bean id="customPropertyEditorRegistrar"

    class="com.foo.editors.spring.CustomPropertyEditorRegistrar"/>

 

Finally, and in a bit of a departure from the focus of this chapter, for those of you using Springs MVC web framework, using PropertyEditorRegistrars in conjunction with data-binding Controllers (such as SimpleFormController) can be very convenient. Find below an example of using a PropertyEditorRegistrar in the implementation of an initBinder(..) method:

最后,暂时脱离一下本节,在你使用springmvcweb框架时,一起使用PropertyEditorRegistrars和数据绑定控制器会更加方便。下面的例子中使用PropertyEditorRegistrar并实现了initBinder方法:

 

public final class RegisterUserController extends SimpleFormController {

 

    private final PropertyEditorRegistrar customPropertyEditorRegistrar;

 

    public RegisterUserController(PropertyEditorRegistrar propertyEditorRegistrar) {

        this.customPropertyEditorRegistrar = propertyEditorRegistrar;

    }

 

    protected void initBinder(HttpServletRequest request,

            ServletRequestDataBinder binder) throws Exception {

        this.customPropertyEditorRegistrar.registerCustomEditors(binder);

    }

 

    // other methods to do with registering a User

// 其他方法用于注册User

}

 

This style of PropertyEditor registration can lead to concise code (the implementation of initBinder(..) is just one line long!), and allows common PropertyEditor registration code to be encapsulated in a class and then shared amongst as many Controllers as needed.

这种使用PropertyEditor注册的风格可以简化代码(initBinder的实现只是一部分),允许通用的PropertyEditor注册代码在一个类中然后根据需要在许多控制器间共享。

 

9.5 Spring Type Conversion

spring的类型转换

 

Spring 3 introduces a core.convert package that provides a general type conversion system. The system defines an SPI to implement type conversion logic, as well as an API to execute type conversions at runtime. Within a Spring container, this system can be used as an alternative to PropertyEditors to convert externalized bean property value strings to required property types. The public API may also be used anywhere in your application where type conversion is needed.

spirng3介绍了core.convert包用于提供通用类型的转换系统。系统定义了SPI来实现类型转换逻辑,和API在运行时执行类型转换一样。在spring的容器中,这个系统可以用于PropertyEditors来转化属性字符串到需要的属性类型。公共API也可以在你应用中使用当需要类型转换时。

 

9.5.1 Converter SPI

 

The SPI to implement type conversion logic is simple and strongly typed:

SPI用于类型转换的逻辑时简单的而且是强类型的:

 

package org.springframework.core.convert.converter;

 

public interface Converter<S, T> {

 

    T convert(S source);

 

}

 

To create your own converter, simply implement the interface above. Parameterize S as the type you are converting from, and T as the type you are converting to. Such a converter can also be applied transparently if a collection or array of S needs to be converted to an array or collection of T, provided that a delegating array/collection converter has been registered as well (which DefaultConversionService does by default).

创建你自己的转化器需要实现上面的接口。参数S是你需要转换的类型,并且T是转换后的类型。这个转化器也可以应用在集合或数组上用于从S转换为T,提供了一个数组和集合转化器也被注册(默认是DefaultConversionService)。

 

For each call to convert(S), the source argument is guaranteed to be NOT null. Your Converter may throw any unchecked exception if conversion fails; specifically, an IllegalArgumentException should be thrown to report an invalid source value. Take care to ensure that your Converter implementation is thread-safe.

对于每次调用转化,源参数不可以是null。如果转换失败该方法可以抛出任何非检查异常:特殊的,一个IllegalArgumentException应该被抛出来反映一个错误的原数据值。保证你的转换实现是线程安全的。

 

Several converter implementations are provided in the core.convert.support package as a convenience. These include converters from Strings to Numbers and other common types. Consider StringToInteger as an example for a typical Converter implementation:

一些转换器的实现在core.convert.support包中被提供作为方便。包括将字符串转化为数字和其他常用的类型转换。考虑StringToInteger作为一个列子描述典型的转换器实现:

 

package org.springframework.core.convert.support;

 

final class StringToInteger implements Converter<String, Integer> {

 

    public Integer convert(String source) {

        return Integer.valueOf(source);

    }

 

}

 

9.5.2 ConverterFactory

转换工厂

 

When you need to centralize the conversion logic for an entire class hierarchy, for example, when converting from String to java.lang.Enum objects, implement ConverterFactory:

当你需要集中转换逻辑用于这个类的层级,例如,当将字符串转换为java.lang.Enumobject时,可以实现ConverterFactory

 

package org.springframework.core.convert.converter;

 

public interface ConverterFactory<S, R> {

 

    <T extends R> Converter<S, T> getConverter(Class<T> targetType);

 

}

 

Parameterize S to be the type you are converting from and R to be the base type defining the range of classes you can convert to. Then implement getConverter(Class<T>), where T is a subclass of R.

参数S是你需要转换的类型,R是你需要转换的类型范围。getConverter实现中TR的一个子类。

 

Consider the StringToEnum ConverterFactory as an example:

考虑StringToEnumConverterFactory作为一个例子:

 

package org.springframework.core.convert.support;

 

final class StringToEnumConverterFactory implements ConverterFactory<String, Enum> {

 

    public <T extends Enum> Converter<String, T> getConverter(Class<T> targetType) {

        return new StringToEnumConverter(targetType);

    }

 

    private final class StringToEnumConverter<T extends Enum> implements Converter<String, T> {

 

        private Class<T> enumType;

 

        public StringToEnumConverter(Class<T> enumType) {

            this.enumType = enumType;

        }

 

        public T convert(String source) {

            return (T) Enum.valueOf(this.enumType, source.trim());

        }

    }

}

 

9.5.3 GenericConverter

通用转换器

 

When you require a sophisticated Converter implementation, consider the GenericConverter interface. With a more flexible but less strongly typed signature, a GenericConverter supports converting between multiple source and target types. In addition, a GenericConverter makes available source and target field context you can use when implementing your conversion logic. Such context allows a type conversion to be driven by a field annotation, or generic information declared on a field signature.

当你需要一个复杂的转换器实现,考虑一下GenericConverter接口。更加方便但是没有强类型标识,支持多个源码到目标类型的转换。此外,GenericConverter使得当你实现你的转换逻辑时使用源码和目标域。这样的上下文允许一个类型转换通过域注解或定义在域中通用的信息。

 

package org.springframework.core.convert.converter;

 

public interface GenericConverter {

 

    public Set<ConvertiblePair> getConvertibleTypes();

 

    Object convert(Object source, TypeDescriptor sourceType, TypeDescriptor targetType);

 

}

 

To implement a GenericConverter, have getConvertibleTypes() return the supported sourcetarget type pairs. Then implement convert(Object, TypeDescriptor, TypeDescriptor) to implement your conversion logic. The source TypeDescriptor provides access to the source field holding the value being converted. The target TypeDescriptor provides access to the target field where the converted value will be set.

实现GenericConvertergetConvertibleTypes需要返回支持源类型到目标类型的对。然后实现convert方法来实现你的转换逻辑。源TypeDescriptor提供访问被转换的元域的值。目标TypeDescriptor提供访问转换后的目标域的值,该值可以被设置。

 

A good example of a GenericConverter is a converter that converts between a Java Array and a Collection. Such an ArrayToCollectionConverter introspects the field that declares the target Collection type to resolve the Collections element type. This allows each element in the source array to be converted to the Collection element type before the Collection is set on the target field.

一个比较好的GenericConverter例子就是Java数组到集合的转换。这样的ArrayToCollectionConverter自省定义在目标集合类型的域用于处理集合元素类型。允许每个在源数组的元素被转换为集合元素类型在结合被设置到目标域之前。

 

[Note]

注意

 

Because GenericConverter is a more complex SPI interface, only use it when you need it. Favor Converter or ConverterFactory for basic type conversion needs.

因为GenericConverter是一个比较复杂的SPI接口,当你需要的时候才会使用。倾向ConverterConverterFactory用于基本类型转换根据需要。

 

ConditionalGenericConverter

 

Sometimes you only want a Converter to execute if a specific condition holds true. For example, you might only want to execute a Converter if a specific annotation is present on the target field. Or you might only want to execute a Converter if a specific method, such as a static valueOf method, is defined on the target class. ConditionalGenericConverter is the union of the GenericConverter and ConditionalConverter interfaces that allows you to define such custom matching criteria:

有时你希望转换器在特定条件下进行转换。例如,你或许希望执行转换如果一个特定注解在目标域上使用时。或许你只是希望执行转换如果一个特定的方法例如静态的valueOf方法被定义在目标类中。ConditionalGenericConverter就是一个GenericConverterConditionalConverter的组合接口允许你定义自定义的匹配逻辑条件:

 

public interface ConditionalGenericConverter

        extends GenericConverter, ConditionalConverter {

 

    boolean matches(TypeDescriptor sourceType, TypeDescriptor targetType);

 

}

 

A good example of a ConditionalGenericConverter is an EntityConverter that converts between an persistent entity identifier and an entity reference. Such a EntityConverter might only match if the target entity type declares a static finder method e.g. findAccount(Long). You would perform such a finder method check in the implementation of matches(TypeDescriptor, TypeDescriptor).

ConditionalGenericConverter的一个好例子是EntityConverter用于转换一个持久化实体定义为一个实体引用。例如EntityConverter可以只匹配目标实体类型定义一个静态的finder方法例如findAccount(Long)。你或许可以使finder方法检测定义在matches(TypeDescriptor, TypeDescriptor)的实现中。

 

9.5.4 ConversionService API

转换服务接口

 

The ConversionService defines a unified API for executing type conversion logic at runtime. Converters are often executed behind this facade interface:

ConversionService定义了一个统一的API用于在运行时执行类型转换逻辑。Converters经常执行在此接口的后面:

 

package org.springframework.core.convert;

 

public interface ConversionService {

 

    boolean canConvert(Class<?> sourceType, Class<?> targetType);

 

    <T> T convert(Object source, Class<T> targetType);

 

    boolean canConvert(TypeDescriptor sourceType, TypeDescriptor targetType);

 

    Object convert(Object source, TypeDescriptor sourceType, TypeDescriptor targetType);

 

}

 

Most ConversionService implementations also implement ConverterRegistry, which provides an SPI for registering converters. Internally, a ConversionService implementation delegates to its registered converters to carry out type conversion logic.

大部分ConversionService实现也实现了ConverterRegistry,用于提供SPI来注册转换器。在其内部,ConversionService实现委托了注册机制给他的注册转换器用于处理类型转换逻辑。

 

A robust ConversionService implementation is provided in the core.convert.support package. GenericConversionService is the general-purpose implementation suitable for use in most environments. ConversionServiceFactory provides a convenient factory for creating common ConversionService configurations.

一个强健的ConversionService实现在core.convert.support包中被提供。GenericConversionService是一个通用的实现可以用于大部分的情况。ConversionServiceFactory提供了一个方便的工厂用于创建普通的ConversionService配置。

 

9.5.5 Configuring a ConversionService

配置一个ConversionService

 

A ConversionService is a stateless object designed to be instantiated at application startup, then shared between multiple threads. In a Spring application, you typically configure a ConversionService instance per Spring container (or ApplicationContext). That ConversionService will be picked up by Spring and then used whenever a type conversion needs to be performed by the framework. You may also inject this ConversionService into any of your beans and invoke it directly.

一个ConversionService是一个无状态的object设计加载应用启动时被实例化,在多个线程间被共享。

 

[Note]

注意

 

If no ConversionService is registered with Spring, the original PropertyEditor-based system is used.

如果spring没有注册ConversionService,则原始的基于属性编辑器的系统将被使用。

 

To register a default ConversionService with Spring, add the following bean definition with id conversionService:

为了使用spring注册默认的ConversionService,需要添加idconversionService的如下bean定义

 

<bean id="conversionService"

    class="org.springframework.context.support.ConversionServiceFactoryBean"/>

 

A default ConversionService can convert between strings, numbers, enums, collections, maps, and other common types. To supplement or override the default converters with your own custom converter(s), set the converters property. Property values may implement either of the Converter, ConverterFactory, or GenericConverter interfaces.

一个默认的ConversionService可以在字符串、数组、枚举、集合、map和其他通用类型间实现转换。为了补充或覆盖默认的转化器使用自定义的转化器,需要设置converters属性。属性值是一个实现ConverterConverterFactoryGenericConverter接口的某个类。

 

<bean id="conversionService"

        class="org.springframework.context.support.ConversionServiceFactoryBean">

    <property name="converters">

        <set>

            <bean class="example.MyCustomConverter"/>

        </set>

    </property>

</bean>

 

It is also common to use a ConversionService within a Spring MVC application. See Section 22.16.3, Conversion and Formattingin the Spring MVC chapter.

springmvc应用中使用GenericConverter也很常见。见22.16.3节,“转换和格式化”在springmvc章节。

 

In certain situations you may wish to apply formatting during conversion. See Section 9.6.3, FormatterRegistry SPIfor details on using FormattingConversionServiceFactoryBean.

在特定的情况你或许希望在转换中使用格式化。见9.6.3节,“FormatterRegistry SPI”中的详细内容使用FormattingConversionServiceFactoryBean

 

9.5.6 Using a ConversionService programmatically

编程使用ConversionService

 

To work with a ConversionService instance programmatically, simply inject a reference to it like you would for any other bean:

为了编程使用ConversionService实例,简单在一个bean中注入一个引用如下:

 

@Service

public class MyService {

 

    @Autowired

    public MyService(ConversionService conversionService) {

        this.conversionService = conversionService;

    }

 

    public void doIt() {

        this.conversionService.convert(...)

    }

}

 

For most use cases, the convert method specifying the targetType can be used but it will not work with more complex types such as a collection of a parameterized element. If you want to convert a List of Integer to a List of String programmatically, for instance, you need to provide a formal definition of the source and target types.

在大部分使用方式中,转换方法定义了目标类型可以被使用但是但是在一些参数化元素的集合类型这样复杂的类型可能无法工作。如果你希望编程转换一个IntegerList到一个字符串的List,例如,你需要提供一个格式定义对源类型和目标类型。

 

Fortunately, TypeDescriptor provides various options to make that straightforward:

幸运的是,TypeDescriptor提供了一些选项用于实现这样的功能:

 

DefaultConversionService cs = new DefaultConversionService();

 

List<Integer> input = ....

cs.convert(input,

    TypeDescriptor.forObject(input), // List<Integer> type descriptor

    TypeDescriptor.collection(List.class, TypeDescriptor.valueOf(String.class)));

 

Note that DefaultConversionService registers converters automatically which are appropriate for most environments. This includes collection converters, scalar converters, and also basic Object to String converters. The same converters can be registered with any ConverterRegistry using the static addDefaultConverters method on the DefaultConversionService class.

注意DefaultConversionService自动注册转换器可以使用于大部分的情况。这里包括集合转换、标量转换和基本object到字符串转化。通过ConverterRegistry同样的转换可以被注册使用DefaultConversionService类中的静态的addDefaultConverters方法。

 

Converters for value types will be reused for arrays and collections, so there is no need to create a specific converter to convert from a Collection of S to a Collection of T, assuming that standard collection handling is appropriate.

用于值类型的转换可以重用在数组和集合中,因此不需要创建特定的转换器用于转换一个集合S到另一个集合T,假设标准集合处理是合适的。

 

9.6 Spring Field Formatting

spring的域格式化

 

As discussed in the previous section, core.convert is a general-purpose type conversion system. It provides a unified ConversionService API as well as a strongly-typed Converter SPI for implementing conversion logic from one type to another. A Spring Container uses this system to bind bean property values. In addition, both the Spring Expression Language (SpEL) and DataBinder use this system to bind field values. For example, when SpEL needs to coerce a Short to a Long to complete an expression.setValue(Object bean, Object value) attempt, the core.convert system performs the coercion.

在前面的几节中讨论,core.convert是一个通用的类型转换系统。他提供特定的ConversionServiceAPI和强健的类型转换器实现用于实现一个类型到另一个类型的转换。一个spring的容器使用这个系统来绑定bean的属性值。此外,spring的表达式语言和DataBinder使用这个系统来绑定属性值。例如,当SpEL需要迫使一个Short类型转换为Long类型用于试图完成expression.setValue(Object bean, Object value),那这个系统可以提供的功能。

 

Now consider the type conversion requirements of a typical client environment such as a web or desktop application. In such environments, you typically convert from String to support the client postback process, as well as back to String to support the view rendering process. In addition, you often need to localize String values. The more general core.convert Converter SPI does not address such formatting requirements directly. To directly address them, Spring 3 introduces a convenient Formatter SPI that provides a simple and robust alternative to PropertyEditors for client environments.

现在考虑典型客户端环境下的类型转换例如作为一个web或桌面应用。在这样的环境下,你通常需要转换字符串来支持客户端回传程序,也包括转换成为字符串用于支持视图表现程序。此外,你也需要本地化字符串值。通常的转化器SPI没有直接进行直接的格式转换根据需要。为了实现这个功能,spring3加入了方便的格式化SPI提供简单强健的的属性编辑器用于客户端环境。

 

In general, use the Converter SPI when you need to implement general-purpose type conversion logic; for example, for converting between a java.util.Date and and java.lang.Long. Use the Formatter SPI when youre working in a client environment, such as a web application, and need to parse and print localized field values. The ConversionService provides a unified type conversion API for both SPIs.

通常,当你需要事项通用类型转换时使用转换器SPI;例如,为了方便将java.util.Date转换为java.lang.Long。当你在客户端环境使用格式化SPI,例如作为一个web营养共,你需要格式化和打印本地化的属性值。ConversionService提供了统一的类型转换API用于所有的SPI

 

9.6.1 Formatter SPI

 

The Formatter SPI to implement field formatting logic is simple and strongly typed:

FormatterSPI用于实现域格式化逻辑是简单而且强类型的:

 

package org.springframework.format;

 

public interface Formatter<T> extends Printer<T>, Parser<T> {

}

 

Where Formatter extends from the Printer and Parser building-block interfaces:

Formatter继承了PrinterParser内置的接口:

 

public interface Printer<T> {

    String print(T fieldValue, Locale locale);

}

 

import java.text.ParseException;

 

public interface Parser<T> {

    T parse(String clientValue, Locale locale) throws ParseException;

}

 

To create your own Formatter, simply implement the Formatter interface above. Parameterize T to be the type of object you wish to format, for example, java.util.Date. Implement the print() operation to print an instance of T for display in the client locale. Implement the parse() operation to parse an instance of T from the formatted representation returned from the client locale. Your Formatter should throw a ParseException or IllegalArgumentException if a parse attempt fails. Take care to ensure your Formatter implementation is thread-safe.

为了创建你自己的Formatter,需要实现上面的Formatter接口。参数T类型是你需要格式化的类型,例如,java.util.Data。实现print方法用于打印T的实例在客户端本地。实现parse方法用于将T实例从客户端本地格式化。你的Formatter应该抛出ParseExceptionIllegalArgumentException如果格式化尝试失败的时候。注意保证你的Formatter是线程安全的。

 

Several Formatter implementations are provided in format subpackages as a convenience. The number package provides a NumberFormatter, CurrencyFormatter, and PercentFormatter to format java.lang.Number objects using a java.text.NumberFormat. The datetime package provides a DateFormatter to format java.util.Date objects with a java.text.DateFormat. The datetime.joda package provides comprehensive datetime formatting support based on the Joda Time library.

一些Formatter实现提供在format子包中作为方便使用。该Number子包中提供了NumberFormatterCurrencyFormatterPercentFormatter用于格式化java.lang.Number通过使用java.text.NumberFormatdatetime子包中提供了DateFormatter用于格式化java.util.Data通过使用java.text.DataFormatdatetime.joda子包中提供了复杂的日期转化用于支持Joda的时间包。

 

Consider DateFormatter as an example Formatter implementation:

考虑Formatter的实现DataFormatter作为一个例子:

 

package org.springframework.format.datetime;

 

public final class DateFormatter implements Formatter<Date> {

 

    private String pattern;

 

    public DateFormatter(String pattern) {

        this.pattern = pattern;

    }

 

    public String print(Date date, Locale locale) {

        if (date == null) {

            return "";

        }

        return getDateFormat(locale).format(date);

    }

 

    public Date parse(String formatted, Locale locale) throws ParseException {

        if (formatted.length() == 0) {

            return null;

        }

        return getDateFormat(locale).parse(formatted);

    }

 

    protected DateFormat getDateFormat(Locale locale) {

        DateFormat dateFormat = new SimpleDateFormat(this.pattern, locale);

        dateFormat.setLenient(false);

        return dateFormat;

    }

 

}

 

The Spring team welcomes community-driven Formatter contributions; see jira.spring.io to contribute.

spring小组欢迎社区的格式化贡献:见jira.spring.io用于贡献。

 

9.6.2 Annotation-driven Formatting

基于注解的格式化

 

As you will see, field formatting can be configured by field type or annotation. To bind an Annotation to a formatter, implement AnnotationFormatterFactory:

你看到域格式化可以通过域类型或注解来配置。为了将注解绑定到formatter上需要实现AnnotationFormatterFactory

 

package org.springframework.format;

 

public interface AnnotationFormatterFactory<A extends Annotation> {

 

    Set<Class<?>> getFieldTypes();

 

    Printer<?> getPrinter(A annotation, Class<?> fieldType);

 

    Parser<?> getParser(A annotation, Class<?> fieldType);

 

}

 

Parameterize A to be the field annotationType you wish to associate formatting logic with, for example org.springframework.format.annotation.DateTimeFormat. Have getFieldTypes() return the types of fields the annotation may be used on. Have getPrinter() return a Printer to print the value of an annotated field. Have getParser() return a Parser to parse a clientValue for an annotated field.

参数A用于域注解类型你希望可以和格式化逻辑相关联,例如org.springframework.format.annotation.DateTimeFormatgetFieldTypes方法可以返回使用的注解域的类型。getPrinter可以返回一个Printer用于打印注解域的值。getParser方法可以返回一个Parser用于格式化用于注解域的clientValue

 

The example AnnotationFormatterFactory implementation below binds the @NumberFormat Annotation to a formatter. This annotation allows either a number style or pattern to be specified:

下面实现AnnotationFormatterFactory的类将NumberFormatter注解和格式化器绑定。注解允许number类型或特定的格式:

 

public final class NumberFormatAnnotationFormatterFactory

        implements AnnotationFormatterFactory<NumberFormat> {

 

    public Set<Class<?>> getFieldTypes() {

        return new HashSet<Class<?>>(asList(new Class<?>[] {

            Short.class, Integer.class, Long.class, Float.class,

            Double.class, BigDecimal.class, BigInteger.class }));

    }

 

    public Printer<Number> getPrinter(NumberFormat annotation, Class<?> fieldType) {

        return configureFormatterFrom(annotation, fieldType);

    }

 

    public Parser<Number> getParser(NumberFormat annotation, Class<?> fieldType) {

        return configureFormatterFrom(annotation, fieldType);

    }

 

    private Formatter<Number> configureFormatterFrom(NumberFormat annotation,

            Class<?> fieldType) {

        if (!annotation.pattern().isEmpty()) {

            return new NumberFormatter(annotation.pattern());

        } else {

            Style style = annotation.style();

            if (style == Style.PERCENT) {

                return new PercentFormatter();

            } else if (style == Style.CURRENCY) {

                return new CurrencyFormatter();

            } else {

                return new NumberFormatter();

            }

        }

    }

}

 

To trigger formatting, simply annotate fields with @NumberFormat:

为了触发格式化,简单声明@NumberFormat注解在域中:

 

public class MyModel {

 

    @NumberFormat(style=Style.CURRENCY)

    private BigDecimal decimal;

 

}

 

Format Annotation API

格式化注解API

 

A portable format annotation API exists in the org.springframework.format.annotation package. Use @NumberFormat to format java.lang.Number fields. Use @DateTimeFormat to format java.util.Date, java.util.Calendar, java.util.Long, or Joda Time fields.

方便的格式化注解APIorg.springframework.format.annotation包中提供。使用@NumberFormat用于格式化java.lang.Number域。使用@DateTimeFormat用于格式化java.util.Datejava.util.Calendarjava.util.LongJoda时间域,

 

The example below uses @DateTimeFormat to format a java.util.Date as a ISO Date (yyyy-MM-dd):

下面的例子展示了使用@DateTimeFormate来将java.util.Date格式化为ISO日期(yyyy-MM-dd):

 

public class MyModel {

 

    @DateTimeFormat(iso=ISO.DATE)

    private Date date;

 

}

 

9.6.3 FormatterRegistry SPI

 

The FormatterRegistry is an SPI for registering formatters and converters. FormattingConversionService is an implementation of FormatterRegistry suitable for most environments. This implementation may be configured programmatically or declaratively as a Spring bean using FormattingConversionServiceFactoryBean. Because this implementation also implements ConversionService, it can be directly configured for use with Springs DataBinder and the Spring Expression Language (SpEL).

FormatterRegistry是一个SPI用于注册格式化器和转换器。FormattingConversionServiceFormatterRegistry的实现用于大部分环境。该实现可以通过编程配置或定义为一个springbean通过使用FormattingConversionServiceFactoryBean。因为这个实现也实现了ConversionService,可以直接配置用于springDataBinderspring的表达式语言。

 

Review the FormatterRegistry SPI below:

回忆下面的FormatterRegistrySPI

 

package org.springframework.format;

 

public interface FormatterRegistry extends ConverterRegistry {

 

    void addFormatterForFieldType(Class<?> fieldType, Printer<?> printer, Parser<?> parser);

 

    void addFormatterForFieldType(Class<?> fieldType, Formatter<?> formatter);

 

    void addFormatterForFieldType(Formatter<?> formatter);

 

    void addFormatterForAnnotation(AnnotationFormatterFactory<?, ?> factory);

 

}

 

As shown above, Formatters can be registered by fieldType or annotation.

就像上面展示的,可以通过域类型或注解来注册格式化器。

 

The FormatterRegistry SPI allows you to configure Formatting rules centrally, instead of duplicating such configuration across your Controllers. For example, you might want to enforce that all Date fields are formatted a certain way, or fields with a specific annotation are formatted in a certain way. With a shared FormatterRegistry, you define these rules once and they are applied whenever formatting is needed.

FormatterRegistrySPI允许你配置格式化规则,避免跨控制器的重复配置。例如,你可以强制所有的日期域格式化为一个特定的形式或有特定注解的域格式化为特定的形式。通过共享FormatterRegistry,你可以一次定义这些规则并将它们应用于你需要的位置。

 

9.6.4 FormatterRegistrar SPI

 

The FormatterRegistrar is an SPI for registering formatters and converters through the FormatterRegistry:

FormatterRegistrar作为一个SPI用于注册格式化器和转换器通过FormatterRegistry

 

package org.springframework.format;

 

public interface FormatterRegistrar {

 

    void registerFormatters(FormatterRegistry registry);

 

}

 

A FormatterRegistrar is useful when registering multiple related converters and formatters for a given formatting category, such as Date formatting. It can also be useful where declarative registration is insufficient. For example when a formatter needs to be indexed under a specific field type different from its own <T> or when registering a Printer/Parser pair. The next section provides more information on converter and formatter registration.

FormatterRegistrar是有用的当注册多个相关的转换器和格式化器用于给定的格式化种类,例如日期格式化。在直接注册不能实现时可以很有用。例如当一个格式化去需要被索引在特定的域类型下不同于T类型或当注册Printer/Parser对时使用。下一节将展示更多的有关转换器和格式化器注册的内容。

 

9.6.5 Configuring Formatting in Spring MVC

springmvc中配置格式化

 

See Section 22.16.3, Conversion and Formattingin the Spring MVC chapter.

22.16.3节,“转换和格式化”在springmvc章节。

 

9.7 Configuring a global date & time format

配置全局的日期和时间格式

 

By default, date and time fields that are not annotated with @DateTimeFormat are converted from strings using the DateFormat.SHORT style. If you prefer, you can change this by defining your own global format.

默认,日期和时间域没有使用@DateTimeFormat来修饰可以使用DateFormat.SHORT的风格从字符串来转化。如果你需要,你可以通过定义你自己的全局格式来改变。

 

You will need to ensure that Spring does not register default formatters, and instead you should register all formatters manually. Use the org.springframework.format.datetime.joda.JodaTimeFormatterRegistrar or org.springframework.format.datetime.DateFormatterRegistrar class depending on whether you use the Joda Time library.

你将会需要确保spring没有注册默认的格式化器,作为代替你需要手动注册所有的格式化去。使用org.springframework.format.datetime.joda.JodaTimeFormatterRegistrarorg.springframework.format.datetime.DateFormatterRegistrar类根据你是否使用Joda时间库。

 

For example, the following Java configuration will register a global ' `yyyyMMddformat. This example does not depend on the Joda Time library:

例如,下面的Java配置注册了一个全局的“yyyyMMdd”格式。这个例子不需要依赖Joda时间库。

 

@Configuration

public class AppConfig {

 

    @Bean

    public FormattingConversionService conversionService() {

 

        // Use the DefaultFormattingConversionService but do not register defaults

// 使用DefaultFormattingConversionService但是没有将其注册为默认

        DefaultFormattingConversionService conversionService = new DefaultFormattingConversionService(false);

 

        // Ensure @NumberFormat is still supported

// 依然支持@NumberFormat

        conversionService.addFormatterForFieldAnnotation(new NumberFormatAnnotationFormatterFactory());

 

        // Register date conversion with a specific global format

// 使用全局的格式化来注册日期的格式化

        DateFormatterRegistrar registrar = new DateFormatterRegistrar();

        registrar.setFormatter(new DateFormatter("yyyyMMdd"));

        registrar.registerFormatters(conversionService);

 

        return conversionService;

    }

}

 

If you prefer XML based configuration you can use a FormattingConversionServiceFactoryBean. Here is the same example, this time using Joda Time:

如果你倾向于基于xml的配置你可以使用FormattingConversionServiceFactoryBean。这里给一个例子,其中这里的时间使用了Joda时间库:

 

<?xml version="1.0" encoding="UTF-8"?>

<beans xmlns="http://www.springframework.org/schema/beans"

    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"

    xsi:schemaLocation="

        http://www.springframework.org/schema/beans

        http://www.springframework.org/schema/beans/spring-beans.xsd>

 

    <bean id="conversionService" class="org.springframework.format.support.FormattingConversionServiceFactoryBean">

        <property name="registerDefaultFormatters" value="false" />

        <property name="formatters">

            <set>

                <bean class="org.springframework.format.number.NumberFormatAnnotationFormatterFactory" />

            </set>

        </property>

        <property name="formatterRegistrars">

            <set>

                <bean class="org.springframework.format.datetime.joda.JodaTimeFormatterRegistrar">

                    <property name="dateFormatter">

                        <bean class="org.springframework.format.datetime.joda.DateTimeFormatterFactoryBean">

                            <property name="pattern" value="yyyyMMdd"/>

                        </bean>

                    </property>

                </bean>

            </set>

        </property>

    </bean>

</beans>

 

[Note]

注意

 

Joda Time provides separate distinct types to represent date, time and date-time values. The dateFormatter, timeFormatter and dateTimeFormatter properties of the JodaTimeFormatterRegistrar should be used to configure the different formats for each type. The DateTimeFormatterFactoryBean provides a convenient way to create formatters.

Joda时间提供了分割的域来代表日期、时间和日期时间值。JodaTimeFormatterRegistrar类的dateFormattertimeFormatterdateTimeFormatter属性应该被使用用于配置不同的类型的格式。DateTimeFormatterFactoryBean提供了一个方便的方式用于创建格式化器。

 

If you are using Spring MVC remember to explicitly configure the conversion service that is used. For Java based @Configuration this means extending the WebMvcConfigurationSupport class and overriding the mvcConversionService() method. For XML you should use the 'conversion-service' attribute of the mvc:annotation-driven element. See Section 22.16.3, Conversion and Formattingfor details.

如果你使用springmvc,记住明确配置需要使用的转换服务。对于@Configuration注解来说这意味着扩展WebMvcConfigurationSupport类和覆盖mvcConversionService方法。对于使用xml,你应当使用mvc:annotation-driven元素的conversion-service属性。见22.16.3,“转换和格式化”。

 

9.8 Spring Validation

spring的验证

 

Spring 3 introduces several enhancements to its validation support. First, the JSR-303 Bean Validation API is now fully supported. Second, when used programmatically, Springs DataBinder can now validate objects as well as bind to them. Third, Spring MVC now has support for declaratively validating @Controller inputs.

spring3增加一些特性用于支持验证。首先,JSR303bean验证api是全部支持的。其次,当编程使用验证时,springDataBinder可以验证object并绑定他们。第三,springmvc现在支持在@Controller中输入验证内容。

 

9.8.1 Overview of the JSR-303 Bean Validation API

JSR303bean验证api的概述

 

JSR-303 standardizes validation constraint declaration and metadata for the Java platform. Using this API, you annotate domain model properties with declarative validation constraints and the runtime enforces them. There are a number of built-in constraints you can take advantage of. You may also define your own custom constraints.

JSR303标准提供验证约束定义和元数据用于java平台。使用这个api,你使用显示的验证约束声明域模型并且运行时会强制执行他们。有很多内置的验证约束需要关注。你也可以定义你自己的自定义约束。

 

To illustrate, consider a simple PersonForm model with two properties:

为了说明,考虑一个有两个属性的简单的PersonForm模型:

 

public class PersonForm {

    private String name;

    private int age;

}

 

JSR-303 allows you to define declarative validation constraints against such properties:

JSR303允许你定义显示的验证约束在这些属性中:

 

public class PersonForm {

 

    @NotNull

    @Size(max=64)

    private String name;

 

    @Min(0)

    private int age;

 

}

 

When an instance of this class is validated by a JSR-303 Validator, these constraints will be enforced.

当这个实例在JSR303验证器下被验证,这些约束会被强制执行。

 

For general information on JSR-303/JSR-349, see the Bean Validation website. For information on the specific capabilities of the default reference implementation, see the Hibernate Validator documentation. To learn how to setup a Bean Validation provider as a Spring bean, keep reading.

JSR303JSR349中,参考bean验证的网站。关于特定的功能对于默认的引用实现,见Hibernate的验证文档。为了给springbean提供bean验证,请继续阅读。

 

9.8.2 Configuring a Bean Validation Provider

配置bean验证提供者

 

Spring provides full support for the Bean Validation API. This includes convenient support for bootstrapping a JSR-303/JSR-349 Bean Validation provider as a Spring bean. This allows for a javax.validation.ValidatorFactory or javax.validation.Validator to be injected wherever validation is needed in your application.

spring提供全面的支持对于bean验证的api。包括方便支持JSR303JSR349bean提供者用于springbean。这允许javax.validation.ValidatorFactoryjavax.validation.Validator可以注入你需要在你的应用中使用验证的位置。

 

Use the LocalValidatorFactoryBean to configure a default Validator as a Spring bean:

使用LocalValidatorFactoryBeanspringbean配置默认的验证器:

 

<bean id="validator"

    class="org.springframework.validation.beanvalidation.LocalValidatorFactoryBean"/>

 

The basic configuration above will trigger Bean Validation to initialize using its default bootstrap mechanism. A JSR-303/JSR-349 provider, such as Hibernate Validator, is expected to be present in the classpath and will be detected automatically.

上面的配置将会在初始化时激活bean的验证,使用默认的启动策略。JSR303JSR349的提供,例如Hibernate的验证器,被期望出现在classpath中并且会自动被探测。

 

Injecting a Validator

注入一个验证器

 

LocalValidatorFactoryBean implements both javax.validation.ValidatorFactory and javax.validation.Validator, as well as Springs org.springframework.validation.Validator. You may inject a reference to either of these interfaces into beans that need to invoke validation logic.

LocalValidatorFactoryBean实现了javax.validation.ValidatorFactoryjavax.validation.Validator接口,也包括Springorg.springframework.validation.Validator。你可以注入任何一个上面三个接口的引用到你的bean中如果你需要调用验证逻辑。

 

Inject a reference to javax.validation.Validator if you prefer to work with the Bean Validation API directly:

如果你希望直接使用bean验证api可以注入javax.validation.Validator的引用:

 

import javax.validation.Validator;

 

@Service

public class MyService {

 

    @Autowired

    private Validator validator;

 

Inject a reference to org.springframework.validation.Validator if your bean requires the Spring Validation API:

如果你需要spring的验证api则注入org.springframework.validation.Validator的引用:

 

import org.springframework.validation.Validator;

 

@Service

public class MyService {

 

    @Autowired

    private Validator validator;

 

}

 

Configuring Custom Constraints

配置自定义的约束

 

Each Bean Validation constraint consists of two parts. First, a @Constraint annotation that declares the constraint and its configurable properties. Second, an implementation of the javax.validation.ConstraintValidator interface that implements the constraints behavior. To associate a declaration with an implementation, each @Constraint annotation references a corresponding ValidationConstraint implementation class. At runtime, a ConstraintValidatorFactory instantiates the referenced implementation when the constraint annotation is encountered in your domain model.

每个bean的验证约束包括两个部分。第一,@Constraint注解声明了约束和他的可配置属性。第二,实现javax.validation.ConstraintValidator接口用于实现约束的行为。为了关联实现的定义,每个@Constraint注解引用一个相关的ValidationConstraint实现类。在运行时,一个ConstraintValidatorFactory实例化相关的实现当约束注解定义你的域模型中。

 

By default, the LocalValidatorFactoryBean configures a SpringConstraintValidatorFactory that uses Spring to create ConstraintValidator instances. This allows your custom ConstraintValidators to benefit from dependency injection like any other Spring bean.

默认的,LocalValidatorFactoryBean配置了SpringConstraintValidatorFactory用于spring来创建ConstraintValidator实例。允许你自定义ConstraintValidators来独立注入类似于其他springbean

 

Shown below is an example of a custom @Constraint declaration, followed by an associated ConstraintValidator implementation that uses Spring for dependency injection:

下面是一个@Constraint声明的例子,使用spring的依赖注入来管理ConstraintValidator的实现:

 

@Target({ElementType.METHOD, ElementType.FIELD})

@Retention(RetentionPolicy.RUNTIME)

@Constraint(validatedBy=MyConstraintValidator.class)

public @interface MyConstraint {

}

 

import javax.validation.ConstraintValidator;

 

public class MyConstraintValidator implements ConstraintValidator {

 

    @Autowired;

    private Foo aDependency;

 

    ...

}

 

As you can see, a ConstraintValidator implementation may have its dependencies @Autowired like any other Spring bean.

可见,ConstraintValidator实现可以有独立的@Autowired类似于其他的springbean

 

Spring-driven Method Validation

基于spring的方法验证

 

The method validation feature supported by Bean Validation 1.1, and as a custom extension also by Hibernate Validator 4.3, can be integrated into a Spring context through a MethodValidationPostProcessor bean definition:

方法验证特性通过bean验证1.1来支持,Hibernate验证4.3的自定义扩展也可以注入spring的上下文通过一个MethodValidationPostProcessorbean定义。

 

<bean class="org.springframework.validation.beanvalidation.MethodValidationPostProcessor"/>

 

In order to be eligible for Spring-driven method validation, all target classes need to be annotated with Springs @Validated annotation, optionally declaring the validation groups to use. Check out the MethodValidationPostProcessor javadocs for setup details with Hibernate Validator and Bean Validation 1.1 providers.

为了适用于基于spring的方法验证,所有的目标的类需要使用spring@Validated注解,可选的使用验证组。查看MethodValidationPostProcessorjavadocs用于了解Hibernate验证器和bean验证1.1的详情。

 

Additional Configuration Options

额外的配置选项

 

The default LocalValidatorFactoryBean configuration should prove sufficient for most cases. There are a number of configuration options for various Bean Validation constructs, from message interpolation to traversal resolution. See the LocalValidatorFactoryBean javadocs for more information on these options.

默认的LocalValidatorFactoryBean配置应当适合大多数场景。需要很多配置选项用于多种bean的验证约束,从信息采集到解决方案。详细见LocalValidatorFactoryBeanjavadocs

 

9.8.3 Configuring a DataBinder

配置DataBinder

 

Since Spring 3, a DataBinder instance can be configured with a Validator. Once configured, the Validator may be invoked by calling binder.validate(). Any validation Errors are automatically added to the binders BindingResult.

自从spring3DataBinder实例可以使用验证器来配置。一次配置,验证器可以通过调用binder.validate来使用。任何验证错误可以自动加入binderBindingResult中。

 

When working with the DataBinder programmatically, this can be used to invoke validation logic after binding to a target object:

当编程使用DataBinder,可以在目标object上调用验证逻辑:

 

Foo target = new Foo();

DataBinder binder = new DataBinder(target);

binder.setValidator(new FooValidator());

 

// bind to the target object

// 绑定到目标object

binder.bind(propertyValues);

 

// validate the target object

// 验证目标object

binder.validate();

 

// get BindingResult that includes any validation errors

// 获得BindingResult里面包含所有验证错误

BindingResult results = binder.getBindingResult();

 

A DataBinder can also be configured with multiple Validator instances via dataBinder.addValidators and dataBinder.replaceValidators. This is useful when combining globally configured Bean Validation with a Spring Validator configured locally on a DataBinder instance. See ???.

DataBinder可以使用多个验证器实例来配置,通过使用dataBinder.addValidatorsdataBinder.replaceValidators。当组合全局配置的bean验证通过使用spring的验证器在本地的DataBinder实例上使用。见……

 

9.8.4 Spring MVC 3 Validation

springmvc3的验证

 

See Section 22.16.4, Validationin the Spring MVC chapter.

22.16.4spirngmvc章节中的验证。

 

 

Not Using Commons Logging ................................................................... 12 Using SLF4J ............................................................................................ 13 Using Log4J ............................................................................................. 14 II. What’s New in Spring Framework 4.x .................................................................................... 16 3. New Features and Enhancements in Spring Framework 4.0 ............................................ 17 3.1. Improved Getting Started Experience .................................................................. 17 3.2. Removed Deprecated Packages and Methods .................................................... 17 3.3. Java 8 (as well as 6 and 7) ............................................................................... 17 3.4. Java EE 6 and 7 ............................................................................................... 18 3.5. Groovy Bean Definition DSL .............................................................................. 18 3.6. Core Container Improvements ............................................................................ 19 3.7. General Web Improvements ............................................................................... 19 3.8. WebSocket, SockJS, and STOMP Messaging ..................................................... 19 3.9. Testing Improvements ........................................................................................ 20 III. Core Technologies .............................................................................................................. 21 4. The IoC container ........................................................................................................ 22 4.1. Introduction to the Spring IoC container and beans .............................................. 22 4.2. Container overview ............................................................................................ 22 Configuration metadata ..................................................................................... 23 Instantiating a container .................................................................................... 24 Composing XML-based configuration metadata .......................................... 25 Using the container .......................................................................................... 26 4.3. Bean overview ................................................................................................... 27 Naming beans .................................................................................................. 28 Aliasing a bean outside the bean definition ................................................ 28 Instantiating beans ........................................................................................... 29 Instantiation with a constructor .................................................................. 29 Instantiation with a static factory method .................................................... 30 Spring Framework 4.0.0.RELEASE Spring Framework Reference Documentation iii Instantiation using an instance factory method ........................................... 30 4.4. Dependencies ................................................................................................... 32 Dependency injection ....................................................................................... 32 Constructor-based dependency injection .................................................... 32 Setter-based dependency injection ............................................................ 34 Dependency resolution process ................................................................. 35 Examples of dependency injection ............................................................. 36 Dependencies and configuration in detail ........................................................... 38 Straight values (primitives, Strings, and so on) ........................................... 38 References to other beans (collaborators) .................................................. 40 Inner beans .............................................................................................. 41 Collections ............................................................................................... 41 Null and empty string values ..................................................................... 44 XML shortcut with the p-namespace .......................................................... 44 XML shortcut with the c-namespace .......................................................... 46 Compound property names ....................................................................... 46 Using depends-on ............................................................................................ 47 Lazy-initialized beans ....................................................................................... 47 Autowiring collaborators .................................................................................... 48 Limitations and disadvantages of autowiring ............................................... 49 Excluding a bean from autowiring .............................................................. 50 Method injection ............................................................................................... 50 Lookup method injection ........................................................................... 51 Arbitrary method replacement ................................................................... 53 4.5. Bean scopes ..................................................................................................... 54 The singleton scope ......................................................................................... 55 The prototype scope ......................................................................................... 55 Singleton beans with prototype-bean dependencies ............................................ 56 Request, session, and global session scopes .................................................... 56 Initial web configuration ............................................................................ 57 Request scope ......................................................................................... 58 Session scope .......................................................................................... 58 Global session scope ............................................................................... 58 Scoped beans as dependencies ................................................................ 58 Custom scopes ................................................................................................ 60 Creating a custom scope .......................................................................... 60 Using a custom scope .............................................................................. 61 4.6. Customizing the nature of a bean ....................................................................... 62 Lifecycle callbacks ............................................................................................ 62 Initialization callbacks ............................................................................... 63 Destruction callbacks ................................................................................ 64 Default initialization and destroy methods .................................................. 64 Combining lifecycle mechanisms ............................................................... 66 Startup and shutdown callbacks ................................................................ 66 Shutting down the Spring IoC container gracefully in non-web applications ................................................................................................................. 68 ApplicationContextAware and BeanNameAware ................................................. 68 Other Aware interfaces ..................................................................................... 69 4.7. Bean definition inheritance ................................................................................. 71 4.8. Container Extension Points ................................................................................ 72 Spring Framework 4.0.0.RELEASE Spring Framework Reference Documentation iv Customizing beans using a BeanPostProcessor ................................................. 72 Example: Hello World, BeanPostProcessor-style ........................................ 74 Example: The RequiredAnnotationBeanPostProcessor ............................... 75 Customizing configuration metadata with a BeanFactoryPostProcessor ................ 75 Example: the Class name substitution PropertyPlaceholderConfigurer .......... 76 Example: the PropertyOverrideConfigurer .................................................. 77 Customizing instantiation logic with a FactoryBean ............................................. 78 4.9. Annotation-based container configuration ............................................................ 79 @Required ....................................................................................................... 80 @Autowired ..................................................................................................... 80 Fine-tuning annotation-based autowiring with qualifiers ....................................... 83 Using generics as autowiring qualifiers .............................................................. 89 CustomAutowireConfigurer ................................................................................ 90 @Resource ...................................................................................................... 90 @PostConstruct and @PreDestroy .................................................................... 92 4.10. Classpath scanning and managed components ................................................. 92 @Component and further stereotype annotations ............................................... 93 Meta-annotations .............................................................................................. 93 Automatically detecting classes and registering bean definitions .......................... 94 Using filters to customize scanning ................................................................... 95 Defining bean metadata within components ....................................................... 96 Naming autodetected components ..................................................................... 97 Providing a scope for autodetected components ................................................ 98 Providing qualifier metadata with annotations ..................................................... 99 4.11. Using JSR 330 Standard Annotations ............................................................... 99 Dependency Injection with @Inject and @Named ............................................. 100 @Named: a standard equivalent to the @Component annotation ....................... 100 Limitations of the standard approach ............................................................... 101 4.12. Java-based container configuration ................................................................. 102 Basic concepts: @Bean and @Configuration ................................................... 102 Instantiating the Spring container using AnnotationConfigApplicationContext ....... 103 Simple construction ................................................................................ 103 Building the container programmatically using register(Class…) ........... 104 Enabling component scanning with scan(String…) .................................... 104 Support for web applications with AnnotationConfigWebApplicationContext ............................................................................................................... 105 Using the @Bean annotation .......................................................................... 106 Declaring a bean .................................................................................... 107 Receiving lifecycle callbacks ................................................................... 107 Specifying bean scope ............................................................................ 108 Customizing bean naming ....................................................................... 109 Bean aliasing ......................................................................................... 109 Bean description ..................................................................................... 110 Using the @Configuration annotation ............................................................... 110 Injecting inter-bean dependencies ............................................................ 110 Lookup method injection ......................................................................... 111 Further information about how Java-based configuration works internally .... 111 Composing Java-based configurations ............................................................. 112 Using the @Import annotation ................................................................. 112 Conditionally including @Configuration classes or @Beans ....................... 116 Spring Framework 4.0.0.RELEASE Spring Framework Reference Documentation v Combining Java and XML configuration ................................................... 117 4.13. Bean definition profiles and environment abstraction ........................................ 120 4.14. PropertySource Abstraction ............................................................................ 120 4.15. Registering a LoadTimeWeaver ...................................................................... 120 4.16. Additional Capabilities of the ApplicationContext .............................................. 120 Internationalization using MessageSource ........................................................ 121 Standard and Custom Events .......................................................................... 124 Convenient access to low-level resources ........................................................ 127 Convenient ApplicationContext instantiation for web applications ....................... 128 Deploying a Spring ApplicationContext as a J2EE RAR file ............................... 128 4.17. The BeanFactory ........................................................................................... 129 BeanFactory or ApplicationContext? ................................................................ 129 Glue code and the evil singleton ..................................................................... 131 5. Resources .................................................................................................................. 132 5.1. Introduction ..................................................................................................... 132 5.2. The Resource interface .................................................................................... 132 5.3. Built-in Resource implementations .................................................................... 133 UrlResource ................................................................................................... 133 ClassPathResource ........................................................................................ 133 FileSystemResource ....................................................................................... 134 ServletContextResource .................................................................................. 134 InputStreamResource ..................................................................................... 134 ByteArrayResource ......................................................................................... 134 5.4. The ResourceLoader ....................................................................................... 134 5.5. The ResourceLoaderAware interface ................................................................ 135 5.6. Resources as dependencies ............................................................................. 136 5.7. Application contexts and Resource paths .......................................................... 137 Constructing application contexts ..................................................................... 137 Constructing ClassPathXmlApplicationContext instances - shortcuts .......... 137 Wildcards in application context constructor resource paths ............................... 138 Ant-style Patterns ................................................................................... 138 The Classpath*: portability classpath*: prefix ............................................ 139 Other notes relating to wildcards ............................................................. 139 FileSystemResource caveats .......................................................................... 140 6. Validation, Data Binding, and Type Conversion ............................................................ 141 6.1. Introduction ..................................................................................................... 141 6.2. Validation using Spring’s Validator interface ...................................................... 141 6.3. Resolving codes to error messages .................................................................. 143 6.4. Bean manipulation and the BeanWrapper ......................................................... 144 Setting and getting basic and nested properties ............................................... 144 Built-in PropertyEditor implementations ............................................................ 146 Registering additional custom PropertyEditors .......................................... 149 6.5. Spring Type Conversion ................................................................................... 151 Converter SPI ................................................................................................ 151 ConverterFactory ............................................................................................ 152 GenericConverter ........................................................................................... 153 ConditionalGenericConverter ................................................................... 154 ConversionService API ................................................................................... 154 Configuring a ConversionService ..................................................................... 154 Using a ConversionService programmatically ................................................... 155 Spring Framework 4.0.0.RELEASE Spring Framework Reference Documentation vi 6.6. Spring Field Formatting .................................................................................... 155 Formatter SPI ................................................................................................. 156 Annotation-driven Formatting ........................................................................... 157 Format Annotation API ............................................................................ 158 FormatterRegistry SPI ..................................................................................... 159 FormatterRegistrar SPI ................................................................................... 159 Configuring Formatting in Spring MVC ............................................................. 159 6.7. Configuring a global date & time format ............................................................ 161 6.8. Spring Validation ............................................................................................. 163 Overview of the JSR-303 Bean Validation API ................................................. 163 Configuring a Bean Validation Provider ............................................................ 164 Injecting a Validator ................................................................................ 164 Configuring Custom Constraints .............................................................. 164 Additional Configuration Options .............................................................. 165 Configuring a DataBinder ................................................................................ 165 Spring MVC 3 Validation ................................................................................. 166 Triggering @Controller Input Validation .................................................... 166 Configuring a Validator for use by Spring MVC ......................................... 166 Configuring a JSR-303/JSR-349 Validator for use by Spring MVC .............. 167 7. Spring Expression Language (SpEL) ........................................................................... 168 7.1. Introduction ..................................................................................................... 168 7.2. Feature Overview ............................................................................................ 168 7.3. Expression Evaluation using Spring’s Expression Interface ................................. 169 The EvaluationContext interface ...................................................................... 171 Type Conversion .................................................................................... 171 7.4. Expression support for defining bean definitions ................................................ 172 XML based configuration ................................................................................ 172 Annotation-based configuration ........................................................................ 173 7.5. Language Reference ........................................................................................ 174 Literal expressions .......................................................................................... 174 Properties, Arrays, Lists, Maps, Indexers ......................................................... 174 Inline lists ....................................................................................................... 175 Array construction ........................................................................................... 175 Methods ......................................................................................................... 176 Operators ....................................................................................................... 176 Relational operators ................................................................................ 176 Logical operators .................................................................................... 177 Mathematical operators ........................................................................... 177 Assignment .................................................................................................... 178 Types ............................................................................................................. 178 Constructors ................................................................................................... 179 Variables ........................................................................................................ 179 The #this and #root variables .................................................................. 179 Functions ....................................................................................................... 180 Bean references ............................................................................................. 180 Ternary Operator (If-Then-Else) ....................................................................... 180 The Elvis Operator ......................................................................................... 181 Safe Navigation operator ................................................................................ 181 Collection Selection ........................................................................................ 182 Collection Projection ....................................................................................... 182 Spring Framework 4.0.0.RELEASE Spring Framework Reference Documentation vii Expression templating ..................................................................................... 183 7.6. Classes used in the examples .......................................................................... 183 8. Aspect Oriented Programming with Spring ................................................................... 187 8.1. Introduction ..................................................................................................... 187 AOP concepts ................................................................................................ 187 Spring AOP capabilities and goals ................................................................... 189 AOP Proxies .................................................................................................. 190 8.2. @AspectJ support ........................................................................................... 190 Enabling @AspectJ Support ............................................................................ 190 Enabling @AspectJ Support with Java configuration ................................. 190 Enabling @AspectJ Support with XML configuration ................................. 191 Declaring an aspect ........................................................................................ 191 Declaring a pointcut ........................................................................................ 192 Supported Pointcut Designators .............................................................. 192 Combining pointcut expressions .............................................................. 194 Sharing common pointcut definitions ........................................................ 194 Examples ............................................................................................... 196 Writing good pointcuts ............................................................................ 198 Declaring advice ............................................................................................. 199 Before advice ......................................................................................... 199 After returning advice .............................................................................. 200 After throwing advice .............................................................................. 200 After (finally) advice ................................................................................ 201 Around advice ........................................................................................ 202 Advice parameters .................................................................................. 203 Advice ordering ...................................................................................... 206 Introductions ................................................................................................... 206 Aspect instantiation models ............................................................................. 207 Example ......................................................................................................... 208 8.3. Schema-based AOP support ............................................................................ 209 Declaring an aspect ........................................................................................ 210 Declaring a pointcut ........................................................................................ 210 Declaring advice ............................................................................................. 212 Before advice ......................................................................................... 212 After returning advice .............................................................................. 212 After throwing advice .............................................................................. 213 After (finally) advice ................................................................................ 214 Around advice ........................................................................................ 214 Advice parameters .................................................................................. 215 Advice ordering ...................................................................................... 216 Introductions ................................................................................................... 217 Aspect instantiation models ............................................................................. 217 Advisors ......................................................................................................... 217 Example ......................................................................................................... 218 8.4. Choosing which AOP declaration style to use .................................................... 220 Spring AOP or full AspectJ? ........................................................................... 220 @AspectJ or XML for Spring AOP? ................................................................. 221 8.5. Mixing aspect types ......................................................................................... 222 8.6. Proxying mechanisms ...................................................................................... 222 Understanding AOP proxies ............................................................................ 223 Spring Framework 4.0.0.RELEASE Spring Framework Reference Documentation viii 8.7. Programmatic creation of @AspectJ Proxies ..................................................... 225 8.8. Using AspectJ with Spring applications ............................................................. 225 Using AspectJ to dependency inject domain objects with Spring ........................ 226 Unit testing @Configurable objects .......................................................... 228 Working with multiple application contexts ................................................ 228 Other Spring aspects for AspectJ .................................................................... 229 Configuring AspectJ aspects using Spring IoC ................................................. 229 Load-time weaving with AspectJ in the Spring Framework ................................. 230 A first example ....................................................................................... 231 Aspects .................................................................................................. 234 ' META-INF/aop.xml' ............................................................................... 234 Required libraries (JARS) ........................................................................ 234 Spring configuration ................................................................................ 235 Environment-specific configuration ........................................................... 237 8.9. Further Resources ........................................................................................... 239 9. Spring AOP APIs ....................................................................................................... 240 9.1. Introduction ..................................................................................................... 240 9.2. Pointcut API in Spring ...................................................................................... 240 Concepts ........................................................................................................ 240 Operations on pointcuts .................................................................................. 241 AspectJ expression pointcuts .......................................................................... 241 Convenience pointcut implementations ............................................................ 241 Static pointcuts ....................................................................................... 241 Dynamic pointcuts .................................................................................. 242 Pointcut superclasses ..................................................................................... 243 Custom pointcuts ............................................................................................ 243 9.3. Advice API in Spring ........................................................................................ 243 Advice lifecycles ............................................................................................. 243 Advice types in Spring .................................................................................... 244 Interception around advice ...................................................................... 244 Before advice ......................................................................................... 244 Throws advice ........................................................................................ 245 After Returning advice ............................................................................ 246 Introduction advice .................................................................................. 247 9.4. Advisor API in Spring ....................................................................................... 249 9.5. Using the ProxyFactoryBean to create AOP proxies ........................................... 250 Basics ............................................................................................................ 250 JavaBean properties ....................................................................................... 250 JDK- and CGLIB-based proxies ...................................................................... 251 Proxying interfaces ......................................................................................... 252 Proxying classes ............................................................................................ 254 Using global advisors ...................................................................................... 255 9.6. Concise proxy definitions ................................................................................. 255 9.7. Creating AOP proxies programmatically with the ProxyFactory ............................ 256 9.8. Manipulating advised objects ............................................................................ 257 9.9. Using the "auto-proxy" facility ........................................................................... 258 Autoproxy bean definitions .............................................................................. 258 BeanNameAutoProxyCreator ................................................................... 259 DefaultAdvisorAutoProxyCreator .............................................................. 259 AbstractAdvisorAutoProxyCreator ............................................................ 260 Spring Framework 4.0.0.RELEASE Spring Framework Reference Documentation ix Using metadata-driven auto-proxying ............................................................... 260 9.10. Using TargetSources ...................................................................................... 262 Hot swappable target sources ......................................................................... 263 Pooling target sources .................................................................................... 263 Prototype target sources ................................................................................. 265 ThreadLocal target sources ............................................................................. 265 9.11. Defining new Advice types ............................................................................. 265 9.12. Further resources ........................................................................................... 266 10. Testing ..................................................................................................................... 267 10.1. Introduction to Spring Testing ......................................................................... 267 10.2. Unit Testing ................................................................................................... 267 Mock Objects ................................................................................................. 267 Environment ........................................................................................... 267 JNDI ...................................................................................................... 267 Servlet API ............................................................................................. 267 Portlet API ............................................................................................. 268 Unit Testing support Classes .......................................................................... 268 General utilities ...................................................................................... 268 Spring MVC ........................................................................................... 268 10.3. Integration Testing ......................................................................................... 268 Overview ........................................................................................................ 268 Goals of Integration Testing ............................................................................ 269 Context management and caching ........................................................... 269 Dependency Injection of test fixtures ....................................................... 269 Transaction management ........................................................................ 270 Support classes for integration testing ..................................................... 270 JDBC Testing Support .................................................................................... 271 Annotations .................................................................................................... 271 Spring Testing Annotations ..................................................................... 271 Standard Annotation Support .................................................................. 276 Spring JUnit Testing Annotations ............................................................. 277 Meta-Annotation Support for Testing ........................................................ 278 Spring TestContext Framework ....................................................................... 279 Key abstractions ..................................................................................... 280 Context management .............................................................................. 281 Dependency injection of test fixtures ........................................................ 297 Testing request and session scoped beans .............................................. 299 Transaction management ........................................................................ 301 TestContext Framework support classes .................................................. 304 Spring MVC Test Framework .......................................................................... 306 Server-Side Tests ................................................................................... 306 Client-Side REST Tests .......................................................................... 312 PetClinic Example .......................................................................................... 313 10.4. Further Resources ......................................................................................... 314 IV. Data Access ..................................................................................................................... 316 11. Transaction Management .......................................................................................... 317 11.1. Introduction to Spring Framework transaction management .............................. 317 11.2. Advantages of the Spring Framework’s transaction support model ..................... 317 Global transactions ......................................................................................... 317 Local transactions ........................................................................................... 318 Spring Framework 4.0.0.RELEASE Spring Framework Reference Documentation x Spring Framework’s consistent programming model ......................................... 318 11.3. Understanding the Spring Framework transaction abstraction ............................ 319 11.4. Synchronizing resources with transactions ....................................................... 323 High-level synchronization approach ................................................................ 323 Low-level synchronization approach ................................................................. 323 TransactionAwareDataSourceProxy ................................................................. 324 11.5. Declarative transaction management ............................................................... 324 Understanding the Spring Framework’s declarative transaction implementation ... 325 Example of declarative transaction implementation ........................................... 326 Rolling back a declarative transaction .............................................................. 330 Configuring different transactional semantics for different beans ........................ 331 settings ....................................................................................... 333 Using @Transactional ..................................................................................... 335 @Transactional settings .......................................................................... 339 Multiple Transaction Managers with @Transactional ................................. 340 Custom shortcut annotations ................................................................... 341 Transaction propagation .................................................................................. 341 Required ................................................................................................ 342 RequiresNew .......................................................................................... 342 Nested ................................................................................................... 343 Advising transactional operations ..................................................................... 343 Using @Transactional with AspectJ ................................................................. 346 11.6. Programmatic transaction management ........................................................... 347 Using the TransactionTemplate ....................................................................... 347 Specifying transaction settings ................................................................ 349 Using the PlatformTransactionManager ............................................................ 349 11.7. Choosing between programmatic and declarative transaction management ........ 350 11.8. Application server-specific integration .............................................................. 350 IBM WebSphere ............................................................................................. 351 Oracle WebLogic Server ................................................................................. 351 11.9. Solutions to common problems ....................................................................... 351 Use of the wrong transaction manager for a specific DataSource ....................... 351 11.10. Further Resources ....................................................................................... 351 12. DAO support ............................................................................................................ 352 12.1. Introduction .................................................................................................... 352 12.2. Consistent exception hierarchy ....................................................................... 352 12.3. Annotations used for configuring DAO or Repository classes ............................ 353 13. Data access with JDBC ............................................................................................ 355 13.1. Introduction to Spring Framework JDBC .......................................................... 355 Choosing an approach for JDBC database access ........................................... 355 Package hierarchy .......................................................................................... 356 13.2. Using the JDBC core classes to control basic JDBC processing and error handling ................................................................................................................. 357 JdbcTemplate ................................................................................................. 357 Examples of JdbcTemplate class usage ................................................... 357 JdbcTemplate best practices ................................................................... 359 NamedParameterJdbcTemplate ....................................................................... 361 SQLExceptionTranslator .................................................................................. 363 Executing statements ...................................................................................... 365 Running queries ............................................................................................. 365 Spring Framework 4.0.0.RELEASE Spring Framework Reference Documentation xi Updating the database .................................................................................... 366 Retrieving auto-generated keys ....................................................................... 367 13.3. Controlling database connections .................................................................... 367 DataSource .................................................................................................... 367 DataSourceUtils .............................................................................................. 369 SmartDataSource ........................................................................................... 369 AbstractDataSource ........................................................................................ 369 SingleConnectionDataSource .......................................................................... 369 DriverManagerDataSource .............................................................................. 369 TransactionAwareDataSourceProxy ................................................................. 370 DataSourceTransactionManager ...................................................................... 370 NativeJdbcExtractor ........................................................................................ 370 13.4. JDBC batch operations .................................................................................. 371 Basic batch operations with the JdbcTemplate ................................................. 371 Batch operations with a List of objects ............................................................. 372 Batch operations with multiple batches ............................................................ 373 13.5. Simplifying JDBC operations with the SimpleJdbc classes ................................ 374 Inserting data using SimpleJdbcInsert .............................................................. 374 Retrieving auto-generated keys using SimpleJdbcInsert .................................... 375 Specifying columns for a SimpleJdbcInsert ...................................................... 376 Using SqlParameterSource to provide parameter values ................................... 376 Calling a stored procedure with SimpleJdbcCall ............................................... 377 Explicitly declaring parameters to use for a SimpleJdbcCall ............................... 379 How to define SqlParameters .......................................................................... 380 Calling a stored function using SimpleJdbcCall ................................................. 381 Returning ResultSet/REF Cursor from a SimpleJdbcCall ................................... 381 13.6. Modeling JDBC operations as Java objects ..................................................... 382 SqlQuery ........................................................................................................ 383 MappingSqlQuery ........................................................................................... 383 SqlUpdate ...................................................................................................... 384 StoredProcedure ............................................................................................. 385 13.7. Common problems with parameter and data value handling .............................. 388 Providing SQL type information for parameters ................................................. 389 Handling BLOB and CLOB objects .................................................................. 389 Passing in lists of values for IN clause ............................................................ 390 Handling complex types for stored procedure calls ........................................... 391 13.8. Embedded database support .......................................................................... 392 Why use an embedded database? .................................................................. 392 Creating an embedded database instance using Spring XML ............................ 392 Creating an embedded database instance programmatically .............................. 392 Extending the embedded database support ...................................................... 393 Using HSQL ................................................................................................... 393 Using H2 ........................................................................................................ 393 Using Derby ................................................................................................... 393 Testing data access logic with an embedded database ..................................... 393 13.9. Initializing a DataSource ................................................................................. 394 Initializing a database instance using Spring XML ............................................. 394 Initialization of Other Components that Depend on the Database ............... 395 14. Object Relational Mapping (ORM) Data Access .......................................................... 397 14.1. Introduction to ORM with Spring ..................................................................... 397 Spring Framework 4.0.0.RELEASE Spring Framework Reference Documentation xii 14.2. General ORM integration considerations ......................................................... 398 Resource and transaction management ........................................................... 398 Exception translation ....................................................................................... 399 14.3. Hibernate ....................................................................................................... 399 SessionFactory setup in a Spring container ...................................................... 400 Implementing DAOs based on plain Hibernate 3 API ........................................ 400 Declarative transaction demarcation ................................................................ 402 Programmatic transaction demarcation ............................................................ 404 Transaction management strategies ................................................................ 405 Comparing container-managed and locally defined resources ............................ 407 Spurious application server warnings with Hibernate ......................................... 408 14.4. JDO .............................................................................................................. 409 PersistenceManagerFactory setup ................................................................... 409 Implementing DAOs based on the plain JDO API ............................................. 410 Transaction management ................................................................................ 412 JdoDialect ...................................................................................................... 413 14.5. JPA ............................................................................................................... 414 Three options for JPA setup in a Spring environment ........................................ 414 LocalEntityManagerFactoryBean .............................................................. 414 Obtaining an EntityManagerFactory from JNDI ......................................... 415 LocalContainerEntityManagerFactoryBean ............................................... 415 Dealing with multiple persistence units ..................................................... 417 Implementing DAOs based on plain JPA .......................................................... 418 Transaction Management ................................................................................ 420 JpaDialect ...................................................................................................... 421 15. Marshalling XML using O/X Mappers ......................................................................... 423 15.1. Introduction .................................................................................................... 423 Ease of configuration ...................................................................................... 423 Consistent Interfaces ...................................................................................... 423 Consistent Exception Hierarchy ....................................................................... 423 15.2. Marshaller and Unmarshaller .......................................................................... 423 Marshaller ...................................................................................................... 423 Unmarshaller .................................................................................................. 424 XmlMappingException ..................................................................................... 425 15.3. Using Marshaller and Unmarshaller ................................................................. 425 15.4. XML Schema-based Configuration .................................................................. 427 15.5. JAXB ............................................................................................................. 427 Jaxb2Marshaller ............................................................................................. 428 XML Schema-based Configuration ........................................................... 428 15.6. Castor ........................................................................................................... 429 CastorMarshaller ............................................................................................ 429 Mapping ......................................................................................................... 429 XML Schema-based Configuration ........................................................... 429 15.7. XMLBeans ..................................................................................................... 430 XmlBeansMarshaller ....................................................................................... 430 XML Schema-based Configuration ........................................................... 430 15.8. JiBX .............................................................................................................. 431 JibxMarshaller ................................................................................................ 431 XML Schema-based Configuration ........................................................... 431 15.9. XStream ........................................................................................................ 432 Spring Framework 4.0.0.RELEASE Spring Framework Reference Documentation xiii XStreamMarshaller ......................................................................................... 432 V. The Web ........................................................................................................................... 434 16. Web MVC framework ................................................................................................ 435 16.1. Introduction to Spring Web MVC framework .................................................... 435 Features of Spring Web MVC ......................................................................... 436 Pluggability of other MVC implementations ...................................................... 437 16.2. The DispatcherServlet .................................................................................... 437 Special Bean Types In the WebApplicationContext ........................................... 440 Default DispatcherServlet Configuration ........................................................... 441 DispatcherServlet Processing Sequence .......................................................... 441 16.3. Implementing Controllers ................................................................................ 443 Defining a controller with @Controller .............................................................. 443 Mapping Requests With Using @RequestMapping ........................................... 444 New Support Classes for @RequestMapping methods in Spring MVC 3.1 .. 446 URI Template Patterns ........................................................................... 447 URI Template Patterns with Regular Expressions ..................................... 448 Path Patterns ......................................................................................... 449 Patterns with Placeholders ...................................................................... 449 Matrix Variables ...................................................................................... 449 Consumable Media Types ....................................................................... 450 Producible Media Types .......................................................................... 451 Request Parameters and Header Values ................................................. 451 Defining @RequestMapping handler methods .................................................. 452 Supported method argument types .......................................................... 452 Supported method return types ............................................................... 454 Binding request parameters to method parameters with @RequestParam ... 455 Mapping the request body with the @RequestBody annotation .................. 456 Mapping the response body with the @ResponseBody annotation ............. 457 Creating REST Controllers with the @RestController annotation ................ 457 Using HttpEntity ...................................................................................... 457 Using @ModelAttribute on a method ....................................................... 458 Using @ModelAttribute on a method argument ......................................... 459 Using @SessionAttributes to store model attributes in the HTTP session between requests ................................................................................... 461 Specifying redirect and flash attributes ..................................................... 461 Working with "application/x-www-form-urlencoded" data ............................ 462 Mapping cookie values with the @CookieValue annotation ........................ 462 Mapping request header attributes with the @RequestHeader annotation ... 463 Method Parameters And Type Conversion ............................................... 463 Customizing WebDataBinder initialization ................................................. 464 Support for the Last-Modified Response Header To Facilitate Content Caching ................................................................................................. 465 Assisting Controllers with the @ControllerAdvice annotation ...................... 465 Asynchronous Request Processing .................................................................. 466 Exception Handling for Async Requests ................................................... 467 Intercepting Async Requests ................................................................... 467 Configuration for Async Request Processing ............................................ 468 Testing Controllers ......................................................................................... 469 16.4. Handler mappings .......................................................................................... 469 Intercepting requests with a HandlerInterceptor ................................................ 469 Spring Framework 4.0.0.RELEASE Spring Framework Reference Documentation xiv 16.5. Resolving views ............................................................................................. 471 Resolving views with the ViewResolver interface .............................................. 471 Chaining ViewResolvers ................................................................................. 473 Redirecting to views ....................................................................................... 474 RedirectView .......................................................................................... 474 The redirect: prefix ................................................................................. 475 The forward: prefix ................................................................................. 475 ContentNegotiatingViewResolver ..................................................................... 475 16.6. Using flash attributes ..................................................................................... 478 16.7. Building URIs ................................................................................................. 479 16.8. Building URIs to Controllers and methods ....................................................... 480 16.9. Using locales ................................................................................................. 480 Obtaining Time Zone Information .................................................................... 481 AcceptHeaderLocaleResolver .......................................................................... 481 CookieLocaleResolver ..................................................................................... 481 SessionLocaleResolver ................................................................................... 481 LocaleChangeInterceptor ................................................................................ 482 16.10. Using themes ............................................................................................... 482 Overview of themes ........................................................................................ 482 Defining themes ............................................................................................. 482 Theme resolvers ............................................................................................. 483 16.11. Spring’s multipart (file upload) support ........................................................... 483 Introduction .................................................................................................... 483 Using a MultipartResolver with Commons FileUpload ........................................ 484 Using a MultipartResolver with Servlet 3.0 ....................................................... 484 Handling a file upload in a form ...................................................................... 484 Handling a file upload request from programmatic clients .................................. 486 16.12. Handling exceptions ..................................................................................... 486 HandlerExceptionResolver ............
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值