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.view.facelets.impl;
20  
21  import java.io.IOException;
22  import java.net.URL;
23  import java.util.ArrayList;
24  import java.util.HashSet;
25  import java.util.Iterator;
26  import java.util.LinkedList;
27  import java.util.List;
28  import java.util.Set;
29  
30  import javax.el.ELContext;
31  import javax.el.ELException;
32  import javax.el.ELResolver;
33  import javax.el.ExpressionFactory;
34  import javax.el.FunctionMapper;
35  import javax.el.ValueExpression;
36  import javax.el.VariableMapper;
37  import javax.faces.FacesException;
38  import javax.faces.application.Resource;
39  import javax.faces.component.UIComponent;
40  import javax.faces.context.FacesContext;
41  import javax.faces.view.facelets.FaceletContext;
42  import javax.faces.view.facelets.FaceletException;
43  
44  import org.apache.myfaces.view.facelets.AbstractFacelet;
45  import org.apache.myfaces.view.facelets.AbstractFaceletContext;
46  import org.apache.myfaces.view.facelets.ELExpressionCacheMode;
47  import org.apache.myfaces.view.facelets.FaceletCompositionContext;
48  import org.apache.myfaces.view.facelets.PageContext;
49  import org.apache.myfaces.view.facelets.TemplateClient;
50  import org.apache.myfaces.view.facelets.TemplateContext;
51  import org.apache.myfaces.view.facelets.TemplateManager;
52  import org.apache.myfaces.view.facelets.el.DefaultVariableMapper;
53  import org.apache.myfaces.view.facelets.el.VariableMapperBase;
54  import org.apache.myfaces.view.facelets.tag.jsf.core.AjaxHandler;
55  
56  /**
57   * Default FaceletContext implementation.
58   * 
59   * A single FaceletContext is used for all Facelets involved in an invocation of
60   * {@link org.apache.myfaces.view.facelets.Facelet#apply(FacesContext, UIComponent)
61   * Facelet#apply(FacesContext, UIComponent)}. This
62   * means that included Facelets are treated the same as the JSP include directive.
63   * 
64   * @author Jacob Hookom
65   * @version $Id: DefaultFaceletContext.java 1523365 2013-09-15 00:11:31Z lu4242 $
66   */
67  final class DefaultFaceletContext extends AbstractFaceletContext
68  {
69      private final FacesContext _faces;
70  
71      private final ELContext _ctx;
72  
73      private final AbstractFacelet _facelet;
74      private final List<AbstractFacelet> _faceletHierarchy;
75  
76      private VariableMapper _varMapper;
77      private final DefaultVariableMapper _defaultVarMapper;
78      private VariableMapperBase _varMapperBase;
79  
80      private FunctionMapper _fnMapper;
81  
82      //private final Map<String, Integer> _ids;
83      //private final Map<Integer, Integer> _prefixes;
84      private String _prefix;
85  
86      private StringBuilder _uniqueIdBuilder;
87  
88      //private final LinkedList<TemplateManager> _clients;
89      
90      private final FaceletCompositionContext _mctx;
91      
92      private LinkedList<AjaxHandler> _ajaxHandlerStack;
93      
94      private final List<TemplateContext> _isolatedTemplateContext;
95      
96      private int _currentTemplateContext;
97      
98      private ELExpressionCacheMode _elExpressionCacheMode;
99      
100     private boolean _isCacheELExpressions;
101 
102     private final List<PageContext> _isolatedPageContext;
103     
104     public DefaultFaceletContext(DefaultFaceletContext ctx,
105             AbstractFacelet facelet, boolean ccWrap)
106     {
107         _ctx = ctx._ctx;
108         //_ids = ctx._ids;
109         //_prefixes = ctx._prefixes;
110         //_clients = ctx._clients;
111         _faces = ctx._faces;
112         _fnMapper = ctx._fnMapper;
113         _varMapper = ctx._varMapper;
114         _defaultVarMapper = ctx._defaultVarMapper;
115         _varMapperBase = ctx._varMapperBase;
116         _faceletHierarchy = new ArrayList<AbstractFacelet>(ctx._faceletHierarchy
117                 .size() + 1);
118         _faceletHierarchy.addAll(ctx._faceletHierarchy);
119         _faceletHierarchy.add(facelet);
120         _facelet = facelet;
121         _mctx = ctx._mctx;
122         
123         if (ccWrap)
124         {
125             // Each time a composite component is being applied, a new
126             // ajax stack should be created, and f:ajax tags outside the
127             // composite component should be ignored.
128             _ajaxHandlerStack = null;
129         }
130         else
131         {
132             // It is a template include, the current ajax stack should be
133             // preserved.
134             _ajaxHandlerStack = ctx._ajaxHandlerStack;
135         }
136         
137         // It is not necessary to create a copy of this array, because we always use
138         // pushTemplateContext(TemplateContext) / popTemplateContext() and
139         // pushCompositeComponentClient(final TemplateClient client) / popCompositeComponentClient()
140         // in pairs.
141         //_isolatedTemplateContext = new ArrayList<TemplateContext>(ctx._isolatedTemplateContext.size()+1);
142         //for (int i = 0; i <= ctx._currentTemplateContext; i++)
143         //{
144         //    _isolatedTemplateContext.add(ctx._isolatedTemplateContext.get(i));
145         //}
146         _isolatedTemplateContext = ctx._isolatedTemplateContext;
147         _currentTemplateContext = ctx._currentTemplateContext;
148         
149         _isolatedPageContext = ctx._isolatedPageContext;
150         
151         _elExpressionCacheMode = ctx._elExpressionCacheMode;
152         _isCacheELExpressions = ctx._isCacheELExpressions;
153 
154     }
155 
156     public DefaultFaceletContext(FacesContext faces, AbstractFacelet facelet, FaceletCompositionContext mctx)
157     {
158         _ctx = faces.getELContext();
159         //_ids = new HashMap<String, Integer>();
160         //_prefixes = new HashMap<Integer, Integer>();
161         //_clients = new LinkedList<TemplateManager>();
162         _faces = faces;
163         _fnMapper = _ctx.getFunctionMapper();
164         _varMapper = _ctx.getVariableMapper();
165         if (_varMapper == null)
166         {
167             _defaultVarMapper = new DefaultVariableMapper();
168             _varMapper = _defaultVarMapper;
169             _varMapperBase = _defaultVarMapper;
170         }
171         else
172         {
173             _defaultVarMapper = new DefaultVariableMapper(_varMapper);
174             _varMapper = _defaultVarMapper;
175             _varMapperBase = _defaultVarMapper;
176         }
177         
178         _faceletHierarchy = new ArrayList<AbstractFacelet>(1);
179         _faceletHierarchy.add(facelet);
180         _facelet = facelet;
181         _mctx = mctx;
182         
183         _isolatedTemplateContext = new ArrayList<TemplateContext>(1);
184         _isolatedTemplateContext.add(new TemplateContextImpl());
185         _currentTemplateContext = 0;
186         _defaultVarMapper.setTemplateContext(_isolatedTemplateContext.get(_currentTemplateContext));
187         
188         _isolatedPageContext = new ArrayList<PageContext>(8);
189         
190         _elExpressionCacheMode = mctx.getELExpressionCacheMode();
191         _isCacheELExpressions = !ELExpressionCacheMode.noCache.equals(_elExpressionCacheMode);
192     }
193 
194     /**
195      * {@inheritDoc}
196      */
197     @Override
198     public FacesContext getFacesContext()
199     {
200         return _faces;
201     }
202 
203     /**
204      * {@inheritDoc}
205      */
206     @Override
207     public ExpressionFactory getExpressionFactory()
208     {
209         return _facelet.getExpressionFactory();
210     }
211 
212     /**
213      * {@inheritDoc}
214      */
215     @Override
216     public void setVariableMapper(VariableMapper varMapper)
217     {
218         // Assert.param("varMapper", varMapper);
219         _varMapper = varMapper;
220         _varMapperBase = (_varMapper instanceof VariableMapperBase) ? (VariableMapperBase) varMapper : null;
221     }
222 
223     /**
224      * {@inheritDoc}
225      */
226     @Override
227     public void setFunctionMapper(FunctionMapper fnMapper)
228     {
229         // Assert.param("fnMapper", fnMapper);
230         _fnMapper = fnMapper;
231     }
232 
233     /**
234      * {@inheritDoc}
235      */
236     @Override
237     public void includeFacelet(UIComponent parent, String relativePath)
238             throws IOException
239     {
240         _facelet.include(this, parent, relativePath);
241     }
242 
243     /**
244      * {@inheritDoc}
245      */
246     @Override
247     public FunctionMapper getFunctionMapper()
248     {
249         return _fnMapper;
250     }
251 
252     /**
253      * {@inheritDoc}
254      */
255     @Override
256     public VariableMapper getVariableMapper()
257     {
258         return _varMapper;
259     }
260 
261     /**
262      * {@inheritDoc}
263      */
264     @Override
265     @SuppressWarnings("unchecked")
266     public Object getContext(Class key)
267     {
268         return _ctx.getContext(key);
269     }
270 
271     /**
272      * {@inheritDoc}
273      */
274     @Override
275     @SuppressWarnings("unchecked")
276     public void putContext(Class key, Object contextObject)
277     {
278         _ctx.putContext(key, contextObject);
279     }
280 
281     /**
282      * {@inheritDoc}
283      */
284     @Override
285     public String generateUniqueId(String base)
286     {
287         if (_prefix == null)
288         {
289             _uniqueIdBuilder = new StringBuilder(
290                     _faceletHierarchy.size() * 30);
291             for (int i = 0; i < _faceletHierarchy.size(); i++)
292             {
293                 AbstractFacelet facelet = _faceletHierarchy.get(i);
294                 _uniqueIdBuilder.append(facelet.getFaceletId());
295             }
296 
297             // Integer prefixInt = new Integer(builder.toString().hashCode());
298             // -= Leonardo Uribe =- if the previous formula is used, it is possible that
299             // negative values are introduced. The presence of '-' char causes problems
300             // with htmlunit 2.4 or lower, so in order to prevent it it is better to use
301             // only positive values instead.
302             // Take into account CompilationManager.nextTagId() uses Math.abs too.
303             Integer prefixInt = new Integer(Math.abs(_uniqueIdBuilder.toString().hashCode()));
304             _prefix = prefixInt.toString();
305         }
306 
307         _uniqueIdBuilder.setLength(0);
308         // getFaceletCompositionContext().generateUniqueId() is the one who ensures
309         // the final id will be unique, but prefix and base ensure it will be unique
310         // per facelet because prefix is calculated from faceletHierarchy and base is
311         // related to the tagId, which depends on the location.
312         //_uniqueIdBuilder.append(getFaceletCompositionContext().generateUniqueId());
313         
314         String uniqueIdFromIterator = getFaceletCompositionContext().getUniqueIdFromIterator();
315         if (uniqueIdFromIterator == null)
316         {
317             getFaceletCompositionContext().generateUniqueId(_uniqueIdBuilder);
318             // Since two different facelets are used to build the metadata, it is necessary
319             // to trim the "base" part from the returned unique id, to ensure the components will be
320             // refreshed properly. Note the "base" part is the one that allows to ensure
321             // uniqueness between two different facelets with the same <f:metadata>, but since by 
322             // spec view metadata sections cannot live on template client facelets, this case is
323             // just not possible. 
324             // MYFACES-3709 It was also noticed that in some cases, the prefix should also
325             // be excluded from the id. The prefix is included if the metadata section is
326             // applied inside an included section (by ui:define and ui:insert for example).
327             if (!getFaceletCompositionContext().isInMetadataSection())
328             {
329                 _uniqueIdBuilder.append("_");
330                 _uniqueIdBuilder.append(_prefix);
331                 _uniqueIdBuilder.append("_");
332                 _uniqueIdBuilder.append(base);
333             }
334             uniqueIdFromIterator = _uniqueIdBuilder.toString();
335             getFaceletCompositionContext().addUniqueId(uniqueIdFromIterator);
336             return uniqueIdFromIterator;
337         }
338         else
339         {
340             getFaceletCompositionContext().incrementUniqueId();
341             return uniqueIdFromIterator;
342         }
343     }
344 
345     /**
346      * {@inheritDoc}
347      */
348     @Override
349     public Object getAttribute(String name)
350     {
351         if (_varMapper != null)
352         {
353             ValueExpression ve = _varMapper.resolveVariable(name);
354             if (ve != null)
355             {
356                 return ve.getValue(this);
357             }
358         }
359         return null;
360     }
361 
362     /**
363      * {@inheritDoc}
364      */
365     @Override
366     public void setAttribute(String name, Object value)
367     {
368         if (_varMapper != null)
369         {
370             if (value == null)
371             {
372                 _varMapper.setVariable(name, null);
373             }
374             else
375             {
376                 _varMapper.setVariable(name, _facelet.getExpressionFactory()
377                         .createValueExpression(value, Object.class));
378             }
379         }
380     }
381 
382     /**
383      * {@inheritDoc}
384      */
385     @Override
386     public void includeFacelet(UIComponent parent, URL absolutePath)
387             throws IOException, FacesException, ELException
388     {
389         _facelet.include(this, parent, absolutePath);
390     }
391 
392     /**
393      * {@inheritDoc}
394      */
395     @Override
396     public ELResolver getELResolver()
397     {
398         return _ctx.getELResolver();
399     }
400 
401     //Begin methods from AbstractFaceletContext
402 
403     @Override
404     public TemplateManager popClient(TemplateClient client)
405     {
406         //if (!this._clients.isEmpty())
407         //{
408         //    Iterator<TemplateManager> itr = this._clients.iterator();
409         //    while (itr.hasNext())
410         //    {
411         //        if (itr.next().equals(client))
412         //        {
413         //            itr.remove();
414         //            return;
415         //        }
416         //    }
417         //}
418         //throw new IllegalStateException(client + " not found");
419         //return _clients.removeFirst();
420         return _isolatedTemplateContext.get(_currentTemplateContext).popClient(this);
421     }
422 
423     @Override
424     public void pushClient(final TemplateClient client)
425     {
426         //this._clients.add(0, new TemplateManager(this._facelet, client, true));
427         //_clients.addFirst(new TemplateManagerImpl(this._facelet, client, true));
428         _isolatedTemplateContext.get(_currentTemplateContext).pushClient(this, this._facelet, client);
429     }
430 
431     public TemplateManager popExtendedClient(TemplateClient client)
432     {
433         //return _clients.removeLast();
434         return _isolatedTemplateContext.get(_currentTemplateContext).popExtendedClient(this);
435     }
436     
437     @Override
438     public void extendClient(final TemplateClient client)
439     {
440         //this._clients.add(new TemplateManager(this._facelet, client, false));
441         //_clients.addLast(new TemplateManagerImpl(this._facelet, client, false));
442         _isolatedTemplateContext.get(_currentTemplateContext).extendClient(this, this._facelet, client);
443     }
444 
445     @Override
446     public boolean includeDefinition(UIComponent parent, String name)
447             throws IOException, FaceletException, FacesException, ELException
448     {
449         //boolean found = false;
450         //TemplateManager client;
451         //for (int i = 0, size = this._clients.size(); i < size && !found; i++)
452         //{
453         //    client = ((TemplateManager) this._clients.get(i));
454         //    if (client.equals(this._facelet))
455         //        continue;
456         //    found = client.apply(this, parent, name);
457         //}
458         //return found;
459         return _isolatedTemplateContext.get(_currentTemplateContext).includeDefinition(
460                 this, this._facelet, parent, name);
461     }
462 
463     /*
464     private final static class TemplateManagerImpl extends TemplateManager implements TemplateClient
465     {
466         private final DefaultFacelet _owner;
467 
468         private final TemplateClient _target;
469 
470         private final boolean _root;
471 
472         private final Set<String> _names = new HashSet<String>();
473 
474         public TemplateManagerImpl(DefaultFacelet owner, TemplateClient target,
475                 boolean root)
476         {
477             this._owner = owner;
478             this._target = target;
479             this._root = root;
480         }
481 
482         public boolean apply(FaceletContext ctx, UIComponent parent, String name)
483                 throws IOException, FacesException, FaceletException,
484                 ELException
485         {
486             String testName = (name != null) ? name : "facelets._NULL_DEF_";
487             if (this._names.contains(testName))
488             {
489                 return false;
490             }
491             else
492             {
493                 this._names.add(testName);
494                 boolean found = false;
495                 found = this._target
496                         .apply(new DefaultFaceletContext(
497                                 (DefaultFaceletContext) ctx, this._owner, false),
498                                 parent, name);
499                 this._names.remove(testName);
500                 return found;
501             }
502         }
503 
504         public boolean equals(Object o)
505         {
506             // System.out.println(this.owner.getAlias() + " == " +
507             // ((DefaultFacelet) o).getAlias());
508             return this._owner == o || this._target == o;
509         }
510 
511         public boolean isRoot()
512         {
513             return this._root;
514         }
515     }*/
516 
517     /*
518     @Override
519     public TemplateManager popCompositeComponentClient(boolean cleanClientStack)
520     {
521         //if (!this._compositeComponentClients.isEmpty())
522         //{
523             //if (cleanClientStack)
524             //{
525             //    _clientsStack.get(_currentClientStack).clear();
526             //}
527             //_currentClientStack--;
528             //return this._compositeComponentClients.remove(0);
529         //}
530         if (_currentTemplateContext > 0)
531         {
532             TemplateManager tm = _isolatedTemplateContext.get(_currentTemplateContext).getCompositeComponentClient();
533             if (cleanClientStack)
534             {
535                 _isolatedTemplateContext.get(_currentTemplateContext).clear();
536             }
537             _currentTemplateContext--;
538             return tm;
539         }
540         return null;
541     }
542     
543 
544     @Override
545     public void pushCompositeComponentClient(final TemplateClient client)
546     {
547         //this._compositeComponentClients.add(0, new CompositeComponentTemplateManager(this._facelet, client));
548         //if (_currentClientStack + 1 <= _clientsStack.size())
549         //{
550         //    _clientsStack.add(new LinkedList<TemplateManager>());
551         //}
552         //_currentClientStack++;
553         if (_currentTemplateContext + 1 <= _isolatedTemplateContext.size())
554         {
555             _isolatedTemplateContext.add(new IsolatedTemplateContextImpl());
556         }
557         _currentTemplateContext++;
558         _isolatedTemplateContext.get(_currentTemplateContext).setCompositeComponentClient(
559             new CompositeComponentTemplateManager(this._facelet, client));
560     }
561     
562     @Override
563     public void pushCompositeComponentClient(final TemplateManager client)
564     {
565         //this._compositeComponentClients.add(0, client);
566         //if (_currentClientStack + 1 < _clientsStack.size())
567         //{
568         //    _clientsStack.add(new LinkedList<TemplateManager>());
569         //}
570         //_currentClientStack++;
571         if (_currentTemplateContext + 1 < _isolatedTemplateContext.size())
572         {
573             _isolatedTemplateContext.add(new IsolatedTemplateContextImpl());
574         }
575         _currentTemplateContext++;
576         _isolatedTemplateContext.get(_currentTemplateContext).setCompositeComponentClient(client);
577     }*/
578     
579     @Override
580     public void pushCompositeComponentClient(final TemplateClient client)
581     {
582         TemplateContext itc = new TemplateContextImpl();
583         itc.setCompositeComponentClient(
584                 new CompositeComponentTemplateManager(this._facelet, client, getPageContext()));
585         _isolatedTemplateContext.add(itc);
586         _currentTemplateContext++;
587         _defaultVarMapper.setTemplateContext(itc);
588     }
589     
590     @Override
591     public void popCompositeComponentClient()
592     {
593         if (_currentTemplateContext > 0)
594         {
595             _isolatedTemplateContext.remove(_currentTemplateContext);
596             _currentTemplateContext--;
597             _defaultVarMapper.setTemplateContext(_isolatedTemplateContext.get(_currentTemplateContext));
598         }
599     }
600     
601     @Override
602     public void pushTemplateContext(TemplateContext client)
603     {
604         _isolatedTemplateContext.add(client);
605         _currentTemplateContext++;
606         _defaultVarMapper.setTemplateContext(client);
607     }    
608 
609     
610     @Override
611     public TemplateContext popTemplateContext()
612     {
613         if (_currentTemplateContext > 0)
614         {
615             TemplateContext itc = _isolatedTemplateContext.get(_currentTemplateContext);
616             _isolatedTemplateContext.remove(_currentTemplateContext);
617             _currentTemplateContext--;
618             _defaultVarMapper.setTemplateContext(_isolatedTemplateContext.get(_currentTemplateContext));
619             return itc;
620         }
621         return null;
622     }
623     
624     @Override
625     public TemplateContext getTemplateContext()
626     {
627         return _isolatedTemplateContext.get(_currentTemplateContext);
628     }
629 
630     @Override
631     public boolean includeCompositeComponentDefinition(UIComponent parent, String name)
632             throws IOException, FaceletException, FacesException, ELException
633     {
634         //boolean found = false;
635         //TemplateManager client;
636 
637         //for (int i = 0, size = this._compositeComponentClients.size(); i < size && !found; i++)
638         //{
639         //    client = ((TemplateManager) this._compositeComponentClients.get(i));
640         //    if (client.equals(this._facelet))
641         //        continue;
642         //    found = client.apply(this, parent, name);
643         //}
644 
645         //return found;
646         TemplateClient ccClient = _isolatedTemplateContext.get(_currentTemplateContext).getCompositeComponentClient();
647         if (ccClient != null)
648         {
649             return ccClient.apply(this, parent, name);
650         }
651         return false;
652     }
653     
654     private final static class CompositeComponentTemplateManager extends TemplateManager implements TemplateClient
655     {
656         private final AbstractFacelet _owner;
657 
658         protected final TemplateClient _target;
659 
660         private final Set<String> _names = new HashSet<String>();
661         
662         private final PageContext _pageContext;
663 
664         public CompositeComponentTemplateManager(AbstractFacelet owner, TemplateClient target, PageContext pageContext)
665         {
666             this._owner = owner;
667             this._target = target;
668             this._pageContext = pageContext;
669         }
670 
671         public boolean apply(FaceletContext ctx, UIComponent parent, String name)
672                 throws IOException, FacesException, FaceletException,
673                 ELException
674         {
675             String testName = (name != null) ? name : "facelets._NULL_DEF_";
676             if (this._names.contains(testName))
677             {
678                 return false;
679             }
680             else
681             {
682                 this._names.add(testName);
683                 boolean found = false;
684                 AbstractFaceletContext actx = new DefaultFaceletContext(
685                         (DefaultFaceletContext) ctx, this._owner, false);
686                 ctx.getFacesContext().getAttributes().put(FaceletContext.FACELET_CONTEXT_KEY, actx);
687                 try
688                 {
689                     actx.pushPageContext(this._pageContext);
690                     found = this._target
691                             .apply(actx,
692                                     parent, name);
693                 }
694                 finally
695                 {
696                     actx.popPageContext();
697                 }
698                 ctx.getFacesContext().getAttributes().put(FaceletContext.FACELET_CONTEXT_KEY, ctx);
699                 this._names.remove(testName);
700                 return found;
701             }
702         }
703 
704         public boolean equals(Object o)
705         {
706             // System.out.println(this.owner.getAlias() + " == " +
707             // ((DefaultFacelet) o).getAlias());
708             return this._owner == o || this._target == o;
709         }
710 
711         @Override
712         public int hashCode()
713         {
714             int result = _owner != null ? _owner.hashCode() : 0;
715             result = 31 * result + (_target != null ? _target.hashCode() : 0);
716             return result;
717         }
718     }
719     
720     @Override
721     public void pushPageContext(PageContext client)
722     {
723         _isolatedPageContext.add(client);
724         _defaultVarMapper.setPageContext(client);
725     }    
726 
727     @Override
728     public PageContext popPageContext()
729     {
730         if (!_isolatedPageContext.isEmpty())
731         {
732             int currentPageContext = _isolatedPageContext.size()-1;
733             PageContext itc = _isolatedPageContext.get(currentPageContext);
734             _isolatedPageContext.remove(currentPageContext);
735             if (!_isolatedPageContext.isEmpty())
736             {
737                 _defaultVarMapper.setPageContext(getPageContext());
738             }
739             else
740             {
741                 _defaultVarMapper.setPageContext(null);
742             }
743             return itc;
744         }
745         return null;
746     }
747     
748     @Override
749     public PageContext getPageContext()
750     {
751         return _isolatedPageContext.get(_isolatedPageContext.size()-1);
752     }
753     
754     //End methods from AbstractFaceletContext
755     
756     /**
757      * {@inheritDoc}
758      */
759     @Override
760     public boolean isPropertyResolved()
761     {
762         return _ctx.isPropertyResolved();
763     }
764 
765     /**
766      * {@inheritDoc}
767      */
768     @Override
769     public void setPropertyResolved(boolean resolved)
770     {
771         _ctx.setPropertyResolved(resolved);
772     }
773 
774     @Override
775     public void applyCompositeComponent(UIComponent parent, Resource resource)
776             throws IOException, FaceletException, FacesException, ELException
777     {
778         _facelet.applyCompositeComponent(this, parent, resource);
779     }
780 
781     @Override
782     public Iterator<AjaxHandler> getAjaxHandlers()
783     {
784         if (_ajaxHandlerStack != null && !_ajaxHandlerStack.isEmpty())
785         {
786             return _ajaxHandlerStack.iterator();
787         }
788         return null;
789     }
790 
791     @Override
792     public void popAjaxHandlerToStack()
793     {
794         if (_ajaxHandlerStack != null && !_ajaxHandlerStack.isEmpty())
795         {
796             _ajaxHandlerStack.removeFirst();
797         }
798     }
799 
800     @Override
801     public void pushAjaxHandlerToStack(
802             AjaxHandler parent)
803     {
804         if (_ajaxHandlerStack == null)
805         {
806             _ajaxHandlerStack = new LinkedList<AjaxHandler>();
807         }
808 
809         _ajaxHandlerStack.addFirst(parent);
810     }
811 
812     @Override
813     public boolean isBuildingCompositeComponentMetadata()
814     {
815         return _facelet.isBuildingCompositeComponentMetadata();
816     }
817     
818     public FaceletCompositionContext getFaceletCompositionContext()
819     {
820         return _mctx;
821     }
822     
823     public boolean isAnyFaceletsVariableResolved()
824     {
825         //if (isAllowCacheELExpressions() && _varMapperBase != null)
826         if (_varMapperBase != null)
827         {
828             return _varMapperBase.isAnyFaceletsVariableResolved();
829         }
830         return true;
831     }
832     
833     public boolean isAllowCacheELExpressions()
834     {
835         return _isCacheELExpressions && getTemplateContext().isAllowCacheELExpressions() 
836                 && getPageContext().isAllowCacheELExpressions();
837     }
838     
839     public void beforeConstructELExpression()
840     {
841         //if (isAllowCacheELExpressions() && _varMapperBase != null)
842         if (_varMapperBase != null)
843         {
844             _varMapperBase.beforeConstructELExpression();
845         }
846     }
847     
848     public void afterConstructELExpression()
849     {
850         //if (isAllowCacheELExpressions() && _varMapperBase != null)
851         if (_varMapperBase != null)
852         {
853             _varMapperBase.afterConstructELExpression();
854         }
855     }
856     
857     public ELExpressionCacheMode getELExpressionCacheMode()
858     {
859         return _elExpressionCacheMode;
860     }
861     
862 }