Coverage Report - net.sf.beanform.validator.CachingValidatorFactoryImpl
 
Classes in this File Line Coverage Branch Coverage Complexity
CachingValidatorFactoryImpl
100% 
100% 
0
 
 1  
 // Copyright 2006 Daniel Gredler
 2  
 //
 3  
 // Licensed under the Apache License, Version 2.0 (the "License");
 4  
 // you may not use this file except in compliance with the License.
 5  
 // You may obtain a copy of the License at
 6  
 //
 7  
 //     http://www.apache.org/licenses/LICENSE-2.0
 8  
 //
 9  
 // Unless required by applicable law or agreed to in writing, software
 10  
 // distributed under the License is distributed on an "AS IS" BASIS,
 11  
 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 12  
 // See the License for the specific language governing permissions and
 13  
 // limitations under the License.
 14  
 
 15  
 package net.sf.beanform.validator;
 16  
 
 17  
 import java.util.ArrayList;
 18  
 import java.util.HashMap;
 19  
 import java.util.List;
 20  
 import java.util.Map;
 21  
 
 22  
 import net.sf.beanform.prop.BeanProperty;
 23  
 
 24  
 import org.apache.commons.logging.Log;
 25  
 import org.apache.commons.logging.LogFactory;
 26  
 import org.apache.tapestry.IComponent;
 27  
 import org.apache.tapestry.event.ReportStatusEvent;
 28  
 import org.apache.tapestry.form.validator.Validator;
 29  
 import org.apache.tapestry.form.validator.ValidatorFactory;
 30  
 
 31  
 /**
 32  
  * Default implementation of the {@link CachingValidatorFactory} interface.
 33  
  *
 34  
  * @author Daniel Gredler
 35  
  */
 36  8
 public class CachingValidatorFactoryImpl implements CachingValidatorFactory {
 37  
 
 38  1
     private final static Log LOG = LogFactory.getLog( CachingValidatorFactoryImpl.class );
 39  
 
 40  
     private String serviceId;
 41  
     private ValidatorFactory validatorFactory;
 42  8
     private Map<BeanProperty, List<Validator>> cache = new HashMap<BeanProperty, List<Validator>>();
 43  
 
 44  
     public void setServiceId( String serviceId ) {
 45  1
         this.serviceId = serviceId;
 46  1
     }
 47  
 
 48  
     public void setValidatorFactory( ValidatorFactory validatorFactory ) {
 49  7
         this.validatorFactory = validatorFactory;
 50  7
     }
 51  
 
 52  
     @SuppressWarnings( "unchecked" )
 53  
     public List<Validator> constructValidatorList( IComponent component, BeanProperty property ) {
 54  
         List<Validator> validators;
 55  11
         synchronized( this.cache ) {
 56  11
             validators = this.cache.get( property );
 57  11
             if( validators == null ) {
 58  
                 // Build up lists of inherent validators and user-defined validators (defined explicitly or via annotations).
 59  9
                 List<Validator> inherent = this.getInherentValidators( component, property );
 60  9
                 List<Validator> userDefined = this.validatorFactory.constructValidatorList( component, property.getValidators() );
 61  
                 // Combine these validator lists into a single master list.
 62  9
                 validators = new ArrayList<Validator>();
 63  9
                 validators.addAll( inherent );
 64  9
                 validators.addAll( userDefined );
 65  
                 // Cache it and we're done!
 66  9
                 this.cache.put( property, validators );
 67  9
                 if( LOG.isDebugEnabled() ) {
 68  9
                     LOG.debug( "Bean property '" + property.getName() + "' " +
 69  
                                "has " + validators.size() + " validators: " + validators );
 70  
                 }
 71  
             }
 72  11
         }
 73  11
         return validators;
 74  
     }
 75  
 
 76  
     public void resetEventDidOccur() {
 77  1
         synchronized( this.cache ) {
 78  1
             this.cache.clear();
 79  1
         }
 80  1
     }
 81  
 
 82  
     public void reportStatus( ReportStatusEvent event ) {
 83  1
         event.title( this.serviceId );
 84  1
         synchronized( this.cache ) {
 85  1
             event.property( "cached validator count", this.cache.size() );
 86  1
             event.collection( "cached validators", this.cache.keySet() );
 87  1
         }
 88  1
     }
 89  
 
 90  
     /**
 91  
      * Returns validators for the specified property that are inherent to the property type (ie, "this
 92  
      * property is a short, so its minimum value must be {@link Short#MIN_VALUE}"). It's important that
 93  
      * the number validation come before the min/max value validations.
 94  
      */
 95  
     @SuppressWarnings( "unchecked" )
 96  
     private List<Validator> getInherentValidators( IComponent component, BeanProperty property ) {
 97  
 
 98  9
         String number = null;
 99  9
         if( property.isNumber() ) {
 100  8
             if( property.isFloat() || property.isDouble() ) number = NumberValidator.NAME;
 101  6
             else number = WholeNumberValidator.NAME;
 102  
         }
 103  
 
 104  
         String minValue;
 105  9
         if( property.isShort() ) minValue = String.valueOf( Short.MIN_VALUE );
 106  5
         else if( property.isInteger() ) minValue = String.valueOf( Integer.MIN_VALUE );
 107  4
         else if( property.isLong() ) minValue = String.valueOf( Long.MIN_VALUE );
 108  3
         else if( property.isFloat() ) minValue = String.valueOf( Float.MIN_VALUE );
 109  2
         else if( property.isDouble() ) minValue = String.valueOf( Double.MIN_VALUE );
 110  1
         else minValue = null;
 111  
 
 112  
         String maxValue;
 113  9
         if( property.isShort() ) maxValue = String.valueOf( Short.MAX_VALUE );
 114  5
         else if( property.isInteger() ) maxValue = String.valueOf( Integer.MAX_VALUE );
 115  4
         else if( property.isLong() ) maxValue = String.valueOf( Long.MAX_VALUE );
 116  3
         else if( property.isFloat() ) maxValue = String.valueOf( Float.MAX_VALUE );
 117  2
         else if( property.isDouble() ) maxValue = String.valueOf( Double.MAX_VALUE );
 118  1
         else maxValue = null;
 119  
 
 120  9
         StringBuilder sb = new StringBuilder();
 121  9
         if( number != null   ) sb.append( number );
 122  9
         if( minValue != null ) sb.append( sb.length() > 0 ? "," : "" ).append( StringMin.NAME ).append( "=" ).append( minValue );
 123  9
         if( maxValue != null ) sb.append( sb.length() > 0 ? "," : "" ).append( StringMax.NAME ).append( "=" ).append( maxValue );
 124  
 
 125  9
         String expression = sb.toString();
 126  9
         return this.validatorFactory.constructValidatorList( component, expression );
 127  
     }
 128  
 
 129  
 }