001 package hirondelle.web4j.config; 002 003 import java.math.BigDecimal; 004 import hirondelle.web4j.model.Decimal; 005 import hirondelle.web4j.model.ModelCtorException; 006 import hirondelle.web4j.request.RequestParameter; 007 import hirondelle.web4j.model.ConvertParamError; 008 import hirondelle.web4j.security.SafeText; 009 010 /** 011 Implementation of {@link ConvertParamError}, required by WEB4J. 012 013 <P>Defines how the application renders conversion errors detected by the framework. 014 */ 015 public final class ConvertParamErrorImpl implements ConvertParamError { 016 017 /** 018 Return a {@link ModelCtorException} having a compound message. 019 020 See {@link hirondelle.web4j.model.AppResponseMessage} for further information on compound messages. 021 */ 022 public ModelCtorException get(Class<?> aTargetClass, String aUserInputValue, RequestParameter aRequestParameter){ 023 String errorMessagePattern = getPatternAsFixedString(aTargetClass); 024 ModelCtorException result = new ModelCtorException(); 025 if( SafeText.class == aTargetClass) { 026 //User input might be long, so it's not included here as a second param. 027 //Ideally, the second param should contain the offending character(s). 028 //That is not possible here, unfortunately. 029 //Mitigated by treating all chars known to EscapeChars.forHTML() as permitted chars. 030 Object[] params = { aRequestParameter }; 031 result.add(errorMessagePattern, params); 032 } 033 else { 034 Object[] params = { aRequestParameter, aUserInputValue }; 035 result.add(errorMessagePattern, params); 036 } 037 return result; 038 } 039 040 // PRIVATE // 041 042 /** 043 If this were a fully multilingual application, these text items would, in this class, 044 remain as they are. The only difference is that the implementation of 045 {@link hirondelle.web4j.ui.translate.Translator} would need to be aware of these 046 text snippets as 'base text'. 047 */ 048 private String getPatternAsFixedString(Class<?> aTargetClass){ 049 String result = null; 050 if ( BigDecimal.class == aTargetClass || Decimal.class == aTargetClass ) { 051 result = "_1_ is not in the expected format/range : '_2_'"; 052 } 053 else if ( Integer.class == aTargetClass ) { 054 result = "_1_ is not an integer : '_2_'"; 055 } 056 else if ( java.util.Date.class == aTargetClass || hirondelle.web4j.model.DateTime.class == aTargetClass) { 057 result = "_1_ is not in the expected date format 'MMDDYYYY hh:mm' (time is optional) : '_2_'"; 058 } 059 else if ( SafeText.class == aTargetClass ) { 060 result = "_1_ contains unpermitted character(s)."; 061 } 062 else { 063 throw new AssertionError("Unexpected case for target base class: " + aTargetClass); 064 } 065 return result; 066 } 067 }