001package org.apache.turbine.util;
002
003
004/*
005 * Licensed to the Apache Software Foundation (ASF) under one
006 * or more contributor license agreements.  See the NOTICE file
007 * distributed with this work for additional information
008 * regarding copyright ownership.  The ASF licenses this file
009 * to you under the Apache License, Version 2.0 (the
010 * "License"); you may not use this file except in compliance
011 * with the License.  You may obtain a copy of the License at
012 *
013 *   http://www.apache.org/licenses/LICENSE-2.0
014 *
015 * Unless required by applicable law or agreed to in writing,
016 * software distributed under the License is distributed on an
017 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
018 * KIND, either express or implied.  See the License for the
019 * specific language governing permissions and limitations
020 * under the License.
021 */
022
023
024import java.util.Hashtable;
025import java.util.Iterator;
026import java.util.List;
027import java.util.Vector;
028
029/**
030 * Used for adding and accessing messages that relate to a specific
031 * form and field.  Allows to query for messages by form name and
032 * field name.  Used together with FormMessage class.
033 *
034 * @author <a href="mailto:neeme@one.lv">Neeme Praks</a>
035 * @version $Id: FormMessages.java 1152507 2011-07-30 20:14:38Z tv $
036 */
037public class FormMessages
038{
039    private final Hashtable<String, Vector<String>> forms_messages;
040    private final Hashtable<String, Vector<String>> fields_messages;
041    private final Hashtable<String, Vector<String>> messages_fields;
042    private final Hashtable<String, Vector<String>> forms_fields;
043
044    /**
045     * Constructor.
046     */
047    public FormMessages()
048    {
049        forms_messages = new Hashtable<String, Vector<String>>();
050        fields_messages = new Hashtable<String, Vector<String>>();
051        messages_fields = new Hashtable<String, Vector<String>>();
052        forms_fields = new Hashtable<String, Vector<String>>();
053    }
054
055    /**
056     * Sets a message for a field of a form.  The message is given as
057     * a long representing a return code.
058     *
059     * @param formName A String with the form name.
060     * @param fieldName A String with the field name.
061     * @param returnCode A long with the return code.
062     */
063    public void setMessage(String formName,
064                           String fieldName,
065                           long returnCode)
066    {
067        setMessage(formName, fieldName, String.valueOf(returnCode));
068    }
069
070    /**
071     * Sets a message for a field of a form.  The message is given as
072     * a String.
073     *
074     * @param formName A String with the form name.
075     * @param fieldName A String with the field name.
076     * @param messageName A String with the message.
077     */
078    public void setMessage(String formName,
079                           String fieldName,
080                           String messageName)
081    {
082        fieldName = formName + "-" + fieldName;
083        addValue(forms_messages, formName, messageName);
084        addValue(fields_messages, fieldName, messageName);
085        addValue(messages_fields, messageName, fieldName);
086        addValue(forms_fields, formName, fieldName);
087    }
088
089    /**
090     * Adds a pair key/value to a table, making sure not to add
091     * duplicate keys.
092     *
093     * @param table A Hashtable.
094     * @param key A String with the key.
095     * @param value A String with value.
096     */
097    private void addValue(Hashtable<String, Vector<String>> table,
098                          String key,
099                          String value)
100    {
101        Vector<String> values;
102
103        if (!table.containsKey(key))
104        {
105            values = new Vector<String>();
106            values.addElement(value);
107            table.put(key, values);
108        }
109        else
110        {
111            values = table.get(key);
112            if (!values.contains(value))
113                values.addElement(value);
114        }
115    }
116
117    /**
118     * Gets a pair key/value from a table.
119     *
120     * @param table A Hashtable.
121     * @param key A String with the key.
122     * @return A Vector with the pair key/value, or null.
123     */
124    private final Vector<String> getValues(Hashtable<String, Vector<String>> table, String key)
125    {
126        return table.get(key);
127    }
128
129    /**
130     * Gets all form messages for a given form.
131     *
132     * @param formName A String with the form name.
133     * @return A FormMessage[].
134     */
135    public FormMessage[] getFormMessages(String formName)
136    {
137        Vector<String> messages, fields;
138        String messageName, fieldName;
139        messages = getValues(forms_messages, formName);
140        if (messages != null)
141        {
142            FormMessage[] result = new FormMessage[messages.size()];
143            for (int i = 0; i < messages.size(); i++)
144            {
145                result[i] = new FormMessage(formName);
146                messageName = messages.elementAt(i);
147                result[i].setMessage(messageName);
148                fields = getValues(messages_fields, messageName);
149                for (int j = 0; j < fields.size(); j++)
150                {
151                    fieldName = fields.elementAt(j);
152                    if (formHasField(formName, fieldName))
153                    {
154                        result[i].setFieldName(fieldName);
155                    }
156                }
157            }
158            return result;
159        }
160        return null;
161    }
162
163    /**
164     * Get form messages for a given form and field.
165     *
166     * @param formName A String with the form name.
167     * @param fieldName A String with the field name.
168     * @return A FormMessage[].
169     */
170    public FormMessage[] getFormMessages(String formName, String fieldName)
171    {
172        String key = formName + "-" + fieldName;
173
174        Vector<String> messages = getValues(fields_messages, key);
175        String messageName;
176
177        if (messages != null)
178        {
179            FormMessage[] result = new FormMessage[messages.size()];
180            for (int i = 0; i < messages.size(); i++)
181            {
182                result[i] = new FormMessage(formName, fieldName);
183                messageName = messages.elementAt(i);
184                result[i].setMessage(messageName);
185            }
186            return result;
187        }
188        return null;
189    }
190
191    /**
192     * Check whether a form as a field.
193     *
194     * @param formName A String with the form name.
195     * @param fieldName A String with the field name.
196     * @return True if form has the field.
197     */
198    private boolean formHasField(String formName,
199                                 String fieldName)
200    {
201        List<String> fields = getValues(forms_fields, formName);
202        for (Iterator<String> iter = fields.iterator(); iter.hasNext();)
203        {
204            if (fieldName.equals(iter.next().toString()))
205            {
206                return true;
207            }
208        }
209        return false;
210    }
211}