View Javadoc
1   /*
2    * Copyright 2006 Werner Guttmann
3    *
4    * Licensed under the Apache License, Version 2.0 (the "License");
5    * you may not use this file except in compliance with the License.
6    * You may obtain a copy of the License at
7    *
8    * http://www.apache.org/licenses/LICENSE-2.0
9    *
10   * Unless required by applicable law or agreed to in writing, software
11   * distributed under the License is distributed on an "AS IS" BASIS,
12   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13   * See the License for the specific language governing permissions and
14   * limitations under the License.
15   */
16  package org.exolab.castor.xml.validators;
17  
18  import org.exolab.castor.xml.TypeValidator;
19  import org.exolab.castor.xml.ValidationContext;
20  import org.exolab.castor.xml.ValidationException;
21  
22  /**
23   * The Int Validation class. This class handles validation for the primitive
24   * <code>int</code> and <code>java.lang.Integer</code> types as well as all
25   * derived types such as unsigned-short.
26   *
27   * @author <a href="mailto:werner DOT guttmann AT gmx DOT net">Werner Guttmann</a>
28   * @version $Revision: 6571 $ $Date: 2006-04-25 15:08:23 -0600 (Tue, 25 Apr
29   *          2006) $
30   */
31  public class IntValidator extends PatternValidator implements TypeValidator {
32  
33      /** If true, we perform "minimum value" validation. */
34      private boolean _useMin       = false;
35      /** If true, we perform "maximum value" validation. */
36      private boolean _useMax       = false;
37      /** If true, we perform "fixed" validation. */
38      private boolean _useFixed     = false;
39      /** Minimum value (inclusive) for this int.  (Not used unless _useMin == true.) */
40      private int     _min          = 0;
41      /** Maximum value (inclusive) for this int.  (Not used unless _useMax == true.) */
42      private int     _max          = 0;
43      /** Maximum number of digits in this int. (Not applied if < 0.) */
44      private int     _totalDigits = -1;
45      /** Fixed value of this int. (Not used unless _useFixed == true.) */
46      private int     _fixed        = 0;
47  
48      /**
49       * Creates a new IntValidator with no restrictions.
50       */
51      public IntValidator() {
52          super();
53      } // -- IntegerValidator
54  
55      /**
56       * Clears the fixed value for this IntValidator.
57       */
58      public void clearFixed() {
59          _useFixed = false;
60      } // -- clearFixed
61  
62      /**
63       * Clears the maximum value for this IntValidator.
64       */
65      public void clearMax() {
66          _useMax = false;
67      } // -- clearMax
68  
69      /**
70       * Clears the minimum value for this IntValidator.
71       */
72      public void clearMin() {
73          _useMin = false;
74      } // -- clearMin
75  
76      /**
77       * Returns the configured fixed value for int validation. Returns null if no
78       * fixed value has been configured.
79       *
80       * @return the fixed value to validate against.
81       */
82      public Integer getFixed() {
83          if (_useFixed) {
84              return new Integer(_fixed);
85          }
86          return null;
87      } // -- getFixed
88  
89      /**
90       * Returns the configured maximum value for int validation. Returns null if
91       * no maximum has been configured.
92       *
93       * @return the maximum (inclusive) value to validate against.
94       */
95      public Integer getMaxInclusive() {
96          if (_useMax) {
97              return new Integer(_max);
98          }
99          return null;
100     } // -- getMaxInclusive
101 
102     /**
103      * Returns the configured minimum value for int validation. Returns null if
104      * no minimum has been configured.
105      *
106      * @return the minimum inclusive value to validate against.
107      */
108     public Integer getMinInclusive() {
109         if (_useMin) {
110             return new Integer(_min);
111         }
112         return null;
113     } // -- getMinInclusive
114 
115     /**
116      * Returns the configured maximum number of digits (inclusive) for int
117      * validation. Returns null if no maximum number of digits has been
118      * configured.
119      *
120      * @return the maximum number of digits to validate against.
121      */
122     public Integer getTotalDigits() {
123         if (_totalDigits >= 0) {
124             return new Integer(_totalDigits);
125         }
126         return null;
127     } // -- getTotalDigits
128 
129     /**
130      * Returns true if a fixed value to validate against has been set.
131      *
132      * @return true if a fixed value has been set.
133      */
134     public boolean hasFixed() {
135         return _useFixed;
136     } // -- hasFixed
137 
138     /**
139      * Sets the fixed value for int validation.
140      * <p>
141      * NOTE: If maximum and/or minimum values have been set and the fixed value
142      * is not within that max/min range, then no int will pass validation. This
143      * is as according to the XML Schema spec.
144      *
145      * @param fixedValue
146      *            the fixed value that a int validated with this validator must
147      *            be equal to.
148      */
149     public void setFixed(final int fixedValue) {
150         _useFixed = true;
151         this._fixed = fixedValue;
152     } // -- setFixed
153 
154     /**
155      * Sets the fixed value for int validation.
156      * <p>
157      * NOTE: If maximum and/or minimum values have been set and the fixed value
158      * is not within that max/min range, then no int will pass validation. This
159      * is as according to the XML Schema spec.
160      *
161      * @param fixedValue
162      *            the fixed value that a int validated with this validator must
163      *            be equal to.
164      */
165     public void setFixed(final Integer fixedValue) {
166         _useFixed = true;
167         this._fixed = fixedValue.intValue();
168     }
169 
170     /**
171      * Sets the minimum (exclusive) value for int validation. To pass
172      * validation, a int must be greater than this value.
173      *
174      * @param minValue
175      *            the minimum (exclusive) value for int validation.
176      */
177     public void setMinExclusive(final int minValue) {
178         _useMin = true;
179         _min = minValue + 1;
180     } // -- setMinExclusive
181 
182     /**
183      * Sets the minimum (inclusive) value for int validation. To pass
184      * validation, a int must be greater than or equal to this value.
185      *
186      * @param minValue
187      *            the minimum (inclusive) value for int validation.
188      */
189     public void setMinInclusive(final int minValue) {
190         _useMin = true;
191         _min = minValue;
192     } // -- setMinInclusive
193 
194     /**
195      * Sets the maximum (exclusive) value for int validation. To pass
196      * validation, a int must be less than this value.
197      *
198      * @param maxValue
199      *            the maximum (exclusive) value for int validation.
200      */
201     public void setMaxExclusive(final int maxValue) {
202         _useMax = true;
203         _max = maxValue - 1;
204     } // -- setMaxExclusive
205 
206     /**
207      * Sets the maximum (inclusive) value for int validation. To pass
208      * validation, a int must be less than or equal to this value.
209      *
210      * @param maxValue
211      *            the maximum (inclusive) value for int validation.
212      */
213     public void setMaxInclusive(final int maxValue) {
214         _useMax = true;
215         _max = maxValue;
216     } // -- setMaxInclusive
217 
218     /**
219      * Sets the maximum number of digits for int validation. To pass validation,
220      * a int must have this many digits or fewer. Leading zeros are not counted.
221      *
222      * @param totalDig
223      *            the maximum (inclusive) number of digits for int validation.
224      *            (must be > 0)
225      */
226     public void setTotalDigits(final int totalDig) {
227         if (totalDig <= 0) {
228             throw new IllegalArgumentException(
229                     "IntegerValidator: the totalDigits facet must be positive");
230         }
231         _totalDigits = totalDig;
232     }
233 
234     /**
235      * Validates the given Object.
236      *
237      * @param i
238      *            the long to validate
239      * @param context
240      *            the ValidationContext
241      * @throws ValidationException if the object fails validation.
242      */
243     public void validate(final int i, final ValidationContext context)
244                                                     throws ValidationException {
245         if (_useFixed && i != _fixed) {
246             String err = "int " + i + " is not equal to the fixed value: " + _fixed;
247             throw new ValidationException(err);
248         }
249 
250         if (_useMin && i < _min) {
251             String err = "int " + i + " is less than the minimum allowed value: " + _min;
252             throw new ValidationException(err);
253         }
254 
255         if (_useMax && i > _max) {
256             String err = "int " + i + " is greater than the maximum allowed value: " + _max;
257             throw new ValidationException(err);
258         }
259 
260         if (_totalDigits != -1) {
261             int length = Integer.toString(i).length();
262             if (i < 0) {
263                 length--;
264             }
265             if (length > _totalDigits) {
266                 String err = "int " + i + " has too many digits -- must have "
267                         + _totalDigits + " digits or fewer.";
268                 throw new ValidationException(err);
269             }
270         }
271 
272         if (hasPattern()) {
273             super.validate(Integer.toString(i), context);
274         }
275     } // -- validate
276 
277     /**
278      * Validates the given Object.
279      *
280      * @param object
281      *            the Object to validate
282      * @throws ValidationException if the object fails validation.
283      */
284     public void validate(final Object object) throws ValidationException {
285         validate(object, (ValidationContext) null);
286     } // -- validate
287 
288     /**
289      * Validates the given Object.
290      *
291      * @param object
292      *            the Object to validate
293      * @param context
294      *            the ValidationContext
295      * @throws ValidationException if the object fails validation.
296      */
297     public void validate(final Object object, final ValidationContext context)
298                                                     throws ValidationException {
299         if (object == null) {
300             String err = "IntValidator cannot validate a null object.";
301             throw new ValidationException(err);
302         }
303 
304         int value = 0;
305         try {
306             value = ((Integer) object).intValue();
307         } catch (Exception ex) {
308             String err = "Expecting an Integer, received instead an instance of: ";
309             err += object.getClass().getName();
310             throw new ValidationException(err);
311         }
312         validate(value, context);
313     } //-- validate
314 
315 } //-- IntegerValidator