    001    // Copyright 2008, 2010, 2011 The Apache Software Foundation
    002    //
    003    // Licensed under the Apache License, Version 2.0 (the "License");
    004    // you may not use this file except in compliance with the License.
    005    // You may obtain a copy of the License at
    006    //
    007    // http://www.apache.org/licenses/LICENSE-2.0
    008    //
    009    // Unless required by applicable law or agreed to in writing, software
    010    // distributed under the License is distributed on an "AS IS" BASIS,
    011    // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    012    // See the License for the specific language governing permissions and
    013    // limitations under the License.
    014
    015    package org.apache.tapestry5.internal.services;
    016
    017    import java.util.Locale;
    018
    019    import org.apache.tapestry5.ComponentResources;
    020    import org.apache.tapestry5.Field;
    021    import org.apache.tapestry5.FieldTranslator;
    022    import org.apache.tapestry5.Translator;
    023    import org.apache.tapestry5.beaneditor.Translate;
    024    import org.apache.tapestry5.ioc.AnnotationProvider;
    025    import org.apache.tapestry5.ioc.MessageFormatter;
    026    import org.apache.tapestry5.ioc.Messages;
    027    import org.apache.tapestry5.ioc.internal.util.InternalUtils;
    028    import org.apache.tapestry5.services.FieldTranslatorSource;
    029    import org.apache.tapestry5.services.FormSupport;
    030    import org.apache.tapestry5.services.TranslatorSource;
    031
    032    @SuppressWarnings("all")
    033    public class FieldTranslatorSourceImpl implements FieldTranslatorSource
    034    {
    035        private final TranslatorSource translatorSource;
    036
    037        private final Messages globalMessages;
    038
    039        private final FormSupport formSupport;
    040
    041        public FieldTranslatorSourceImpl(TranslatorSource translatorSource, Messages globalMessages,
    042                FormSupport formSupport)
    043        {
    044            this.translatorSource = translatorSource;
    045            this.globalMessages = globalMessages;
    046            this.formSupport = formSupport;
    047        }
    048
    049        public FieldTranslator createDefaultTranslator(ComponentResources resources, String parameterName)
    050        {
    051            assert resources != null;
    052            assert InternalUtils.isNonBlank(parameterName);
    053            Field field = (Field) resources.getComponent();
    054            Class propertyType = resources.getBoundType(parameterName);
    055
    056            return createDefaultTranslator(field, resources.getId(), resources.getContainerMessages(),
    057                    null, propertyType, resources.getAnnotationProvider(parameterName));
    058        }
    059
    060        public FieldTranslator createDefaultTranslator(Field field, String overrideId, Messages overrideMessages,
    061                Locale locale, Class propertyType, AnnotationProvider propertyAnnotations)
    062        {
    063            assert field != null;
    064            assert overrideMessages != null;
    065            assert InternalUtils.isNonBlank(overrideId);
    066            if (propertyType == null)
    067                return null;
    068
    069            Translator translator = findTranslator(propertyType, propertyAnnotations);
    070
    071            if (translator == null)
    072                return null;
    073
    074            return createTranslator(field, overrideId, overrideMessages, locale, translator);
    075        }
    076
    077        Translator findTranslator(Class propertyType, AnnotationProvider propertyAnnotations)
    078        {
    079            Translate annotation = propertyAnnotations.getAnnotation(Translate.class);
    080
    081            if (annotation != null)
    082                return translatorSource.get(annotation.value());
    083
    084            if (propertyType == null)
    085                return null;
    086
    087            return translatorSource.findByType(propertyType);
    088        }
    089
    090        public FieldTranslator createTranslator(Field field, String overrideId, Messages overrideMessages, Locale locale,
    091                Translator translator)
    092        {
    093            MessageFormatter formatter = findFormatter(overrideId, overrideMessages, translator);
    094
    095            return new FieldTranslatorImpl(field, translator, formatter, formSupport);
    096        }
    097
    098        public FieldTranslator createTranslator(ComponentResources resources, String translatorName)
    099        {
    100            assert resources != null;
    101            assert InternalUtils.isNonBlank(translatorName);
    102            Field field = (Field) resources.getComponent();
    103
    104            Translator translator = translatorSource.get(translatorName);
    105
    106            return createTranslator(field, resources.getId(), resources.getContainerMessages(), null, translator);
    107        }
    108
    109        private MessageFormatter findFormatter(String overrideId, Messages overrideMessages, Translator translator)
    110        {
    111            // TAP5-228: Try to distinguish message overrides by form id and overrideId (i.e., property name) first.
    112
    113            String translatorName = translator.getName();
    114
    115            String overrideKey = formSupport.getFormValidationId() + "-" + overrideId + "-" + translatorName + "-message";
    116
    117            if (overrideMessages.contains(overrideKey))
    118                return overrideMessages.getFormatter(overrideKey);
    119
    120            // Ok, look for a simpler name that omits the formId prefix.
    121
    122            overrideKey = overrideId + "-" + translatorName + "-message";
    123
    124            if (overrideMessages.contains(overrideKey))
    125                return overrideMessages.getFormatter(overrideKey);
    126
    127            // Otherwise, use the built-in validation message appropriate to this validator.
    128            String messageKey = translator.getMessageKey();
    129
    130            // If no key has been specified, use translator name to create a key
    131            if(messageKey == null)
    132            {
    133                messageKey = translatorName + "-message";
    134            }
    135
    136            return globalMessages.getFormatter(messageKey);
    137        }
    138    }