1 /*
2  * Licensed to the Apache Software Foundation (ASF) under one or more
3  * contributor license agreements.  See the NOTICE file distributed with
4  * this work for additional information regarding copyright ownership.
5  * The ASF licenses this file to You under the Apache License, Version 2.0
6  * (the "License"); you may not use this file except in compliance with
7  * the License.  You may obtain a copy of the License at
8  *
9  *      http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  */

17 package org.apache.jasper.runtime;
18
19 import java.security.AccessController;
20 import java.security.PrivilegedAction;
21 import java.util.ArrayList;
22 import java.util.List;
23
24 import javax.el.CompositeELResolver;
25 import javax.el.ELContext;
26 import javax.el.ELContextEvent;
27 import javax.el.ELContextListener;
28 import javax.el.ELResolver;
29 import javax.el.ExpressionFactory;
30 import javax.servlet.ServletContext;
31 import javax.servlet.jsp.JspApplicationContext;
32 import javax.servlet.jsp.JspContext;
33
34 import org.apache.jasper.Constants;
35 import org.apache.jasper.compiler.Localizer;
36 import org.apache.jasper.el.ELContextImpl;
37 import org.apache.jasper.el.JasperELResolver;
38
39 /**
40  * Implementation of JspApplicationContext
41  *
42  * @author Jacob Hookom
43  */

44 public class JspApplicationContextImpl implements JspApplicationContext {
45
46     private static final String KEY = JspApplicationContextImpl.class.getName();
47
48     private final ExpressionFactory expressionFactory =
49             ExpressionFactory.newInstance();
50
51     private final List<ELContextListener> contextListeners = new ArrayList<>();
52
53     private final List<ELResolver> resolvers = new ArrayList<>();
54
55     private boolean instantiated = false;
56
57     private ELResolver resolver;
58
59     public JspApplicationContextImpl() {
60
61     }
62
63     @Override
64     public void addELContextListener(ELContextListener listener) {
65         if (listener == null) {
66             throw new IllegalArgumentException(Localizer.getMessage("jsp.error.nullArgument"));
67         }
68         this.contextListeners.add(listener);
69     }
70
71     public static JspApplicationContextImpl getInstance(ServletContext context) {
72         if (context == null) {
73             throw new IllegalArgumentException(Localizer.getMessage("jsp.error.nullArgument"));
74         }
75         JspApplicationContextImpl impl = (JspApplicationContextImpl) context
76                 .getAttribute(KEY);
77         if (impl == null) {
78             impl = new JspApplicationContextImpl();
79             context.setAttribute(KEY, impl);
80         }
81         return impl;
82     }
83
84     public ELContextImpl createELContext(JspContext context) {
85         if (context == null) {
86             throw new IllegalArgumentException(Localizer.getMessage("jsp.error.nullArgument"));
87         }
88
89         // create ELContext for JspContext
90         final ELResolver r = this.createELResolver();
91         ELContextImpl ctx;
92         if (Constants.IS_SECURITY_ENABLED) {
93             ctx = AccessController.doPrivileged(
94                     new PrivilegedAction<ELContextImpl>() {
95                         @Override
96                         public ELContextImpl run() {
97                             return new ELContextImpl(r);
98                         }
99                     });
100         } else {
101             ctx = new ELContextImpl(r);
102         }
103         ctx.putContext(JspContext.class, context);
104
105         // alert all ELContextListeners
106         fireListeners(ctx);
107
108         return ctx;
109     }
110
111     protected void fireListeners(ELContext elContext) {
112         ELContextEvent event = new ELContextEvent(elContext);
113         for (int i = 0; i < this.contextListeners.size(); i++) {
114             this.contextListeners.get(i).contextCreated(event);
115         }
116     }
117
118     private ELResolver createELResolver() {
119         this.instantiated = true;
120         if (this.resolver == null) {
121             CompositeELResolver r = new JasperELResolver(this.resolvers,
122                     expressionFactory.getStreamELResolver());
123             this.resolver = r;
124         }
125         return this.resolver;
126     }
127
128     @Override
129     public void addELResolver(ELResolver resolver) throws IllegalStateException {
130         if (resolver == null) {
131             throw new IllegalArgumentException(Localizer.getMessage("jsp.error.nullArgument"));
132         }
133         if (this.instantiated) {
134             throw new IllegalStateException(Localizer.getMessage("jsp.error.cannotAddResolver"));
135         }
136         this.resolvers.add(resolver);
137     }
138
139     @Override
140     public ExpressionFactory getExpressionFactory() {
141         return expressionFactory;
142     }
143
144 }
145