1 /* 2 * Licensed to the Apache Software Foundation (ASF) under one or more 3 * contributor license agreements. See the NOTICE file distributed with 4 * this work for additional information regarding copyright ownership. 5 * The ASF licenses this file to You under the Apache License, Version 2.0 6 * (the "License"); you may not use this file except in compliance with 7 * the License. You may obtain a copy of the License at 8 * 9 * http://www.apache.org/licenses/LICENSE-2.0 10 * 11 * Unless required by applicable law or agreed to in writing, software 12 * distributed under the License is distributed on an "AS IS" BASIS, 13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 * See the License for the specific language governing permissions and 15 * limitations under the License. 16 */ 17 package org.apache.commons.beanutils.converters; 18 19 /** 20 * {@link org.apache.commons.beanutils.Converter} implementation that handles conversion 21 * to and from <b>Boolean</b> objects. 22 * {@link org.apache.commons.beanutils.Converter} implementation that 23 * handles conversion to and from <b>java.lang.Boolean</b> objects. 24 * <p> 25 * Can be configured to either return a <i>default value</i> or throw a 26 * <code>ConversionException</code> if a conversion error occurs. 27 * <p> 28 * By default any object whose string representation is one of the values 29 * {"yes", "y", "true", "on", "1"} is converted to Boolean.TRUE, and 30 * string representations {"no", "n", "false", "off", "0"} are converted 31 * to Boolean.FALSE. The recognized true/false strings can be changed by: 32 * <pre> 33 * String[] trueStrings = {"oui", "o", "1"}; 34 * String[] falseStrings = {"non", "n", "0"}; 35 * Converter bc = new BooleanConverter(trueStrings, falseStrings); 36 * ConvertUtils.register(bc, Boolean.class); 37 * ConvertUtils.register(bc, Boolean.TYPE); 38 * </pre> 39 * In addition, it is recommended that the BooleanArrayConverter also be 40 * modified to recognise the same set of values: 41 * <pre> 42 * Converter bac = new BooleanArrayConverter(bc, BooleanArrayConverter.NO_DEFAULT); 43 * ConvertUtils.register(bac, bac.MODEL); 44 * </pre> 45 * </p> 46 * 47 * <p>Case is ignored when converting values to true or false.</p> 48 * 49 * @version $Id$ 50 * @since 1.3 51 */ 52 public final class BooleanConverter extends AbstractConverter { 53 54 55 // ----------------------------------------------------------- Constructors 56 57 58 /** 59 * Create a {@link org.apache.commons.beanutils.Converter} that will throw a 60 * {@link org.apache.commons.beanutils.ConversionException} 61 * if a conversion error occurs, ie the string value being converted is 62 * not one of the known true strings, nor one of the known false strings. 63 */ 64 public BooleanConverter() { 65 super(); 66 } 67 68 69 /** 70 * Create a {@link org.apache.commons.beanutils.Converter} that will return the specified default value 71 * if a conversion error occurs, ie the string value being converted is 72 * not one of the known true strings, nor one of the known false strings. 73 * 74 * @param defaultValue The default value to be returned if the value 75 * being converted is not recognized. This value may be null, in which 76 * case null will be returned on conversion failure. When non-null, it is 77 * expected that this value will be either Boolean.TRUE or Boolean.FALSE. 78 * The special value BooleanConverter.NO_DEFAULT can also be passed here, 79 * in which case this constructor acts like the no-argument one. 80 */ 81 public BooleanConverter(final Object defaultValue) { 82 super(); 83 if (defaultValue != NO_DEFAULT) { 84 setDefaultValue(defaultValue); 85 } 86 } 87 88 /** 89 * Create a {@link org.apache.commons.beanutils.Converter} that will throw a 90 * {@link org.apache.commons.beanutils.ConversionException} 91 * if a conversion error occurs, ie the string value being converted is 92 * not one of the known true strings, nor one of the known false strings. 93 * <p> 94 * The provided string arrays are copied, so that changes to the elements 95 * of the array after this call is made do not affect this object. 96 * 97 * @param trueStrings is the set of strings which should convert to the 98 * value Boolean.TRUE. The value null must not be present. Case is 99 * ignored. 100 * 101 * @param falseStrings is the set of strings which should convert to the 102 * value Boolean.TRUE. The value null must not be present. Case is 103 * ignored. 104 * @since 1.8.0 105 */ 106 public BooleanConverter(final String[] trueStrings, final String[] falseStrings) { 107 super(); 108 this.trueStrings = copyStrings(trueStrings); 109 this.falseStrings = copyStrings(falseStrings); 110 } 111 112 /** 113 * Create a {@link org.apache.commons.beanutils.Converter} that will return 114 * the specified default value if a conversion error occurs. 115 * <p> 116 * The provided string arrays are copied, so that changes to the elements 117 * of the array after this call is made do not affect this object. 118 * 119 * @param trueStrings is the set of strings which should convert to the 120 * value Boolean.TRUE. The value null must not be present. Case is 121 * ignored. 122 * 123 * @param falseStrings is the set of strings which should convert to the 124 * value Boolean.TRUE. The value null must not be present. Case is 125 * ignored. 126 * 127 * @param defaultValue The default value to be returned if the value 128 * being converted is not recognized. This value may be null, in which 129 * case null will be returned on conversion failure. When non-null, it is 130 * expected that this value will be either Boolean.TRUE or Boolean.FALSE. 131 * The special value BooleanConverter.NO_DEFAULT can also be passed here, 132 * in which case an exception will be thrown on conversion failure. 133 * @since 1.8.0 134 */ 135 public BooleanConverter(final String[] trueStrings, final String[] falseStrings, 136 final Object defaultValue) { 137 super(); 138 this.trueStrings = copyStrings(trueStrings); 139 this.falseStrings = copyStrings(falseStrings); 140 if (defaultValue != NO_DEFAULT) { 141 setDefaultValue(defaultValue); 142 } 143 } 144 145 146 // ----------------------------------------------------- Static Variables 147 148 149 /** 150 * This is a special reference that can be passed as the "default object" 151 * to the constructor to indicate that no default is desired. Note that 152 * the value 'null' cannot be used for this purpose, as the caller may 153 * want a null to be returned as the default. 154 * @deprecated Use constructors without default value. 155 */ 156 @Deprecated 157 public static final Object NO_DEFAULT = new Object(); 158 159 160 // ----------------------------------------------------- Instance Variables 161 162 /** 163 * The set of strings that are known to map to Boolean.TRUE. 164 */ 165 private String[] trueStrings = {"true", "yes", "y", "on", "1"}; 166 167 /** 168 * The set of strings that are known to map to Boolean.FALSE. 169 */ 170 private String[] falseStrings = {"false", "no", "n", "off", "0"}; 171 172 // --------------------------------------------------------- Protected Methods 173 174 /** 175 * Return the default type this <code>Converter</code> handles. 176 * 177 * @return The default type this <code>Converter</code> handles. 178 * @since 1.8.0 179 */ 180 @Override 181 protected Class<Boolean> getDefaultType() { 182 return Boolean.class; 183 } 184 185 /** 186 * Convert the specified input object into an output object of the 187 * specified type. 188 * 189 * @param <T> Target type of the conversion. 190 * @param type is the type to which this value should be converted. In the 191 * case of this BooleanConverter class, this value is ignored. 192 * 193 * @param value is the input value to be converted. The toString method 194 * shall be invoked on this object, and the result compared (ignoring 195 * case) against the known "true" and "false" string values. 196 * 197 * @return Boolean.TRUE if the value was a recognized "true" value, 198 * Boolean.FALSE if the value was a recognized "false" value, or 199 * the default value if the value was not recognized and the constructor 200 * was provided with a default value. 201 * 202 * @throws Throwable if an error occurs converting to the specified type 203 * @since 1.8.0 204 */ 205 @Override 206 protected <T> T convertToType(final Class<T> type, final Object value) throws Throwable { 207 208 if (Boolean.class.equals(type) || Boolean.TYPE.equals(type)) { 209 // All the values in the trueStrings and falseStrings arrays are 210 // guaranteed to be lower-case. By converting the input value 211 // to lowercase too, we can use the efficient String.equals method 212 // instead of the less-efficient String.equalsIgnoreCase method. 213 final String stringValue = value.toString().toLowerCase(); 214 215 for (String trueString : trueStrings) { 216 if (trueString.equals(stringValue)) { 217 return type.cast(Boolean.TRUE); 218 } 219 } 220 221 for (String falseString : falseStrings) { 222 if (falseString.equals(stringValue)) { 223 return type.cast(Boolean.FALSE); 224 } 225 } 226 } 227 228 throw conversionException(type, value); 229 } 230 231 /** 232 * This method creates a copy of the provided array, and ensures that 233 * all the strings in the newly created array contain only lower-case 234 * letters. 235 * <p> 236 * Using this method to copy string arrays means that changes to the 237 * src array do not modify the dst array. 238 */ 239 private static String[] copyStrings(final String[] src) { 240 final String[] dst = new String[src.length]; 241 for(int i=0; i<src.length; ++i) { 242 dst[i] = src[i].toLowerCase(); 243 } 244 return dst; 245 } 246 }