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.el.unified.resolver;
20  
21  import javax.el.ELContext;
22  import javax.faces.context.FacesContext;
23  import java.beans.FeatureDescriptor;
24  import java.util.Iterator;
25  import java.util.Map;
26  import java.util.Arrays;
27  
28  /**
29   * <p>
30   * This composite el resolver will be used at the top level resolver for faces
31   * ({@link javax.faces.application.Application#getELResolver()})
32   * and jsp (the one we add with {@link javax.servlet.jsp.JspApplicationContext#addELResolver(javax.el.ELResolver)}.
33   * It keeps track of its scope to let the variable resolver {@link org.apache.myfaces.el.VariableResolverImpl}
34   * know in which scope it is executed. This is
35   * necessarry to call either the faces or the jsp resolver head.
36   * </p>
37   * <p>
38   * This implementation does nothing if there is no actual faces context. This is necessarry since we registered our
39   * resolvers into the jsp engine. Therefore we have to make sure that jsp only pages where no faces context is available
40   * are still working
41   * </p>
42   *
43   * @author Mathias Broekelmann (latest modification by $Author$)
44   * @version $Revision$ $Date$
45   */
46  public final class FacesCompositeELResolver extends org.apache.myfaces.el.CompositeELResolver
47  {
48      private final Scope _scope;
49  
50      public enum Scope
51      {
52          Faces, JSP, NONE
53      }
54      
55      public static final String SCOPE = "org.apache.myfaces.el.unified.resolver.FacesCompositeELResolver.Scope";
56      
57      public FacesCompositeELResolver(final Scope scope)
58      {
59          if (scope == null)
60          {
61              throw new IllegalArgumentException("scope must not be one of " + Arrays.toString(Scope.values()));
62          }
63          _scope = scope;
64      }
65  
66      private static FacesContext facesContext(final ELContext context)
67      {
68          FacesContext facesContext = (FacesContext)context.getContext(FacesContext.class);
69          if (facesContext == null)
70          {
71              facesContext = FacesContext.getCurrentInstance();
72          }
73          return facesContext;
74      }
75      
76      @Override
77      public Class<?> getCommonPropertyType(final ELContext context, final Object base)
78      {
79          final FacesContext facesContext = facesContext(context);
80          if (facesContext == null)
81          {
82              return null;
83          }
84          final Map<Object, Object> requestMap = facesContext.getAttributes();
85          Scope prevScope = null;
86          try
87          {
88              prevScope = getScope(requestMap);
89              setScope(requestMap);
90              return super.getCommonPropertyType(context, base);
91          }
92          finally
93          {
94              if(prevScope != null)
95              {
96                  setScope(requestMap, prevScope);
97              }
98              else
99              {
100                 unsetScope(requestMap);
101             }
102         }
103 
104     }
105 
106     @Override
107     public Iterator<FeatureDescriptor> getFeatureDescriptors(final ELContext context, final Object base)
108     {
109         final FacesContext facesContext = facesContext(context);
110         if (facesContext == null)
111         {
112             return null;
113         }
114         final Map<Object, Object> requestMap = facesContext.getAttributes();
115         Scope prevScope = null;
116         try
117         {
118             prevScope = getScope(requestMap);
119             setScope(requestMap);
120             return super.getFeatureDescriptors(context, base);
121 
122         }
123         finally
124         {
125             if(prevScope != null)
126             {
127                 setScope(requestMap, prevScope);
128             }
129             else
130             {
131                 unsetScope(requestMap);
132             }
133         }
134     }
135 
136     @Override
137     public Class<?> getType(final ELContext context, final Object base, final Object property)
138     {
139         final FacesContext facesContext = facesContext(context);
140         if (facesContext == null)
141         {
142             return null;
143         }
144         final Map<Object, Object> requestMap = facesContext.getAttributes();
145         Scope prevScope = null;
146         try
147         {
148             prevScope = getScope(requestMap);
149             setScope(requestMap);
150             return super.getType(context, base, property);
151         }
152         finally
153         {
154             if(prevScope != null)
155             {
156                 setScope(requestMap, prevScope);
157             }
158             else
159             {
160                 unsetScope(requestMap);
161             }
162         }
163     }
164 
165     @Override
166     public Object getValue(final ELContext context, final Object base, final Object property)
167     {
168         final FacesContext facesContext = facesContext(context);
169         if (facesContext == null)
170         {
171             return null;
172         }
173         final Map<Object, Object> requestMap = facesContext.getAttributes();
174         Scope prevScope = null;
175         try
176         {
177             prevScope = getScope(requestMap);
178             setScope(requestMap);
179             return super.getValue(context, base, property);
180         }
181         finally
182         {
183             if(prevScope != null)
184             {
185                 setScope(requestMap, prevScope);
186             }
187             else
188             {
189                 unsetScope(requestMap);
190             }
191         }
192     }
193 
194     @Override
195     public boolean isReadOnly(final ELContext context, final Object base, final Object property)
196     {
197         final FacesContext facesContext = facesContext(context);
198         if (facesContext == null)
199         {
200             return false;
201         }
202         final Map<Object, Object> requestMap = facesContext.getAttributes();
203         Scope prevScope = null;
204         try
205         {
206             prevScope = getScope(requestMap);
207             setScope(requestMap);
208             return super.isReadOnly(context, base, property);
209         }
210         finally
211         {
212             if(prevScope != null)
213             {
214                 setScope(requestMap, prevScope);
215             }
216             else
217             {
218                 unsetScope(requestMap);
219             }
220         }
221     }
222 
223     @Override
224     public void setValue(final ELContext context, final Object base, final Object property, final Object val)
225     {
226         final FacesContext facesContext = facesContext(context);
227         if (facesContext == null)
228         {
229             return;
230         }
231         final Map<Object, Object> requestMap = facesContext.getAttributes();
232         Scope prevScope = null;
233         try
234         {
235             prevScope = getScope(requestMap);
236             setScope(requestMap);
237             super.setValue(context, base, property, val);
238 
239         }
240         finally
241         {
242             if(prevScope != null)
243             {
244                 setScope(requestMap, prevScope);
245             }
246             else
247             {
248                 unsetScope(requestMap);
249             }
250         }
251     }
252 
253     private void setScope(final Map<Object, Object> attributes)
254     {
255         attributes.put(SCOPE, _scope);
256     }
257     
258     private Scope getScope(final Map<Object, Object> attributes)
259     {
260         return (Scope) attributes.get(SCOPE);
261     }
262 
263     private void setScope(final Map<Object, Object> attributes, Scope prevScope)
264     {
265         attributes.put(SCOPE, prevScope);
266     }
267 
268     private static void unsetScope(final Map<Object, Object> attributes)
269     {
270         //attributes.remove(SCOPE);
271         attributes.put(SCOPE, Scope.NONE);
272     }
273 }