Browse Source
git-svn-id: https://src.springframework.org/svn/spring-framework/trunk@1345 50f2f4bb-b051-0410-bef5-90022cba6387pull/1/head
4 changed files with 311 additions and 14 deletions
@ -0,0 +1,95 @@ |
|||||||
|
/* |
||||||
|
* Copyright 2004-2009 the original author or authors. |
||||||
|
* |
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License"); |
||||||
|
* you may not use this file except in compliance with the License. |
||||||
|
* You may obtain a copy of the License at |
||||||
|
* |
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
* |
||||||
|
* Unless required by applicable law or agreed to in writing, software |
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS, |
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
||||||
|
* See the License for the specific language governing permissions and |
||||||
|
* limitations under the License. |
||||||
|
*/ |
||||||
|
package org.springframework.ui.binding.support; |
||||||
|
|
||||||
|
import java.util.ArrayList; |
||||||
|
import java.util.List; |
||||||
|
import java.util.Map; |
||||||
|
|
||||||
|
import org.springframework.ui.binding.UserValue; |
||||||
|
|
||||||
|
/** |
||||||
|
* A binder designed for use in HTTP (web) environments. |
||||||
|
* Suited for binding user-provided HTTP query parameters to model properties. |
||||||
|
* @author Keith Donald |
||||||
|
* @param <M> The type of model object this binder binds to |
||||||
|
* @see #setFieldDefaultPrefix(String) |
||||||
|
* @see #setFieldMarkerPrefix(String) |
||||||
|
*/ |
||||||
|
public class WebBinder<M> extends GenericBinder<M> { |
||||||
|
|
||||||
|
private String fieldMarkerPrefix = "_"; |
||||||
|
|
||||||
|
private String fieldDefaultPrefix = "!"; |
||||||
|
|
||||||
|
/** |
||||||
|
* Creates a new web binder for the model object. |
||||||
|
* @param model the model object containing properties this binder will bind to |
||||||
|
*/ |
||||||
|
public WebBinder(M model) { |
||||||
|
super(model); |
||||||
|
} |
||||||
|
|
||||||
|
/** |
||||||
|
* Configure the prefix for determining default field values. |
||||||
|
* Default is '!'. |
||||||
|
*/ |
||||||
|
public void setFieldDefaultPrefix(String fieldDefaultPrefix) { |
||||||
|
this.fieldDefaultPrefix = fieldDefaultPrefix; |
||||||
|
} |
||||||
|
|
||||||
|
/** |
||||||
|
* Configure the prefix for determining empty fields. |
||||||
|
* Default is '_'. |
||||||
|
*/ |
||||||
|
public void setFieldMarkerPrefix(String fieldMarkerPrefix) { |
||||||
|
this.fieldMarkerPrefix = fieldMarkerPrefix; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public List<UserValue> createUserValues(Map<String, ? extends Object> userMap) { |
||||||
|
List<UserValue> values = new ArrayList<UserValue>(); |
||||||
|
for (Map.Entry<String, ? extends Object> entry : userMap.entrySet()) { |
||||||
|
String field = entry.getKey(); |
||||||
|
Object value = entry.getValue(); |
||||||
|
if (field.startsWith(fieldDefaultPrefix)) { |
||||||
|
field = field.substring(fieldDefaultPrefix.length()); |
||||||
|
if (!userMap.containsKey(field)) { |
||||||
|
values.add(new UserValue(field, value)); |
||||||
|
} |
||||||
|
} else if (field.startsWith(fieldMarkerPrefix)) { |
||||||
|
field = field.substring(fieldMarkerPrefix.length()); |
||||||
|
if (!userMap.containsKey(field) && !userMap.containsKey(fieldDefaultPrefix + field)) { |
||||||
|
value = getEmptyValue((BindingImpl) getBinding(field)); |
||||||
|
values.add(new UserValue(field, value)); |
||||||
|
} |
||||||
|
} else { |
||||||
|
values.add(new UserValue(entry.getKey(), entry.getValue())); |
||||||
|
} |
||||||
|
} |
||||||
|
return values; |
||||||
|
} |
||||||
|
|
||||||
|
protected Object getEmptyValue(BindingImpl binding) { |
||||||
|
Class<?> type = binding.getValueType(); |
||||||
|
if (boolean.class.equals(type) || Boolean.class.equals(type)) { |
||||||
|
return Boolean.FALSE; |
||||||
|
} else { |
||||||
|
return null; |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
} |
||||||
@ -0,0 +1,197 @@ |
|||||||
|
package org.springframework.ui.binding.support; |
||||||
|
|
||||||
|
import static org.junit.Assert.assertEquals; |
||||||
|
|
||||||
|
import java.math.BigDecimal; |
||||||
|
import java.text.ParseException; |
||||||
|
import java.util.Date; |
||||||
|
import java.util.LinkedHashMap; |
||||||
|
import java.util.List; |
||||||
|
import java.util.Locale; |
||||||
|
import java.util.Map; |
||||||
|
|
||||||
|
import org.junit.After; |
||||||
|
import org.junit.Before; |
||||||
|
import org.junit.Test; |
||||||
|
import org.springframework.context.i18n.LocaleContextHolder; |
||||||
|
import org.springframework.ui.binding.Binder; |
||||||
|
import org.springframework.ui.binding.BindingConfiguration; |
||||||
|
import org.springframework.ui.binding.BindingResult; |
||||||
|
import org.springframework.ui.binding.UserValue; |
||||||
|
import org.springframework.ui.format.date.DateFormatter; |
||||||
|
import org.springframework.ui.format.number.CurrencyAnnotationFormatterFactory; |
||||||
|
import org.springframework.ui.format.number.CurrencyFormat; |
||||||
|
|
||||||
|
public class WebBinderTests { |
||||||
|
|
||||||
|
@Before |
||||||
|
public void setUp() { |
||||||
|
LocaleContextHolder.setLocale(Locale.US); |
||||||
|
} |
||||||
|
|
||||||
|
@After |
||||||
|
public void tearDown() { |
||||||
|
LocaleContextHolder.setLocale(null); |
||||||
|
} |
||||||
|
|
||||||
|
@Test |
||||||
|
public void bindUserValuesCreatedFromUserMap() throws ParseException { |
||||||
|
Binder<TestBean> binder = new WebBinder<TestBean>(new TestBean()); |
||||||
|
binder.add(new CurrencyAnnotationFormatterFactory()); |
||||||
|
binder.add(new BindingConfiguration("date", new DateFormatter())); |
||||||
|
Map<String, String> userMap = new LinkedHashMap<String, String>(); |
||||||
|
userMap.put("string", "test"); |
||||||
|
userMap.put("_integer", "doesn't matter"); |
||||||
|
userMap.put("_bool", "doesn't matter"); |
||||||
|
userMap.put("!date", "2009-06-10"); |
||||||
|
userMap.put("!currency", "$5.00"); |
||||||
|
userMap.put("_currency", "doesn't matter"); |
||||||
|
userMap.put("_addresses", "doesn't matter"); |
||||||
|
List<UserValue> values = binder.createUserValues(userMap); |
||||||
|
List<BindingResult> results = binder.bind(values); |
||||||
|
assertEquals(6, results.size()); |
||||||
|
assertEquals("test", results.get(0).getUserValue()); |
||||||
|
assertEquals(null, results.get(1).getUserValue()); |
||||||
|
assertEquals(Boolean.FALSE, results.get(2).getUserValue()); |
||||||
|
assertEquals("2009-06-10", results.get(3).getUserValue()); |
||||||
|
assertEquals("$5.00", results.get(4).getUserValue()); |
||||||
|
assertEquals(null, results.get(5).getUserValue()); |
||||||
|
|
||||||
|
assertEquals("test", binder.getModel().getString()); |
||||||
|
assertEquals(0, binder.getModel().getInteger()); |
||||||
|
assertEquals(new DateFormatter().parse("2009-06-10", Locale.US), binder.getModel().getDate()); |
||||||
|
assertEquals(false, binder.getModel().isBool()); |
||||||
|
assertEquals(new BigDecimal("5.00"), binder.getModel().getCurrency()); |
||||||
|
assertEquals(null, binder.getModel().getAddresses()); |
||||||
|
} |
||||||
|
|
||||||
|
public static enum FooEnum { |
||||||
|
BAR, BAZ, BOOP; |
||||||
|
} |
||||||
|
|
||||||
|
public static class TestBean { |
||||||
|
private String string; |
||||||
|
private int integer; |
||||||
|
private boolean bool; |
||||||
|
private Date date; |
||||||
|
private FooEnum foo; |
||||||
|
private BigDecimal currency; |
||||||
|
private List<FooEnum> foos; |
||||||
|
private List<Address> addresses; |
||||||
|
|
||||||
|
public String getString() { |
||||||
|
return string; |
||||||
|
} |
||||||
|
|
||||||
|
public void setString(String string) { |
||||||
|
this.string = string; |
||||||
|
} |
||||||
|
|
||||||
|
public int getInteger() { |
||||||
|
return integer; |
||||||
|
} |
||||||
|
|
||||||
|
public void setInteger(int integer) { |
||||||
|
this.integer = integer; |
||||||
|
} |
||||||
|
|
||||||
|
public boolean isBool() { |
||||||
|
return bool; |
||||||
|
} |
||||||
|
|
||||||
|
public void setBool(boolean bool) { |
||||||
|
this.bool = bool; |
||||||
|
} |
||||||
|
|
||||||
|
public Date getDate() { |
||||||
|
return date; |
||||||
|
} |
||||||
|
|
||||||
|
public void setDate(Date date) { |
||||||
|
this.date = date; |
||||||
|
} |
||||||
|
|
||||||
|
public FooEnum getFoo() { |
||||||
|
return foo; |
||||||
|
} |
||||||
|
|
||||||
|
public void setFoo(FooEnum foo) { |
||||||
|
this.foo = foo; |
||||||
|
} |
||||||
|
|
||||||
|
@CurrencyFormat |
||||||
|
public BigDecimal getCurrency() { |
||||||
|
return currency; |
||||||
|
} |
||||||
|
|
||||||
|
public void setCurrency(BigDecimal currency) { |
||||||
|
this.currency = currency; |
||||||
|
} |
||||||
|
|
||||||
|
public List<FooEnum> getFoos() { |
||||||
|
return foos; |
||||||
|
} |
||||||
|
|
||||||
|
public void setFoos(List<FooEnum> foos) { |
||||||
|
this.foos = foos; |
||||||
|
} |
||||||
|
|
||||||
|
public List<Address> getAddresses() { |
||||||
|
return addresses; |
||||||
|
} |
||||||
|
|
||||||
|
public void setAddresses(List<Address> addresses) { |
||||||
|
this.addresses = addresses; |
||||||
|
} |
||||||
|
|
||||||
|
} |
||||||
|
|
||||||
|
public static class Address { |
||||||
|
private String street; |
||||||
|
private String city; |
||||||
|
private String state; |
||||||
|
private String zip; |
||||||
|
private String country; |
||||||
|
|
||||||
|
public String getStreet() { |
||||||
|
return street; |
||||||
|
} |
||||||
|
|
||||||
|
public void setStreet(String street) { |
||||||
|
this.street = street; |
||||||
|
} |
||||||
|
|
||||||
|
public String getCity() { |
||||||
|
return city; |
||||||
|
} |
||||||
|
|
||||||
|
public void setCity(String city) { |
||||||
|
this.city = city; |
||||||
|
} |
||||||
|
|
||||||
|
public String getState() { |
||||||
|
return state; |
||||||
|
} |
||||||
|
|
||||||
|
public void setState(String state) { |
||||||
|
this.state = state; |
||||||
|
} |
||||||
|
|
||||||
|
public String getZip() { |
||||||
|
return zip; |
||||||
|
} |
||||||
|
|
||||||
|
public void setZip(String zip) { |
||||||
|
this.zip = zip; |
||||||
|
} |
||||||
|
|
||||||
|
public String getCountry() { |
||||||
|
return country; |
||||||
|
} |
||||||
|
|
||||||
|
public void setCountry(String country) { |
||||||
|
this.country = country; |
||||||
|
} |
||||||
|
|
||||||
|
} |
||||||
|
} |
||||||
Loading…
Reference in new issue