1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20 package org.archive.wayback.util.webapp;
21
22 import java.io.IOException;
23 import java.util.ArrayList;
24 import java.util.Collection;
25 import java.util.HashMap;
26 import java.util.Iterator;
27 import java.util.logging.Logger;
28
29 import javax.servlet.ServletContext;
30 import javax.servlet.ServletException;
31 import javax.servlet.http.HttpServletRequest;
32 import javax.servlet.http.HttpServletResponse;
33
34 import org.archive.wayback.core.UIResults;
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50 public class RequestMapper {
51
52 private static final Logger LOGGER = Logger.getLogger(
53 RequestMapper.class.getName());
54
55 private ArrayList<ShutdownListener> shutdownListeners = null;
56
57 private HashMap<Integer,PortMapper> portMap = null;
58 private RequestHandler globalPreRequestHandler = null;
59 private RequestHandler globalPostRequestHandler = null;
60
61
62
63
64
65
66 public static final String REQUEST_CONTEXT_PREFIX =
67 "webapp-request-context-path-prefix";
68
69
70
71
72 public final static String GLOBAL_PRE_REQUEST_HANDLER = "-";
73
74
75
76 public final static String GLOBAL_POST_REQUEST_HANDLER = "+";
77
78
79
80
81
82
83
84
85
86
87
88 public RequestMapper(Collection<RequestHandler> requestHandlers,
89 ServletContext servletContext) {
90 portMap = new HashMap<Integer, PortMapper>();
91 shutdownListeners = new ArrayList<ShutdownListener>();
92 Iterator<RequestHandler> itr = requestHandlers.iterator();
93 LOGGER.info("Registering handlers.");
94 while(itr.hasNext()) {
95 RequestHandler requestHandler = itr.next();
96 requestHandler.setServletContext(servletContext);
97 requestHandler.registerPortListener(this);
98 }
99 LOGGER.info("Registering handlers complete.");
100 }
101
102
103
104
105
106
107
108 public void addShutdownListener(ShutdownListener shutdownListener) {
109 shutdownListeners.add(shutdownListener);
110 }
111
112
113
114
115
116 public void addGlobalPreRequestHandler(RequestHandler requestHandler) {
117 globalPreRequestHandler = requestHandler;
118 }
119
120
121
122
123
124 public void addGlobalPostRequestHandler(RequestHandler requestHandler) {
125 globalPostRequestHandler = requestHandler;
126 }
127
128
129
130
131
132
133
134
135
136
137 public void addRequestHandler(int port, String host, String path,
138 RequestHandler requestHandler) {
139 Integer portInt = Integer.valueOf(port);
140 PortMapper portMapper = portMap.get(portInt);
141 if (portMapper == null) {
142 portMapper = new PortMapper(portInt);
143 portMap.put(portInt, portMapper);
144 }
145 portMapper.addRequestHandler(host, path, requestHandler);
146 LOGGER.info("Registered " + port + "/" +
147 (host == null ? "*" : host) + "/" +
148 (path == null ? "*" : path) + " --> " +
149 requestHandler);
150 }
151
152 public RequestHandlerContext mapRequest(HttpServletRequest request) {
153 RequestHandlerContext handlerContext = null;
154
155 int port = request.getLocalPort();
156 Integer portInt = Integer.valueOf(port);
157 PortMapper portMapper = portMap.get(portInt);
158 if (portMapper != null) {
159 handlerContext = portMapper.getRequestHandlerContext(request);
160 } else {
161 LOGGER.warning("No PortMapper for port " + port);
162 }
163 return handlerContext;
164 }
165
166
167
168
169
170
171
172
173
174
175 public boolean handleRequest(HttpServletRequest request,
176 HttpServletResponse response) throws IOException, ServletException {
177 boolean handled = false;
178
179
180 if (request.getAttribute(UIResults.FERRET_NAME) != null) {
181 return false;
182 }
183
184 if (globalPreRequestHandler != null) {
185 handled = globalPreRequestHandler.handleRequest(request, response);
186 }
187 if (handled == false) {
188 RequestHandlerContext handlerContext = mapRequest(request);
189 if (handlerContext != null) {
190 RequestHandler requestHandler =
191 handlerContext.getRequestHandler();
192
193 String pathPrefix = handlerContext.getPathPrefix();
194 if (!pathPrefix.equals("/")) {
195 pathPrefix += "/";
196 }
197 request.setAttribute(REQUEST_CONTEXT_PREFIX,pathPrefix);
198 handled = requestHandler.handleRequest(request, response);
199 }
200 }
201 if (handled == false) {
202 if(globalPostRequestHandler != null) {
203 handled = globalPostRequestHandler.handleRequest(request,
204 response);
205 }
206 }
207
208 return handled;
209 }
210
211
212
213
214
215 public void shutdown() {
216 for (ShutdownListener shutdownListener : shutdownListeners) {
217 try {
218 shutdownListener.shutdown();
219 } catch(Exception e) {
220 LOGGER.severe("failed shutdown"+e.getMessage());
221 }
222 }
223 }
224
225
226
227
228
229
230
231
232
233 public static String getRequestPathPrefix(HttpServletRequest request) {
234 return (String) request.getAttribute(REQUEST_CONTEXT_PREFIX);
235 }
236
237
238
239
240
241
242
243 public static String getRequestContextPath(HttpServletRequest request) {
244 String prefix = (String) request.getAttribute(REQUEST_CONTEXT_PREFIX);
245 String requestUrl = request.getRequestURI();
246 if (prefix == null) {
247 return requestUrl;
248 }
249 if (requestUrl.startsWith(prefix)) {
250 return requestUrl.substring(prefix.length());
251 }
252 return requestUrl;
253 }
254
255
256
257
258
259
260
261 public static String getRequestContextPathQuery(HttpServletRequest request) {
262 String prefix = (String)request.getAttribute(REQUEST_CONTEXT_PREFIX);
263
264
265 StringBuilder sb = new StringBuilder(request.getRequestURI());
266 String requestUrl = null;
267 String query = request.getQueryString();
268 if (query != null) {
269 requestUrl = sb.append("?").append(query).toString();
270 } else {
271 requestUrl = sb.toString();
272 }
273 if (prefix == null) {
274 return requestUrl;
275 }
276 if (requestUrl.startsWith(prefix)) {
277 return requestUrl.substring(prefix.length());
278 }
279
280 else if (prefix.endsWith("/") && (requestUrl + "/").equals(prefix)) {
281 return "";
282 }
283 return requestUrl;
284 }
285 }