1
22
23 package com.liferay.portlet;
24
25 import com.liferay.portal.kernel.log.Log;
26 import com.liferay.portal.kernel.log.LogFactoryUtil;
27 import com.liferay.portal.kernel.portlet.LiferayPortletURL;
28 import com.liferay.portal.kernel.servlet.URLEncoder;
29 import com.liferay.portal.kernel.util.ArrayUtil;
30 import com.liferay.portal.kernel.util.StringPool;
31 import com.liferay.portal.kernel.util.StringUtil;
32 import com.liferay.portal.model.Portlet;
33 import com.liferay.portal.model.PortletApp;
34 import com.liferay.portal.servlet.NamespaceServletRequest;
35 import com.liferay.portal.struts.StrutsURLEncoder;
36 import com.liferay.portal.theme.ThemeDisplay;
37 import com.liferay.portal.util.PortalUtil;
38 import com.liferay.portal.util.WebKeys;
39 import com.liferay.util.servlet.DynamicServletRequest;
40
41 import java.io.IOException;
42
43 import java.util.HashMap;
44 import java.util.Map;
45 import java.util.Set;
46
47 import javax.portlet.PortletException;
48 import javax.portlet.PortletRequest;
49 import javax.portlet.PortletRequestDispatcher;
50 import javax.portlet.PortletResponse;
51 import javax.portlet.RenderRequest;
52 import javax.portlet.RenderResponse;
53
54 import javax.servlet.RequestDispatcher;
55 import javax.servlet.ServletException;
56 import javax.servlet.http.HttpServletRequest;
57 import javax.servlet.http.HttpServletResponse;
58
59 import org.apache.struts.Globals;
60
61
69 public class PortletRequestDispatcherImpl implements PortletRequestDispatcher {
70
71 public PortletRequestDispatcherImpl(
72 RequestDispatcher requestDispatcher, boolean named,
73 PortletContextImpl portletContextImpl) {
74
75 this(requestDispatcher, named, portletContextImpl, null);
76 }
77
78 public PortletRequestDispatcherImpl(
79 RequestDispatcher requestDispatcher, boolean named,
80 PortletContextImpl portletContextImpl, String path) {
81
82 _requestDispatcher = requestDispatcher;
83 _named = named;
84 _portlet = portletContextImpl.getPortlet();
85 _portletContextImpl = portletContextImpl;
86 _path = path;
87 }
88
89 public void forward(
90 PortletRequest portletRequest, PortletResponse portletResponse)
91 throws IllegalStateException, IOException, PortletException {
92
93 HttpServletResponse response = PortalUtil.getHttpServletResponse(
94 portletResponse);
95
96 if (response.isCommitted()) {
97 throw new IllegalStateException("Response is already committed");
98 }
99
100 try {
101 dispatch(portletRequest, portletResponse, false, false);
102 }
103 catch (ServletException se) {
104 _log.error(se, se);
105
106 throw new PortletException(se);
107 }
108 }
109
110 public void include(
111 PortletRequest portletRequest, PortletResponse portletResponse)
112 throws IOException, PortletException {
113
114 try {
115 dispatch(portletRequest, portletResponse, false, true);
116 }
117 catch (ServletException se) {
118 _log.error(se, se);
119
120 throw new PortletException(se);
121 }
122 }
123
124 public void include(
125 PortletRequest portletRequest, PortletResponse portletResponse,
126 boolean strutsURLEncoder)
127 throws IOException, PortletException {
128
129 try {
130 dispatch(portletRequest, portletResponse, strutsURLEncoder, true);
131 }
132 catch (ServletException se) {
133 _log.error(se, se);
134
135 throw new PortletException(se);
136 }
137 }
138
139 public void include(
140 RenderRequest renderRequest, RenderResponse renderResponse)
141 throws IOException, PortletException {
142
143 try {
144 dispatch(renderRequest, renderResponse, false, true);
145 }
146 catch (ServletException se) {
147 _log.error(se, se);
148
149 throw new PortletException(se);
150 }
151 }
152
153 protected void dispatch(
154 PortletRequest portletRequest, PortletResponse portletResponse,
155 boolean strutsURLEncoder, boolean include)
156 throws IOException, ServletException {
157
158 if (!include) {
159 if (portletResponse instanceof MimeResponseImpl) {
160 MimeResponseImpl mimeResponseImpl =
161 (MimeResponseImpl)portletResponse;
162
163 if (mimeResponseImpl.isCalledFlushBuffer()) {
164 throw new IllegalStateException();
165 }
166 }
167 }
168
169 PortletRequestImpl portletRequestImpl =
170 (PortletRequestImpl)portletRequest;
171 PortletResponseImpl portletResponseImpl =
172 PortletResponseImpl.getPortletResponseImpl(portletResponse);
173
174 HttpServletRequest request = PortalUtil.getHttpServletRequest(
175 portletRequest);
176 HttpServletResponse response = PortalUtil.getHttpServletResponse(
177 portletResponse);
178
179 String pathInfo = null;
180 String queryString = null;
181 String requestURI = null;
182 String servletPath = null;
183
184 if (_path != null) {
185
192
193 String pathNoQueryString = _path;
194
195 int pos = _path.indexOf(StringPool.QUESTION);
196
197 if (pos != -1) {
198 pathNoQueryString = _path.substring(0, pos);
199 queryString = _path.substring(pos + 1, _path.length());
200
201 Map<String, String[]> queryParams =
202 new HashMap<String, String[]>();
203
204 String[] queryParamsArray = StringUtil.split(
205 queryString, StringPool.AMPERSAND);
206
207 for (int i = 0; i < queryParamsArray.length; i++) {
208 String[] nameValuePair = StringUtil.split(
209 queryParamsArray[i], StringPool.EQUAL);
210
211 String name = nameValuePair[0];
212 String value = StringPool.BLANK;
213
214 if (nameValuePair.length == 2) {
215 value = nameValuePair[1];
216 }
217
218 String[] values = queryParams.get(name);
219
220 if (values == null) {
221 queryParams.put(name, new String[] {value});
222 }
223 else {
224 String[] newValues = new String[values.length + 1];
225
226 System.arraycopy(
227 values, 0, newValues, 0, values.length);
228
229 newValues[newValues.length - 1] = value;
230
231 queryParams.put(name, newValues);
232 }
233 }
234
235 DynamicServletRequest dynamicRequest = null;
236
237 if (portletRequestImpl.isPrivateRequestAttributes()) {
238 String portletNamespace = PortalUtil.getPortletNamespace(
239 portletRequestImpl.getPortletName());
240
241 dynamicRequest = new NamespaceServletRequest(
242 request, portletNamespace, portletNamespace);
243 }
244 else {
245 dynamicRequest = new DynamicServletRequest(request);
246 }
247
248 for (Map.Entry<String, String[]> entry :
249 queryParams.entrySet()) {
250
251 String name = entry.getKey();
252 String[] values = entry.getValue();
253
254 String[] oldValues = dynamicRequest.getParameterValues(
255 name);
256
257 if (oldValues == null) {
258 dynamicRequest.setParameterValues(name, values);
259 }
260 else {
261 String[] newValues = ArrayUtil.append(
262 values, oldValues);
263
264 dynamicRequest.setParameterValues(name, newValues);
265 }
266 }
267
268 request = dynamicRequest;
269 }
270
271 Portlet portlet = portletRequestImpl.getPortlet();
272
273 PortletApp portletApp = portlet.getPortletApp();
274
275 Set<String> servletURLPatterns = portletApp.getServletURLPatterns();
276
277 for (String urlPattern : servletURLPatterns) {
278 if (urlPattern.endsWith("/*")) {
279 pos = urlPattern.indexOf("/*");
280
281 urlPattern = urlPattern.substring(0, pos);
282
283 if (pathNoQueryString.startsWith(urlPattern)) {
284 pathInfo = pathNoQueryString.substring(
285 urlPattern.length());
286 servletPath = urlPattern;
287
288 break;
289 }
290 }
291 }
292
293 if ((pathInfo == null) && (servletPath == null)) {
294 pathInfo = pathNoQueryString;
295 servletPath = pathNoQueryString;
296 }
297
298 requestURI = portletRequest.getContextPath() + pathNoQueryString;
299 }
300
301 PortletServletRequest portletServletRequest = new PortletServletRequest(
302 request, portletRequestImpl, pathInfo, queryString, requestURI,
303 servletPath, _named, include);
304
305 PortletServletResponse portletServletResponse =
306 new PortletServletResponse(response, portletResponseImpl, include);
307
308 URLEncoder urlEncoder = _portlet.getURLEncoderInstance();
309
310 if (urlEncoder != null) {
311 portletResponseImpl.setURLEncoder(urlEncoder);
312 }
313 else if (strutsURLEncoder) {
314 ThemeDisplay themeDisplay =
315 (ThemeDisplay)portletRequest.getAttribute(
316 WebKeys.THEME_DISPLAY);
317
318 URLEncoder strutsURLEncoderObj = new StrutsURLEncoder(
319 portletServletRequest.getContextPath(),
320 themeDisplay.getPathMain(),
321 (String)_portletContextImpl.getAttribute(
322 Globals.SERVLET_KEY),
323 (LiferayPortletURL)portletResponseImpl.createRenderURL());
324
325 portletResponseImpl.setURLEncoder(strutsURLEncoderObj);
326 }
327
328 if (include) {
329 _requestDispatcher.include(
330 portletServletRequest, portletServletResponse);
331 }
332 else {
333 _requestDispatcher.forward(
334 portletServletRequest, portletServletResponse);
335 }
336 }
337
338 private static Log _log =
339 LogFactoryUtil.getLog(PortletRequestDispatcherImpl.class);
340
341 private RequestDispatcher _requestDispatcher;
342 private boolean _named;
343 private Portlet _portlet;
344 private PortletContextImpl _portletContextImpl;
345 private String _path;
346
347 }