View Javadoc

1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one
3    * or more contributor license agreements.  See the NOTICE file
4    * distributed with this work for additional information
5    * regarding copyright ownership.  The ASF licenses this file
6    * to you under the Apache License, Version 2.0 (the
7    * "License"); you may not use this file except in compliance
8    * with the License.  You may obtain a copy of the License at
9    *
10   *   http://www.apache.org/licenses/LICENSE-2.0
11   *
12   * Unless required by applicable law or agreed to in writing,
13   * software distributed under the License is distributed on an
14   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15   * KIND, either express or implied.  See the License for the
16   * specific language governing permissions and limitations
17   * under the License.
18   */
19  package org.apache.myfaces.taglib.core;
20  
21  import javax.el.ELContext;
22  import javax.el.ValueExpression;
23  import javax.faces.component.StateHolder;
24  import javax.faces.component.UIComponent;
25  import javax.faces.context.FacesContext;
26  import javax.faces.convert.Converter;
27  import javax.faces.convert.ConverterException;
28  
29  /**
30   * This class is used in conjunction with ConverterImplTag. 
31   * 
32   * When a tag like this is in a jsp page:
33   * <code>
34   * &lt;f:converter binding="#{mybean}"/&gt;
35   *  
36   *  or
37   *  
38   * &lt;f:converter converterId="#{'anyid'}" binding="#{mybean}"/&gt;
39   * </code>
40   * The value of mybean could be already on the context, so this
41   * converter avoid creating a new variable and use the previous one.
42   * 
43   * @author Leonardo Uribe (latest modification by $Author$)
44   * @version $Revision$ $Date$ 
45   */
46  public class DelegateConverter implements Converter, StateHolder
47  {
48  
49      private ValueExpression _converterId;
50      private ValueExpression _binding;
51      private String _converterIdString = null;
52      
53      public DelegateConverter()
54      {
55          
56      }
57      
58      public DelegateConverter(ValueExpression id, ValueExpression binding, String converterIdString)
59      {
60          super();
61          _converterId = id;
62          _binding = binding;
63          _converterIdString = converterIdString;
64      }
65  
66      public boolean isTransient()
67      {
68          return false;
69      }
70  
71      public void restoreState(FacesContext facesContext, Object state)
72      {
73          Object[] values = (Object[]) state;
74          _converterId = (ValueExpression) values[0];
75          _binding = (ValueExpression) values[1];
76          _converterIdString = (String) values[2];
77      }
78  
79      public Object saveState(FacesContext facesContext)
80      {
81          Object[] values = new Object[3];
82          values[0] = _converterId;
83          values[1] = _binding;
84          values[2] = _converterIdString;
85          return values;
86      }
87  
88      public void setTransient(boolean arg0)
89      {
90          // Do nothing        
91      }
92  
93      public Object getAsObject(FacesContext facesContext, UIComponent component,
94              String value)
95      {
96          return _getDelegate().getAsObject(facesContext, component, value);
97      }
98  
99      public String getAsString(FacesContext facesContext, UIComponent component,
100             Object value)
101     {
102         return _getDelegate().getAsString(facesContext, component, value);
103     }
104 
105     private Converter _getDelegate()
106     {
107         return _createConverter();
108     }
109 
110     private Converter _createConverter()
111     {
112         Converter converter = null;
113 
114         FacesContext facesContext = FacesContext.getCurrentInstance();
115         ELContext elContext = facesContext.getELContext();
116 
117         // try to create the converter from the binding expression first, and then from
118         // the converterId
119         if (_binding != null)
120         {
121             try
122             {
123                 converter = (Converter) _binding.getValue(elContext);
124 
125                 if (converter != null)
126                 {
127                     return converter;
128                 }
129             }
130             catch (Exception e)
131             {
132                 throw new ConverterException("Exception creating converter using binding", e);
133             }
134         }
135 
136         if ((_converterId != null) || (_converterIdString != null))
137         {
138             try
139             {
140                 if (null != _converterIdString)
141                 {
142                     converter = facesContext.getApplication().createConverter(_converterIdString);
143                 }
144                 else
145                 {
146                     String converterId = (String) _converterId.getValue(elContext);
147                     converter = facesContext.getApplication().createConverter(converterId);
148                 }
149 
150                 // with binding no converter was created, set its value with the converter
151                 // created using the converterId
152                 if (converter != null && _binding != null)
153                 {
154                     _binding.setValue(elContext, converter);
155                 }
156             }
157             catch (Exception e)
158             {
159                 throw new ConverterException("Exception creating converter with converterId: " + _converterId, e);
160             }
161         }
162         
163         if (converter == null)
164         {
165             throw new IllegalStateException("Could not create converter. Please specify a valid converterId" +
166                     " or a non-null binding.");
167         }
168 
169         return converter;
170     }
171 
172 }