下面列出了怎么用org.springframework.web.bind.WebDataBinder的API类实例代码及写法,或者点击链接到github查看源代码。
/**
* Resolve the argument from the model or if not found instantiate it with
* its default if it is available. The model attribute is then populated
* with request values via data binding and optionally validated
* if {@code @java.validation.Valid} is present on the argument.
* @throws BindException if data binding and validation result in an error
* and the next method parameter is not of type {@link Errors}.
* @throws Exception if WebDataBinder initialization fails.
*/
@Override
public final Object resolveArgument(MethodParameter parameter, ModelAndViewContainer mavContainer,
NativeWebRequest webRequest, WebDataBinderFactory binderFactory) throws Exception {
String name = ModelFactory.getNameForParameter(parameter);
Object attribute = (mavContainer.containsAttribute(name) ?
mavContainer.getModel().get(name) : createAttribute(name, parameter, binderFactory, webRequest));
WebDataBinder binder = binderFactory.createBinder(webRequest, attribute, name);
if (binder.getTarget() != null) {
bindRequestParameters(binder, webRequest);
validateIfApplicable(binder, parameter);
if (binder.getBindingResult().hasErrors() && isBindExceptionRequired(binder, parameter)) {
throw new BindException(binder.getBindingResult());
}
}
// Add resolved attribute and BindingResult at the end of the model
Map<String, Object> bindingResultModel = binder.getBindingResult().getModel();
mavContainer.removeAttributes(bindingResultModel);
mavContainer.addAllAttributes(bindingResultModel);
return binder.convertIfNecessary(binder.getTarget(), parameter.getParameterType(), parameter);
}
@Override
protected void validateIfApplicable(WebDataBinder binder, MethodParameter parameter) {
if (AnnotatedElementUtils.hasAnnotation(parameter.getContainingClass(), ApiController.class)) {
binder.validate();
} else {
Annotation[] annotations = parameter.getParameterAnnotations();
for (Annotation ann : annotations) {
Validated validatedAnn = AnnotationUtils.getAnnotation(ann, Validated.class);
if (validatedAnn != null || ann.annotationType().getSimpleName().startsWith("Valid")) {
Object hints = (validatedAnn != null ? validatedAnn.value() : AnnotationUtils.getValue(ann));
Object[] validationHints = (hints instanceof Object[] ? (Object[])hints : new Object[] {hints});
binder.validate(validationHints);
break;
}
}
}
}
@Test
public void updateModelWhenRedirecting() throws Exception {
String attributeName = "sessionAttr";
String attribute = "value";
ModelAndViewContainer container = new ModelAndViewContainer();
container.addAttribute(attributeName, attribute);
String queryParam = "123";
String queryParamName = "q";
container.setRedirectModel(new ModelMap(queryParamName, queryParam));
container.setRedirectModelScenario(true);
WebDataBinder dataBinder = new WebDataBinder(attribute, attributeName);
WebDataBinderFactory binderFactory = mock(WebDataBinderFactory.class);
given(binderFactory.createBinder(this.webRequest, attribute, attributeName)).willReturn(dataBinder);
ModelFactory modelFactory = new ModelFactory(null, binderFactory, this.sessionAttrsHandler);
modelFactory.updateModel(this.webRequest, container);
assertEquals(queryParam, container.getModel().get(queryParamName));
assertEquals(1, container.getModel().size());
assertEquals(attribute, this.sessionAttributeStore.retrieveAttribute(this.webRequest, attributeName));
}
@Override
protected int writeTagContent(TagWriter tagWriter) throws JspException {
super.writeTagContent(tagWriter);
if (!isDisabled()) {
// Write out the 'field was present' marker.
tagWriter.startTag("input");
tagWriter.writeAttribute("type", "hidden");
String name = WebDataBinder.DEFAULT_FIELD_MARKER_PREFIX + getName();
tagWriter.writeAttribute("name", name);
tagWriter.writeAttribute("value", processFieldValue(name, "on", getInputType()));
tagWriter.endTag();
}
return SKIP_BODY;
}
@Before
public void setUp() throws Exception {
controller = new WidgetController();
service = createMock(WidgetService.class);
controller.setWidgetService(service);
widgetValidator = new UpdateWidgetValidator(service);
controller.setWidgetValidator(widgetValidator);
validToken = AdminControllerUtil.generateSessionToken();
preferenceService = createMock(PortalPreferenceService.class);
controller.setPreferenceService(preferenceService);
categoryService = createMock(CategoryService.class);
controller.setCategoryService(categoryService);
categories = new ArrayList<Category>();
categories.add(new CategoryImpl());
categories.add(new CategoryImpl());
webDataBinder = createMock(WebDataBinder.class);
categoryEditor = new CategoryEditor(categoryService);
controller.setCategoryEditor(categoryEditor);
}
@InitBinder
@Override
protected void initBinder(WebDataBinder binder) {
super.initBinder(binder);
binder.registerCustomEditor(Collection.class, "userList", new CustomCollectionEditor(Collection.class) {
@Override
protected Object convertElement(Object element) {
Long id = null;
if (element instanceof String && !((String) element).equals("")) {
//From the JSP 'element' will be a String
try {
id = Long.parseLong((String) element);
} catch (NumberFormatException e) {
Logger.getLogger(this.getClass()).warn("Element was " + ((String) element));
}
} else if (element instanceof Long) {
//From the database 'element' will be a Long
id = (Long) element;
}
return id != null ? getUserDataService().read(id) : null;
}
});
}
/**
* Validate the specified candidate value if applicable.
* <p>The default implementation checks for {@code @javax.validation.Valid},
* Spring's {@link org.springframework.validation.annotation.Validated},
* and custom annotations whose name starts with "Valid".
* @param binder the DataBinder to be used
* @param parameter the method parameter declaration
* @param targetType the target type
* @param fieldName the name of the field
* @param value the candidate value
* @since 5.1
* @see #validateIfApplicable(WebDataBinder, MethodParameter)
* @see SmartValidator#validateValue(Class, String, Object, Errors, Object...)
*/
protected void validateValueIfApplicable(WebDataBinder binder, MethodParameter parameter,
Class<?> targetType, String fieldName, @Nullable Object value) {
for (Annotation ann : parameter.getParameterAnnotations()) {
Object[] validationHints = determineValidationHints(ann);
if (validationHints != null) {
for (Validator validator : binder.getValidators()) {
if (validator instanceof SmartValidator) {
try {
((SmartValidator) validator).validateValue(targetType, fieldName, value,
binder.getBindingResult(), validationHints);
}
catch (IllegalArgumentException ex) {
// No corresponding field on the target class...
}
}
}
break;
}
}
}
@InitBinder("employeeForm")
public void initBinder(WebDataBinder binder){
binder.setValidator(employeeValidator);
binder.registerCustomEditor(Date.class, new DateEditor());
binder.registerCustomEditor(Integer.class, "age", new AgeEditor());
}
/**
* Create a new {@link WebDataBinder} for the given target object and
* initialize it through a {@link WebBindingInitializer}.
* @throws Exception in case of invalid state or arguments
*/
@Override
public final WebDataBinder createBinder(NativeWebRequest webRequest, Object target, String objectName)
throws Exception {
WebDataBinder dataBinder = createBinderInstance(target, objectName, webRequest);
if (this.initializer != null) {
this.initializer.initBinder(dataBinder, webRequest);
}
initBinder(dataBinder, webRequest);
return dataBinder;
}
@Test
public void createBinder() throws Exception {
MockServerWebExchange exchange = MockServerWebExchange.from(MockServerHttpRequest.get("/"));
BindingContext context = createBindingContext("initBinder", WebDataBinder.class);
WebDataBinder dataBinder = context.createDataBinder(exchange, null, null);
assertNotNull(dataBinder.getDisallowedFields());
assertEquals("id", dataBinder.getDisallowedFields()[0]);
}
@Override
public WebDataBinder createBinder(NativeWebRequest webRequest, Object target, String objectName) throws Exception {
LocalValidatorFactoryBean validator = new LocalValidatorFactoryBean();
validator.afterPropertiesSet();
WebDataBinder dataBinder = new WebDataBinder(target, objectName);
dataBinder.setValidator(validator);
return dataBinder;
}
/**
* Initiates the data binding from web request parameters to JavaBeans objects
*
* @param webDataBinder - a Web Data Binder instance
*/
@InitBinder
public void initBinder(WebDataBinder webDataBinder) {
SimpleDateFormat dateFormat = new SimpleDateFormat(DATE_FORMAT);
dateFormat.setLenient(true);
webDataBinder.registerCustomEditor(Date.class, new CustomDateEditor(dateFormat, true));
}
@Test
public void createBinder() throws Exception {
MockServerWebExchange exchange = MockServerWebExchange.from(MockServerHttpRequest.get("/"));
BindingContext context = createBindingContext("initBinder", WebDataBinder.class);
WebDataBinder dataBinder = context.createDataBinder(exchange, null, null);
assertNotNull(dataBinder.getDisallowedFields());
assertEquals("id", dataBinder.getDisallowedFields()[0]);
}
@Test
public void createBinderWithGlobalInitialization() throws Exception {
ConversionService conversionService = new DefaultFormattingConversionService();
bindingInitializer.setConversionService(conversionService);
MockServerWebExchange exchange = MockServerWebExchange.from(MockServerHttpRequest.get("/"));
BindingContext context = createBindingContext("initBinder", WebDataBinder.class);
WebDataBinder dataBinder = context.createDataBinder(exchange, null, null);
assertSame(conversionService, dataBinder.getConversionService());
}
/**
* If using a multi-select, a hidden element is needed to make sure all
* items are correctly unselected on the server-side in response to a
* {@code null} post.
*/
private void writeHiddenTagIfNecessary(TagWriter tagWriter) throws JspException {
if (isMultiple()) {
tagWriter.startTag("input");
tagWriter.writeAttribute("type", "hidden");
String name = WebDataBinder.DEFAULT_FIELD_MARKER_PREFIX + getName();
tagWriter.writeAttribute("name", name);
tagWriter.writeAttribute("value", processFieldValue(name, "1", "hidden"));
tagWriter.endTag();
}
}
private void doBind(WebDataBinder binder, NativeWebRequest webRequest, boolean validate,
Object[] validationHints, boolean failOnErrors) throws Exception {
doBind(binder, webRequest);
if (validate) {
binder.validate(validationHints);
}
if (failOnErrors && binder.getBindingResult().hasErrors()) {
throw new BindException(binder.getBindingResult());
}
}
/**
* 将前台传递过来的日期格式的字符串,自动转化为Date类型
*/
@InitBinder
public void initBinder(WebDataBinder binder) {
// Date 类型转换
binder.registerCustomEditor(Date.class, new PropertyEditorSupport() {
@Override
public void setAsText(String text) {
setValue(DateUtils.parseDate(text));
}
});
}
protected void initBinder(Object handler, String attrName, WebDataBinder binder, NativeWebRequest webRequest)
throws Exception {
if (this.bindingInitializer != null) {
this.bindingInitializer.initBinder(binder, webRequest);
}
if (handler != null) {
Set<Method> initBinderMethods = this.methodResolver.getInitBinderMethods();
if (!initBinderMethods.isEmpty()) {
boolean debug = logger.isDebugEnabled();
for (Method initBinderMethod : initBinderMethods) {
Method methodToInvoke = BridgeMethodResolver.findBridgedMethod(initBinderMethod);
String[] targetNames = AnnotationUtils.findAnnotation(initBinderMethod, InitBinder.class).value();
if (targetNames.length == 0 || Arrays.asList(targetNames).contains(attrName)) {
Object[] initBinderArgs =
resolveInitBinderArguments(handler, methodToInvoke, binder, webRequest);
if (debug) {
logger.debug("Invoking init-binder method: " + methodToInvoke);
}
ReflectionUtils.makeAccessible(methodToInvoke);
Object returnValue = methodToInvoke.invoke(handler, initBinderArgs);
if (returnValue != null) {
throw new IllegalStateException(
"InitBinder methods must not have a return value: " + methodToInvoke);
}
}
}
}
}
}
@InitBinder
public void initBinder(WebDataBinder binder, @PathVariable("hotel") String hotel) {
assertEquals("Invalid path variable value", "42", hotel);
binder.initBeanPropertyAccess();
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd");
dateFormat.setLenient(false);
binder.registerCustomEditor(Date.class, new CustomDateEditor(dateFormat, false));
}
@Test
public void createBinderWithGlobalInitialization() throws Exception {
ConversionService conversionService = new DefaultFormattingConversionService();
bindingInitializer.setConversionService(conversionService);
WebDataBinderFactory factory = createFactory("initBinder", WebDataBinder.class);
WebDataBinder dataBinder = factory.createBinder(this.webRequest, null, null);
assertSame(conversionService, dataBinder.getConversionService());
}
@Override
public WebDataBinder createBinder(NativeWebRequest webRequest, @Nullable Object target,
String objectName) throws Exception {
LocalValidatorFactoryBean validator = new LocalValidatorFactoryBean();
validator.afterPropertiesSet();
WebDataBinder dataBinder = new WebDataBinder(target, objectName);
dataBinder.setValidator(validator);
return dataBinder;
}
@InitBinder({"myCommand", "date"})
public void initBinder(WebDataBinder binder, String date, @RequestParam("date") String[] date2) {
LocalValidatorFactoryBean vf = new LocalValidatorFactoryBean();
vf.afterPropertiesSet();
binder.setValidator(vf);
assertEquals("2007-10-02", date);
assertEquals(1, date2.length);
assertEquals("2007-10-02", date2[0]);
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd");
dateFormat.setLenient(false);
binder.registerCustomEditor(Date.class, new CustomDateEditor(dateFormat, false));
}
@InitBinder
public void initBinder(WebDataBinder binder) {
// Date - dd/MM/yyyy
SimpleDateFormat dateFormat = new SimpleDateFormat("dd/MM/yyyy");
binder.registerCustomEditor(Date.class, new CustomDateEditor(
dateFormat, false));
}
@InitBinder
public void initBinder(WebDataBinder binder) {
binder.initDirectFieldAccess();
binder.setConversionService(new DefaultFormattingConversionService());
LocalValidatorFactoryBean vf = new LocalValidatorFactoryBean();
vf.afterPropertiesSet();
binder.setValidator(vf);
}
/**
* Validate the request part if applicable.
* <p>The default implementation checks for {@code @javax.validation.Valid},
* Spring's {@link org.springframework.validation.annotation.Validated},
* and custom annotations whose name starts with "Valid".
* @param binder the DataBinder to be used
* @param methodParam the method parameter
* @see #isBindExceptionRequired
* @since 4.1.5
*/
protected void validateIfApplicable(WebDataBinder binder, MethodParameter methodParam) {
Annotation[] annotations = methodParam.getParameterAnnotations();
for (Annotation ann : annotations) {
Validated validatedAnn = AnnotationUtils.getAnnotation(ann, Validated.class);
if (validatedAnn != null || ann.annotationType().getSimpleName().startsWith("Valid")) {
Object hints = (validatedAnn != null ? validatedAnn.value() : AnnotationUtils.getValue(ann));
Object[] validationHints = (hints instanceof Object[] ? (Object[]) hints : new Object[] {hints});
binder.validate(validationHints);
break;
}
}
}
@Override
public void initBinder(WebDataBinder binder, WebRequest request) {
assertNotNull(request.getLocale());
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd");
dateFormat.setLenient(false);
binder.registerCustomEditor(Date.class, new CustomDateEditor(dateFormat, false));
}
@InitBinder
public void initBinder(WebDataBinder binder, @PathVariable("hotel") String hotel) {
assertEquals("Invalid path variable value", "42", hotel);
binder.initBeanPropertyAccess();
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd");
dateFormat.setLenient(false);
binder.registerCustomEditor(Date.class, new CustomDateEditor(dateFormat, false));
}
@Test
public void noUriTemplateVars() throws Exception {
TestBean target = new TestBean();
WebDataBinder binder = new ExtendedServletRequestDataBinder(target, "");
((ServletRequestDataBinder) binder).bind(request);
assertEquals(null, target.getName());
assertEquals(0, target.getAge());
}
@InitBinder
public void initBinder(WebDataBinder binder) {
// Date - dd/MM/yyyy
SimpleDateFormat dateFormat = new SimpleDateFormat("dd/MM/yyyy");
binder.registerCustomEditor(Date.class, new CustomDateEditor(
dateFormat, false));
}
/**
* Determine whether the given {@code @InitBinder} method should be used
* to initialize the given {@link WebDataBinder} instance. By default we
* check the specified attribute names in the annotation value, if any.
*/
protected boolean isBinderMethodApplicable(HandlerMethod initBinderMethod, WebDataBinder dataBinder) {
InitBinder ann = initBinderMethod.getMethodAnnotation(InitBinder.class);
Assert.state(ann != null, "No InitBinder annotation");
String[] names = ann.value();
return (ObjectUtils.isEmpty(names) || ObjectUtils.containsElement(names, dataBinder.getObjectName()));
}