001: /*
002: * Copyright (c) 1998-2007 Caucho Technology -- all rights reserved
003: *
004: * This file is part of Resin(R) Open Source
005: *
006: * Each copy or derived work must preserve the copyright notice and this
007: * notice unmodified.
008: *
009: * Resin Open Source is free software; you can redistribute it and/or modify
010: * it under the terms of the GNU General Public License as published by
011: * the Free Software Foundation; either version 2 of the License, or
012: * (at your option) any later version.
013: *
014: * Resin Open Source is distributed in the hope that it will be useful,
015: * but WITHOUT ANY WARRANTY; without even the implied warranty of
016: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE, or any warranty
017: * of NON-INFRINGEMENT. See the GNU General Public License for more
018: * details.
019: *
020: * You should have received a copy of the GNU General Public License
021: * along with Resin Open Source; if not, write to the
022: * Free SoftwareFoundation, Inc.
023: * 59 Temple Place, Suite 330
024: * Boston, MA 02111-1307 USA
025: *
026: * @author Alex Rojkov
027: */
028:
029: package javax.faces.convert;
030:
031: import javax.faces.component.StateHolder;
032: import javax.faces.component.UIComponent;
033: import javax.faces.context.FacesContext;
034: import javax.faces.application.FacesMessage;
035:
036: public class EnumConverter implements Converter, StateHolder {
037:
038: public static final java.lang.String CONVERTER_ID = "javax.faces.Enum";
039: public static final java.lang.String ENUM_ID = "javax.faces.converter.EnumConverter.ENUM";
040: public static final java.lang.String ENUM_NO_CLASS_ID = "javax.faces.converter.EnumConverter.ENUM_NO_CLASS";
041:
042: private Class<? extends Enum> _targetClass;
043:
044: private boolean _transient;
045:
046: public EnumConverter() {
047: }
048:
049: public EnumConverter(Class targetClass) {
050: _targetClass = targetClass;
051: }
052:
053: public Object getAsObject(FacesContext context,
054: UIComponent component, String value)
055: throws ConverterException {
056: if (_targetClass == null) {
057: FacesMessage msg = createFacesMessageForEnumNoClass(
058: context, component, value);
059: throw new ConverterException(msg);
060: }
061:
062: if (value == null)
063: return null;
064:
065: value = value.trim();
066:
067: if (value.length() == 0)
068: return null;
069:
070: try {
071: return Enum.valueOf(_targetClass, value);
072: } catch (Exception e) {
073: FacesMessage msg = createFacesMessageForEnum(context,
074: component, value);
075:
076: throw new ConverterException(msg, e);
077: }
078: }
079:
080: public String getAsString(FacesContext context,
081: UIComponent component, Object value)
082: throws ConverterException {
083: if (_targetClass == null) {
084: FacesMessage msg = createFacesMessageForEnumNoClass(
085: context, component, value);
086: throw new ConverterException(msg);
087: }
088:
089: if (value == null)
090: return null;
091:
092: if (_targetClass.isAssignableFrom(value.getClass()))
093: return value.toString();
094:
095: FacesMessage msg = createFacesMessageForEnum(context,
096: component, value);
097:
098: throw new ConverterException(msg);
099: }
100:
101: public Object saveState(FacesContext context) {
102: return _targetClass;
103: }
104:
105: public void restoreState(FacesContext context, Object state) {
106: _targetClass = (Class<? extends Enum>) state;
107: }
108:
109: public boolean isTransient() {
110: return _transient;
111: }
112:
113: public void setTransient(boolean isTransient) {
114: _transient = isTransient;
115: }
116:
117: public String toString() {
118: return "EnumConverter[]";
119: }
120:
121: private FacesMessage createFacesMessageForEnumNoClass(
122: FacesContext context, UIComponent component, Object value) {
123: String summary = Util
124: .l10n(
125: context,
126: ENUM_NO_CLASS_ID,
127: "{1}: \"{0}\" must be convertible to an enum from the enum, but no enum class provided.",
128: value, Util.getLabel(context, component));
129:
130: String detail = Util
131: .l10n(
132: context,
133: ENUM_NO_CLASS_ID + "_detail",
134: "{1}: \"{0}\" must be convertible to an enum from the enum, but no enum class provided.",
135: value, Util.getLabel(context, component));
136:
137: return new FacesMessage(summary, detail);
138: }
139:
140: private FacesMessage createFacesMessageForEnum(
141: FacesContext context, UIComponent component, Object value) {
142: String summary = Util.l10n(context, ENUM_ID,
143: "{2}: \"{0}\" must be convertible to an enum.", value,
144: getExample(), Util.getLabel(context, component));
145:
146: String detail = Util
147: .l10n(
148: context,
149: ENUM_ID + "_detail",
150: "{2}: \"{0}\" must be convertible to an enum from the enum that contains the constant \"{1}\"",
151: value, getExample(), Util.getLabel(context,
152: component));
153:
154: FacesMessage msg = new FacesMessage(summary, detail);
155: return msg;
156: }
157:
158: private Object getExample() {
159: Object[] enumConstants = _targetClass.getEnumConstants();
160:
161: if (enumConstants.length == 0)
162: return "";
163:
164: return enumConstants[0];
165: }
166:
167: }
|