001    // Copyright 2005 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.hivemind.impl;
016    
017    import java.text.MessageFormat;
018    import java.util.Locale;
019    
020    import org.apache.hivemind.HiveMind;
021    import org.apache.hivemind.Messages;
022    import org.apache.hivemind.util.Defense;
023    
024    /**
025     * Abstract base class for implementations of {@link org.apache.hivemind.Messages}. Subclasses must
026     * provide {@link #getLocale()}and {@link #findMessage(String)} implementations.
027     * 
028     * @author Howard M. Lewis Ship
029     * @since 1.1
030     */
031    public abstract class AbstractMessages implements Messages
032    {
033        public String format(String key, Object[] args)
034        {
035            String pattern = getMessage(key);
036    
037            for (int i = 0; i < args.length; i++)
038            {
039                Object arg = args[i];
040    
041                if (arg != null && arg instanceof Throwable)
042                    args[i] = extractMessage((Throwable) arg);
043            }
044    
045            // This ugliness is mandated for JDK 1.3 compatibility, which has a bug
046            // in MessageFormat ... the
047            // pattern is applied in the constructor, using the system default Locale,
048            // regardless of what locale is later specified!
049            // It appears that the problem does not exist in JDK 1.4.
050    
051            MessageFormat messageFormat = new MessageFormat("");
052            messageFormat.setLocale(getLocale());
053            messageFormat.applyPattern(pattern);
054    
055            return messageFormat.format(args);
056        }
057    
058        private String extractMessage(Throwable t)
059        {
060            String message = t.getMessage();
061    
062            return HiveMind.isNonBlank(message) ? message : t.getClass().getName();
063        }
064    
065        public String format(String key, Object arg0)
066        {
067            return format(key, new Object[]
068            { arg0 });
069        }
070    
071        public String format(String key, Object arg0, Object arg1)
072        {
073            return format(key, new Object[]
074            { arg0, arg1 });
075        }
076    
077        public String format(String key, Object arg0, Object arg1, Object arg2)
078        {
079            return format(key, new Object[]
080            { arg0, arg1, arg2 });
081        }
082    
083        public String getMessage(String key)
084        {
085            Defense.notNull(key, "key");
086    
087            String result = findMessage(key);
088    
089            if (result == null)
090                result = "[" + key.toUpperCase() + "]";
091    
092            return result;
093        }
094    
095        /**
096         * Concrete implementations must provide a non-null Locale.
097         */
098    
099        protected abstract Locale getLocale();
100    
101        /**
102         * Concrete implementations must implement this method.
103         * 
104         * @param key
105         * @return the localized message for the key, or null if no such message exists.
106         */
107    
108        protected abstract String findMessage(String key);
109    
110    }