001
014
015 package com.liferay.portlet;
016
017 import com.liferay.portal.kernel.exception.PortalException;
018 import com.liferay.portal.kernel.exception.SystemException;
019 import com.liferay.portal.kernel.io.unsync.UnsyncStringWriter;
020 import com.liferay.portal.kernel.log.Log;
021 import com.liferay.portal.kernel.log.LogFactoryUtil;
022 import com.liferay.portal.kernel.portlet.LiferayPortletResponse;
023 import com.liferay.portal.kernel.portlet.LiferayPortletURL;
024 import com.liferay.portal.kernel.servlet.URLEncoder;
025 import com.liferay.portal.kernel.util.ArrayUtil;
026 import com.liferay.portal.kernel.util.GetterUtil;
027 import com.liferay.portal.kernel.util.ParamUtil;
028 import com.liferay.portal.kernel.util.Validator;
029 import com.liferay.portal.model.Layout;
030 import com.liferay.portal.model.LayoutConstants;
031 import com.liferay.portal.model.Portlet;
032 import com.liferay.portal.model.PortletApp;
033 import com.liferay.portal.model.PortletURLListener;
034 import com.liferay.portal.service.LayoutLocalServiceUtil;
035 import com.liferay.portal.service.PortletLocalServiceUtil;
036 import com.liferay.portal.util.PortalUtil;
037 import com.liferay.portal.util.WebKeys;
038
039 import java.io.Writer;
040
041 import java.lang.reflect.Constructor;
042 import java.lang.reflect.Method;
043
044 import java.util.ArrayList;
045 import java.util.LinkedHashMap;
046 import java.util.List;
047 import java.util.Map;
048 import java.util.Set;
049
050 import javax.portlet.MimeResponse;
051 import javax.portlet.PortletException;
052 import javax.portlet.PortletModeException;
053 import javax.portlet.PortletPreferences;
054 import javax.portlet.PortletRequest;
055 import javax.portlet.PortletResponse;
056 import javax.portlet.PortletURL;
057 import javax.portlet.PortletURLGenerationListener;
058 import javax.portlet.ResourceURL;
059 import javax.portlet.WindowStateException;
060
061 import javax.servlet.http.Cookie;
062 import javax.servlet.http.HttpServletRequest;
063 import javax.servlet.http.HttpServletResponse;
064
065 import javax.xml.parsers.DocumentBuilder;
066 import javax.xml.parsers.DocumentBuilderFactory;
067 import javax.xml.parsers.ParserConfigurationException;
068 import javax.xml.transform.OutputKeys;
069 import javax.xml.transform.Transformer;
070 import javax.xml.transform.TransformerFactory;
071 import javax.xml.transform.dom.DOMSource;
072 import javax.xml.transform.stream.StreamResult;
073
074 import org.w3c.dom.DOMException;
075 import org.w3c.dom.Document;
076 import org.w3c.dom.Element;
077
078
081 public abstract class PortletResponseImpl implements LiferayPortletResponse {
082
083 public static PortletResponseImpl getPortletResponseImpl(
084 PortletResponse portletResponse) {
085
086 PortletResponseImpl portletResponseImpl = null;
087
088 if (portletResponse instanceof PortletResponseImpl) {
089 portletResponseImpl = (PortletResponseImpl)portletResponse;
090 }
091 else {
092
093
094
095 try {
096 Method method = portletResponse.getClass().getMethod(
097 "getResponse");
098
099 Object obj = method.invoke(portletResponse, (Object[])null);
100
101 portletResponseImpl = getPortletResponseImpl(
102 (PortletResponse)obj);
103 }
104 catch (Exception e) {
105 throw new RuntimeException(
106 "Unable to get the portlet response from " +
107 portletResponse.getClass().getName());
108 }
109 }
110
111 return portletResponseImpl;
112 }
113
114 public void addDateHeader(String name, long date) {
115 if (Validator.isNull(name)) {
116 throw new IllegalArgumentException();
117 }
118
119 Long[] values = (Long[])_headers.get(name);
120
121 if (values == null) {
122 setDateHeader(name, date);
123 }
124 else {
125 values = ArrayUtil.append(values, new Long(date));
126
127 _headers.put(name, values);
128 }
129 }
130
131 public void addHeader(String name, String value) {
132 if (Validator.isNull(name)) {
133 throw new IllegalArgumentException();
134 }
135
136 String[] values = (String[])_headers.get(name);
137
138 if (values == null) {
139 setHeader(name, value);
140 }
141 else {
142 values = ArrayUtil.append(values, value);
143
144 _headers.put(name, values);
145 }
146 }
147
148 public void addIntHeader(String name, int value) {
149 if (Validator.isNull(name)) {
150 throw new IllegalArgumentException();
151 }
152
153 Integer[] values = (Integer[])_headers.get(name);
154
155 if (values == null) {
156 setIntHeader(name, value);
157 }
158 else {
159 values = ArrayUtil.append(values, new Integer(value));
160
161 _headers.put(name, values);
162 }
163 }
164
165 public void addProperty(Cookie cookie) {
166 if (cookie == null) {
167 throw new IllegalArgumentException();
168 }
169
170 Cookie[] cookies = (Cookie[])_headers.get("cookies");
171
172 if (cookies == null) {
173 _headers.put("cookies", new Cookie[] {cookie});
174 }
175 else {
176 cookies = ArrayUtil.append(cookies, cookie);
177
178 _headers.put("cookies", cookies);
179 }
180 }
181
182 public void addProperty(String key, Element element) {
183 if (key == null) {
184 throw new IllegalArgumentException();
185 }
186
187 if (key.equalsIgnoreCase(MimeResponse.MARKUP_HEAD_ELEMENT)) {
188 List<Element> values = _markupHeadElements.get(key);
189
190 if (values != null) {
191 if (element != null) {
192 values.add(element);
193 }
194 else {
195 _markupHeadElements.remove(key);
196 }
197 }
198 else {
199 if (element != null) {
200 values = new ArrayList<Element>();
201
202 values.add(element);
203
204 _markupHeadElements.put(key, values);
205 }
206 }
207 }
208 }
209
210 public void addProperty(String key, String value) {
211 if (Validator.isNull(key)) {
212 throw new IllegalArgumentException();
213 }
214
215 addHeader(key, value);
216 }
217
218 public PortletURL createActionURL() {
219 return createActionURL(_portletName);
220 }
221
222 public LiferayPortletURL createActionURL(String portletName) {
223 return createLiferayPortletURL(
224 portletName, PortletRequest.ACTION_PHASE);
225 }
226
227 public Element createElement(String tagName) throws DOMException {
228 if (_document == null) {
229 try {
230 DocumentBuilderFactory documentBuilderFactory =
231 DocumentBuilderFactory.newInstance();
232
233 DocumentBuilder documentBuilder =
234 documentBuilderFactory.newDocumentBuilder();
235
236 _document = documentBuilder.newDocument();
237 }
238 catch (ParserConfigurationException pce) {
239 throw new DOMException(
240 DOMException.INVALID_STATE_ERR, pce.getMessage());
241 }
242 }
243
244 return _document.createElement(tagName);
245 }
246
247 public LiferayPortletURL createLiferayPortletURL(
248 long plid, String portletName, String lifecycle) {
249
250 try {
251 Layout layout = (Layout)_portletRequestImpl.getAttribute(
252 WebKeys.LAYOUT);
253
254 PortletPreferences portletSetup =
255 PortletPreferencesFactoryUtil.getLayoutPortletSetup(
256 layout, _portletName);
257
258 String linkToLayoutUuid = GetterUtil.getString(
259 portletSetup.getValue(
260 "portlet-setup-link-to-layout-uuid", null));
261
262 if (Validator.isNotNull(linkToLayoutUuid)) {
263 try {
264 Layout linkedLayout =
265 LayoutLocalServiceUtil.getLayoutByUuidAndGroupId(
266 linkToLayoutUuid, layout.getGroupId());
267
268 plid = linkedLayout.getPlid();
269 }
270 catch (PortalException pe) {
271 }
272 }
273 }
274 catch (SystemException e) {
275 if (_log.isWarnEnabled()) {
276 _log.warn(e);
277 }
278 }
279
280 if (plid == LayoutConstants.DEFAULT_PLID) {
281 plid = _plid;
282 }
283
284 PortletURLImpl portletURLImpl = null;
285
286 Portlet portlet = getPortlet();
287
288 String portletURLClass = portlet.getPortletURLClass();
289
290 if (portlet.getPortletId().equals(portletName) &&
291 Validator.isNotNull(portletURLClass)) {
292
293 try {
294 Class<?> portletURLClassObj = Class.forName(portletURLClass);
295
296 Constructor<?> constructor = portletURLClassObj.getConstructor(
297 new Class[] {
298 com.liferay.portlet.PortletResponseImpl.class,
299 long.class, String.class
300 });
301
302 portletURLImpl = (PortletURLImpl)constructor.newInstance(
303 new Object[] {this, plid, lifecycle});
304 }
305 catch (Exception e) {
306 _log.error(e);
307 }
308 }
309
310 if (portletURLImpl == null) {
311 portletURLImpl = new PortletURLImpl(
312 _portletRequestImpl, portletName, plid, lifecycle);
313 }
314
315 PortletApp portletApp = portlet.getPortletApp();
316
317 Set<PortletURLListener> portletURLListeners =
318 portletApp.getPortletURLListeners();
319
320 for (PortletURLListener portletURLListener : portletURLListeners) {
321 try {
322 PortletURLGenerationListener portletURLGenerationListener =
323 PortletURLListenerFactory.create(portletURLListener);
324
325 if (lifecycle.equals(PortletRequest.ACTION_PHASE)) {
326 portletURLGenerationListener.filterActionURL(
327 portletURLImpl);
328 }
329 else if (lifecycle.equals(PortletRequest.RENDER_PHASE)) {
330 portletURLGenerationListener.filterRenderURL(
331 portletURLImpl);
332 }
333 else if (lifecycle.equals(PortletRequest.RESOURCE_PHASE)) {
334 portletURLGenerationListener.filterResourceURL(
335 portletURLImpl);
336 }
337 }
338 catch (PortletException pe) {
339 _log.error(pe, pe);
340 }
341 }
342
343 try {
344 portletURLImpl.setWindowState(_portletRequestImpl.getWindowState());
345 }
346 catch (WindowStateException wse) {
347 _log.error(wse.getMessage());
348 }
349
350 try {
351 portletURLImpl.setPortletMode(_portletRequestImpl.getPortletMode());
352 }
353 catch (PortletModeException pme) {
354 _log.error(pme.getMessage());
355 }
356
357 if (lifecycle.equals(PortletRequest.ACTION_PHASE)) {
358 portletURLImpl.setCopyCurrentPublicRenderParameters(true);
359 }
360
361 if (lifecycle.equals(PortletRequest.RESOURCE_PHASE)) {
362 portletURLImpl.setCopyCurrentPublicRenderParameters(true);
363 portletURLImpl.setCopyCurrentRenderParameters(true);
364 }
365
366 return portletURLImpl;
367 }
368
369 public LiferayPortletURL createLiferayPortletURL(String lifecycle) {
370 return createLiferayPortletURL(_portletName, lifecycle);
371 }
372
373 public LiferayPortletURL createLiferayPortletURL(
374 String portletName, String lifecycle) {
375
376 return createLiferayPortletURL(_plid, portletName, lifecycle);
377 }
378
379 public PortletURL createRenderURL() {
380 return createRenderURL(_portletName);
381 }
382
383 public LiferayPortletURL createRenderURL(String portletName) {
384 return createLiferayPortletURL(
385 portletName, PortletRequest.RENDER_PHASE);
386 }
387
388 public ResourceURL createResourceURL() {
389 return createResourceURL(_portletName);
390 }
391
392 public LiferayPortletURL createResourceURL(String portletName) {
393 return createLiferayPortletURL(
394 portletName, PortletRequest.RESOURCE_PHASE);
395 }
396
397 public String encodeURL(String path) {
398 if ((path == null) ||
399 (!path.startsWith("#") && !path.startsWith("/") &&
400 (path.indexOf(":
401
402
403
404 throw new IllegalArgumentException(
405 "URL path must start with a '/' or include ':
406 }
407
408 if (_urlEncoder != null) {
409 return _urlEncoder.encodeURL(_response, path);
410 }
411 else {
412 return path;
413 }
414 }
415
416 public long getCompanyId() {
417 return _companyId;
418 }
419
420 public HttpServletRequest getHttpServletRequest() {
421 return _portletRequestImpl.getHttpServletRequest();
422 }
423
424 public HttpServletResponse getHttpServletResponse() {
425 return _response;
426 }
427
428 public abstract String getLifecycle();
429
430 public String getNamespace() {
431 if (_wsrp) {
432 return "wsrp_rewrite_";
433 }
434
435 if (_namespace == null) {
436 _namespace = PortalUtil.getPortletNamespace(_portletName);
437 }
438
439 return _namespace;
440 }
441
442 public long getPlid() {
443 return _plid;
444 }
445
446 public Portlet getPortlet() {
447 if (_portlet == null) {
448 try {
449 _portlet = PortletLocalServiceUtil.getPortletById(
450 _companyId, _portletName);
451 }
452 catch (Exception e) {
453 _log.error(e);
454 }
455 }
456
457 return _portlet;
458 }
459
460 public String getPortletName() {
461 return _portletName;
462 }
463
464 public PortletRequestImpl getPortletRequest() {
465 return _portletRequestImpl;
466 }
467
468 public Map<String, String[]> getProperties() {
469 Map<String, String[]> properties =
470 new LinkedHashMap<String, String[]>();
471
472 for (Map.Entry<String, Object> entry : _headers.entrySet()) {
473 String name = entry.getKey();
474 Object[] values = (Object[])entry.getValue();
475
476 String[] valuesString = new String[values.length];
477
478 for (int i = 0; i < values.length; i++) {
479 valuesString[i] = values[i].toString();
480 }
481
482 properties.put(name, valuesString);
483 }
484
485 return properties;
486 }
487
488 public URLEncoder getUrlEncoder() {
489 return _urlEncoder;
490 }
491
492 public void setDateHeader(String name, long date) {
493 if (Validator.isNull(name)) {
494 throw new IllegalArgumentException();
495 }
496
497 if (date <= 0) {
498 _headers.remove(name);
499 }
500 else {
501 _headers.put(name, new Long[] {new Long(date)});
502 }
503 }
504
505 public void setHeader(String name, String value) {
506 if (Validator.isNull(name)) {
507 throw new IllegalArgumentException();
508 }
509
510 if (Validator.isNull(value)) {
511 _headers.remove(name);
512 }
513 else {
514 _headers.put(name, new String[] {value});
515 }
516 }
517
518 public void setIntHeader(String name, int value) {
519 if (Validator.isNull(name)) {
520 throw new IllegalArgumentException();
521 }
522
523 if (value <= 0) {
524 _headers.remove(name);
525 }
526 else {
527 _headers.put(name, new Integer[] {new Integer(value)});
528 }
529 }
530
531 public void setPlid(long plid) {
532 _plid = plid;
533
534 if (_plid <= 0) {
535 Layout layout = (Layout)_portletRequestImpl.getAttribute(
536 WebKeys.LAYOUT);
537
538 if (layout != null) {
539 _plid = layout.getPlid();
540 }
541 }
542 }
543
544 public void setProperty(String key, String value) {
545 if (key == null) {
546 throw new IllegalArgumentException();
547 }
548
549 setHeader(key, value);
550 }
551
552 public void setURLEncoder(URLEncoder urlEncoder) {
553 _urlEncoder = urlEncoder;
554 }
555
556 public void transferHeaders(HttpServletResponse response) {
557 for (Map.Entry<String, Object> entry : _headers.entrySet()) {
558 String name = entry.getKey();
559 Object values = entry.getValue();
560
561 if (values instanceof Integer[]) {
562 Integer[] intValues = (Integer[])values;
563
564 for (int value : intValues) {
565 if (response.containsHeader(name)) {
566 response.addIntHeader(name, value);
567 }
568 else {
569 response.setIntHeader(name, value);
570 }
571 }
572 }
573 else if (values instanceof Long[]) {
574 Long[] dateValues = (Long[])values;
575
576 for (long value : dateValues) {
577 if (response.containsHeader(name)) {
578 response.addDateHeader(name, value);
579 }
580 else {
581 response.setDateHeader(name, value);
582 }
583 }
584 }
585 else if (values instanceof String[]) {
586 String[] stringValues = (String[])values;
587
588 for (String value : stringValues) {
589 if (response.containsHeader(name)) {
590 response.addHeader(name, value);
591 }
592 else {
593 response.setHeader(name, value);
594 }
595 }
596 }
597 else if (values instanceof Cookie[]) {
598 Cookie[] cookies = (Cookie[])values;
599
600 for (Cookie cookie : cookies) {
601 response.addCookie(cookie);
602 }
603 }
604 }
605 }
606
607 public void transferMarkupHeadElements() {
608 List<Element> elements = _markupHeadElements.get(
609 MimeResponse.MARKUP_HEAD_ELEMENT);
610
611 if ((elements == null) || elements.isEmpty()) {
612 return;
613 }
614
615 HttpServletRequest request = getHttpServletRequest();
616
617 List<String> markupHeadElements = (List<String>)request.getAttribute(
618 MimeResponse.MARKUP_HEAD_ELEMENT);
619
620 if (markupHeadElements == null) {
621 markupHeadElements = new ArrayList<String>();
622
623 request.setAttribute(
624 MimeResponse.MARKUP_HEAD_ELEMENT, markupHeadElements);
625 }
626
627 for (Element element : elements) {
628 try {
629 Writer writer = new UnsyncStringWriter();
630
631 TransformerFactory transformerFactory =
632 TransformerFactory.newInstance();
633
634 Transformer transformer = transformerFactory.newTransformer();
635
636 transformer.setOutputProperty(
637 OutputKeys.OMIT_XML_DECLARATION, "yes");
638
639 transformer.transform(
640 new DOMSource(element), new StreamResult(writer));
641
642 markupHeadElements.add(writer.toString());
643 }
644 catch (Exception e) {
645 if (_log.isWarnEnabled()) {
646 _log.warn(e, e);
647 }
648 }
649 }
650 }
651
652 protected void init(
653 PortletRequestImpl portletRequestImpl, HttpServletResponse response,
654 String portletName, long companyId, long plid) {
655
656 _portletRequestImpl = portletRequestImpl;
657 _response = response;
658 _portletName = portletName;
659 _companyId = companyId;
660 _wsrp = ParamUtil.getBoolean(getHttpServletRequest(), "wsrp");
661
662 setPlid(plid);
663 }
664
665 private static Log _log = LogFactoryUtil.getLog(PortletResponseImpl.class);
666
667 private long _companyId;
668 private Document _document;
669 private Map<String, Object> _headers = new LinkedHashMap<String, Object>();
670 private Map<String, List<Element>> _markupHeadElements =
671 new LinkedHashMap<String, List<Element>>();
672 private String _namespace;
673 private long _plid;
674 private Portlet _portlet;
675 private String _portletName;
676 private PortletRequestImpl _portletRequestImpl;
677 private HttpServletResponse _response;
678 private URLEncoder _urlEncoder;
679 private boolean _wsrp;
680
681 }