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