001
014
015 package com.liferay.taglib.ui;
016
017 import com.liferay.portal.kernel.language.LanguageUtil;
018 import com.liferay.portal.kernel.log.Log;
019 import com.liferay.portal.kernel.log.LogFactoryUtil;
020 import com.liferay.portal.kernel.servlet.taglib.ui.BreadcrumbEntry;
021 import com.liferay.portal.kernel.util.CookieKeys;
022 import com.liferay.portal.kernel.util.GetterUtil;
023 import com.liferay.portal.kernel.util.HtmlUtil;
024 import com.liferay.portal.kernel.util.HttpUtil;
025 import com.liferay.portal.kernel.util.PropsKeys;
026 import com.liferay.portal.kernel.util.PropsUtil;
027 import com.liferay.portal.kernel.util.StringBundler;
028 import com.liferay.portal.kernel.util.StringPool;
029 import com.liferay.portal.kernel.util.StringUtil;
030 import com.liferay.portal.kernel.util.UnicodeProperties;
031 import com.liferay.portal.kernel.util.Validator;
032 import com.liferay.portal.kernel.util.WebKeys;
033 import com.liferay.portal.model.Account;
034 import com.liferay.portal.model.Group;
035 import com.liferay.portal.model.GroupConstants;
036 import com.liferay.portal.model.Layout;
037 import com.liferay.portal.model.LayoutConstants;
038 import com.liferay.portal.model.LayoutSet;
039 import com.liferay.portal.model.Organization;
040 import com.liferay.portal.model.User;
041 import com.liferay.portal.service.GroupLocalServiceUtil;
042 import com.liferay.portal.service.LayoutLocalServiceUtil;
043 import com.liferay.portal.service.LayoutSetLocalServiceUtil;
044 import com.liferay.portal.service.OrganizationLocalServiceUtil;
045 import com.liferay.portal.service.UserLocalServiceUtil;
046 import com.liferay.portal.theme.PortletDisplay;
047 import com.liferay.portal.theme.ThemeDisplay;
048 import com.liferay.portal.util.PortalUtil;
049 import com.liferay.taglib.aui.AUIUtil;
050 import com.liferay.taglib.util.IncludeTag;
051
052 import java.util.List;
053 import java.util.Map;
054
055 import javax.portlet.PortletURL;
056
057 import javax.servlet.http.HttpServletRequest;
058 import javax.servlet.http.HttpSession;
059
060
063 public class BreadcrumbTag extends IncludeTag {
064
065 public void setPortletURL(PortletURL portletURL) {
066 _portletURL = portletURL;
067 }
068
069 public void setSelLayout(Layout selLayout) {
070 _selLayout = selLayout;
071 }
072
073 public void setSelLayoutParam(String selLayoutParam) {
074 _selLayoutParam = selLayoutParam;
075 }
076
077 public void setShowCurrentGroup(boolean showCurrentGroup) {
078 _showCurrentGroup = showCurrentGroup;
079 }
080
081 public void setShowCurrentPortlet(boolean showCurrentPortlet) {
082 _showCurrentPortlet = showCurrentPortlet;
083 }
084
085 public void setShowGuestGroup(boolean showGuestGroup) {
086 _showGuestGroup = showGuestGroup;
087 }
088
089 public void setShowLayout(boolean showLayout) {
090 _showLayout = showLayout;
091 }
092
093 public void setShowParentGroups(boolean showParentGroups) {
094 _showParentGroups = showParentGroups;
095 }
096
097 public void setShowPortletBreadcrumb(boolean showPortletBreadcrumb) {
098 _showPortletBreadcrumb = showPortletBreadcrumb;
099 }
100
101 protected void buildGuestGroupBreadcrumb(
102 ThemeDisplay themeDisplay, StringBundler sb)
103 throws Exception {
104
105 Group group = GroupLocalServiceUtil.getGroup(
106 themeDisplay.getCompanyId(), GroupConstants.GUEST);
107
108 if (group.getPublicLayoutsPageCount() == 0) {
109 return;
110 }
111
112 sb.append("<li><a href=\"");
113
114 LayoutSet layoutSet = LayoutSetLocalServiceUtil.getLayoutSet(
115 group.getGroupId(), false);
116
117 String layoutSetFriendlyURL = PortalUtil.getLayoutSetFriendlyURL(
118 layoutSet, themeDisplay);
119
120 if (themeDisplay.isAddSessionIdToURL()) {
121 layoutSetFriendlyURL = PortalUtil.getURLWithSessionId(
122 layoutSetFriendlyURL, themeDisplay.getSessionId());
123 }
124
125 sb.append(layoutSetFriendlyURL);
126
127 sb.append("\">");
128
129 Account account = themeDisplay.getAccount();
130
131 sb.append(HtmlUtil.escape(account.getName()));
132
133 sb.append("</a><span class=\"divider\">/</span></li>");
134 }
135
136 protected void buildLayoutBreadcrumb(
137 Layout selLayout, String selLayoutParam, boolean selectedLayout,
138 PortletURL portletURL, ThemeDisplay themeDisplay, StringBundler sb)
139 throws Exception {
140
141 if (selLayout.getParentLayoutId() !=
142 LayoutConstants.DEFAULT_PARENT_LAYOUT_ID) {
143
144 Layout parentLayout = LayoutLocalServiceUtil.getParentLayout(
145 selLayout);
146
147 buildLayoutBreadcrumb(
148 parentLayout, selLayoutParam, false, portletURL, themeDisplay,
149 sb);
150 }
151
152 sb.append("<li><a href=\"");
153
154 String layoutURL = getBreadcrumbLayoutURL(
155 selLayout, selLayoutParam, portletURL, themeDisplay);
156
157 if (themeDisplay.isAddSessionIdToURL()) {
158 layoutURL = PortalUtil.getURLWithSessionId(
159 layoutURL, themeDisplay.getSessionId());
160 }
161
162 if (selLayout.isTypeControlPanel()) {
163 layoutURL = HttpUtil.removeParameter(
164 layoutURL, "controlPanelCategory");
165 }
166
167 sb.append(layoutURL);
168
169 sb.append("\" ");
170
171 String layoutName = selLayout.getName(themeDisplay.getLocale());
172
173 if (selLayout.isTypeControlPanel()) {
174 sb.append("target=\"_top\"");
175
176 if (layoutName.equals(LayoutConstants.NAME_CONTROL_PANEL_DEFAULT)) {
177 layoutName = LanguageUtil.get(
178 themeDisplay.getLocale(), "control-panel");
179 }
180 }
181 else {
182 String target = PortalUtil.getLayoutTarget(selLayout);
183
184 sb.append(target);
185 }
186
187 sb.append(StringPool.GREATER_THAN);
188 sb.append(HtmlUtil.escape(layoutName));
189 sb.append("</a><span class=\"divider\">/</span></li>");
190 }
191
192 protected void buildParentGroupsBreadcrumb(
193 LayoutSet layoutSet, PortletURL portletURL,
194 ThemeDisplay themeDisplay, StringBundler sb)
195 throws Exception {
196
197 Group group = layoutSet.getGroup();
198
199 if (group.isControlPanel()) {
200 return;
201 }
202
203 if (group.isSite()) {
204 Group parentSite = group.getParentGroup();
205
206 if (parentSite != null) {
207 LayoutSet parentLayoutSet =
208 LayoutSetLocalServiceUtil.getLayoutSet(
209 parentSite.getGroupId(), layoutSet.isPrivateLayout());
210
211 buildParentGroupsBreadcrumb(
212 parentLayoutSet, portletURL, themeDisplay, sb);
213 }
214 }
215 else if (group.isUser()) {
216 User groupUser = UserLocalServiceUtil.getUser(group.getClassPK());
217
218 List<Organization> organizations =
219 OrganizationLocalServiceUtil.getUserOrganizations(
220 groupUser.getUserId());
221
222 if (!organizations.isEmpty()) {
223 Organization organization = organizations.get(0);
224
225 Group parentGroup = organization.getGroup();
226
227 LayoutSet parentLayoutSet =
228 LayoutSetLocalServiceUtil.getLayoutSet(
229 parentGroup.getGroupId(), layoutSet.isPrivateLayout());
230
231 buildParentGroupsBreadcrumb(
232 parentLayoutSet, portletURL, themeDisplay, sb);
233 }
234 }
235
236 int layoutsPageCount = 0;
237
238 if (layoutSet.isPrivateLayout()) {
239 layoutsPageCount = group.getPrivateLayoutsPageCount();
240 }
241 else {
242 layoutsPageCount = group.getPublicLayoutsPageCount();
243 }
244
245 if ((layoutsPageCount > 0) && !group.isGuest()) {
246 String layoutSetFriendlyURL = PortalUtil.getLayoutSetFriendlyURL(
247 layoutSet, themeDisplay);
248
249 if (themeDisplay.isAddSessionIdToURL()) {
250 layoutSetFriendlyURL = PortalUtil.getURLWithSessionId(
251 layoutSetFriendlyURL, themeDisplay.getSessionId());
252 }
253
254 sb.append("<li><a href=\"");
255 sb.append(layoutSetFriendlyURL);
256 sb.append("\">");
257 sb.append(HtmlUtil.escape(group.getDescriptiveName()));
258 sb.append("</a><span class=\"divider\">/</span></li>");
259 }
260 }
261
262 protected void buildPortletBreadcrumb(
263 HttpServletRequest request, boolean showCurrentGroup,
264 boolean showCurrentPortlet, ThemeDisplay themeDisplay,
265 StringBundler sb)
266 throws Exception {
267
268 List<BreadcrumbEntry> breadcrumbEntries =
269 PortalUtil.getPortletBreadcrumbs(request);
270
271 if (breadcrumbEntries == null) {
272 return;
273 }
274
275 for (int i = 0; i < breadcrumbEntries.size(); i++) {
276 BreadcrumbEntry breadcrumbEntry = breadcrumbEntries.get(i);
277
278 Map<String, Object> data = breadcrumbEntry.getData();
279
280 String breadcrumbTitle = breadcrumbEntry.getTitle();
281 String breadcrumbURL = breadcrumbEntry.getURL();
282
283 if (!showCurrentGroup) {
284 String siteGroupName = themeDisplay.getSiteGroupName();
285
286 if (siteGroupName.equals(breadcrumbTitle)) {
287 continue;
288 }
289 }
290
291 if (!showCurrentPortlet) {
292 PortletDisplay portletDisplay =
293 themeDisplay.getPortletDisplay();
294
295 String portletTitle = PortalUtil.getPortletTitle(
296 portletDisplay.getId(), themeDisplay.getUser());
297
298 if (portletTitle.equals(breadcrumbTitle)) {
299 continue;
300 }
301 }
302
303 if (!CookieKeys.hasSessionId(request) &&
304 Validator.isNotNull(breadcrumbURL)) {
305
306 HttpSession session = request.getSession();
307
308 breadcrumbURL = PortalUtil.getURLWithSessionId(
309 breadcrumbURL, session.getId());
310 }
311
312 sb.append("<li>");
313
314 if (i < (breadcrumbEntries.size() - 1)) {
315 if (Validator.isNotNull(breadcrumbURL)) {
316 sb.append("<a href=\"");
317 sb.append(HtmlUtil.escape(breadcrumbURL));
318 sb.append("\"");
319 sb.append(AUIUtil.buildData(data));
320 sb.append(">");
321 }
322
323 sb.append(HtmlUtil.escape(breadcrumbTitle));
324
325 if (Validator.isNotNull(breadcrumbURL)) {
326 sb.append("</a>");
327 }
328
329 sb.append("<span class=\"divider\">/</span>");
330 }
331 else {
332 sb.append(HtmlUtil.escape(breadcrumbTitle));
333 }
334
335 sb.append("</li>");
336 }
337 }
338
339 @Override
340 protected void cleanUp() {
341 _portletURL = null;
342 _selLayout = null;
343 _selLayoutParam = null;
344 _showCurrentGroup = true;
345 _showCurrentPortlet = true;
346 _showGuestGroup = _SHOW_GUEST_GROUP;
347 _showLayout = true;
348 _showParentGroups = null;
349 _showPortletBreadcrumb = true;
350 }
351
352 protected String getBreadcrumbLayoutURL(
353 Layout selLayout, String selLayoutParam, PortletURL portletURL,
354 ThemeDisplay themeDisplay)
355 throws Exception {
356
357 if (portletURL == null) {
358 return PortalUtil.getLayoutFullURL(selLayout, themeDisplay);
359 }
360
361 portletURL.setParameter(
362 selLayoutParam, String.valueOf(selLayout.getPlid()));
363
364 if (selLayout.isTypeControlPanel()) {
365 if (themeDisplay.getDoAsGroupId() > 0) {
366 portletURL.setParameter(
367 "doAsGroupId",
368 String.valueOf(themeDisplay.getDoAsGroupId()));
369 }
370
371 if (themeDisplay.getRefererPlid() != LayoutConstants.DEFAULT_PLID) {
372 portletURL.setParameter(
373 "refererPlid",
374 String.valueOf(themeDisplay.getRefererPlid()));
375 }
376 }
377
378 return portletURL.toString();
379 }
380
381 protected String getBreadcrumbString(HttpServletRequest request) {
382 ThemeDisplay themeDisplay = (ThemeDisplay)request.getAttribute(
383 WebKeys.THEME_DISPLAY);
384
385 StringBundler sb = new StringBundler();
386
387 try {
388 if (Validator.isNull(_selLayout)) {
389 setSelLayout(themeDisplay.getLayout());
390 }
391
392 Group group = _selLayout.getGroup();
393
394 if (_showGuestGroup) {
395 buildGuestGroupBreadcrumb(themeDisplay, sb);
396 }
397
398 if (_showParentGroups) {
399 buildParentGroupsBreadcrumb(
400 _selLayout.getLayoutSet(), _portletURL, themeDisplay, sb);
401 }
402
403 if (_showLayout && !group.isLayoutPrototype()) {
404 buildLayoutBreadcrumb(
405 _selLayout, _selLayoutParam, true, _portletURL,
406 themeDisplay, sb);
407 }
408
409 if (_showPortletBreadcrumb) {
410 buildPortletBreadcrumb(
411 request, _showCurrentGroup, _showCurrentPortlet,
412 themeDisplay, sb);
413 }
414 }
415 catch (Exception e) {
416 _log.error(e, e);
417 }
418
419 String breadcrumbString = sb.toString();
420
421 if (Validator.isNull(breadcrumbString)) {
422 return StringPool.BLANK;
423 }
424
425 String breadcrumbTruncateClass = StringPool.BLANK;
426
427 String[] breadcrumbArray = breadcrumbString.split("<li", -1);
428
429 boolean breadcrumbTruncate = false;
430
431 if (breadcrumbArray.length > 3) {
432 breadcrumbTruncate = true;
433 }
434
435 if (breadcrumbTruncate) {
436 breadcrumbTruncateClass = " breadcrumb-truncate";
437 }
438
439 int x = breadcrumbString.indexOf("<li") + 3;
440 int y = breadcrumbString.lastIndexOf("<li") + 3;
441
442 if (x == y) {
443 breadcrumbString = StringUtil.insert(
444 breadcrumbString,
445 " class=\"active only" + breadcrumbTruncateClass + "\"", x);
446 }
447 else {
448 breadcrumbString = StringUtil.insert(
449 breadcrumbString,
450 " class=\"active last" + breadcrumbTruncateClass + "\"", y);
451
452 breadcrumbString = StringUtil.insert(
453 breadcrumbString,
454 " class=\"first" + breadcrumbTruncateClass + "\"", x);
455 }
456
457 if (breadcrumbTruncate) {
458 y = breadcrumbString.lastIndexOf("<li");
459
460 int z = breadcrumbString.lastIndexOf("<li", y - 1) + 3;
461
462 breadcrumbString = StringUtil.insert(
463 breadcrumbString,
464 " class=\"current-parent" + breadcrumbTruncateClass + "\"", z);
465 }
466
467 return breadcrumbString;
468 }
469
470 @Override
471 protected String getPage() {
472 return _PAGE;
473 }
474
475 protected void initShowParentGroups(HttpServletRequest request) {
476 if (_showParentGroups != null) {
477 return;
478 }
479
480 ThemeDisplay themeDisplay = (ThemeDisplay)request.getAttribute(
481 WebKeys.THEME_DISPLAY);
482
483 try {
484 if (Validator.isNull(_selLayout)) {
485 setSelLayout(themeDisplay.getLayout());
486 }
487
488 Group group = _selLayout.getGroup();
489
490 UnicodeProperties typeSettingsProperties =
491 group.getTypeSettingsProperties();
492
493 _showParentGroups = GetterUtil.getBoolean(
494 typeSettingsProperties.getProperty(
495 "breadcrumbShowParentGroups"),
496 _SHOW_PARENT_GROUPS);
497 }
498 catch (Exception e) {
499 _log.error(e, e);
500 }
501 }
502
503 @Override
504 protected void setAttributes(HttpServletRequest request) {
505 initShowParentGroups(request);
506
507 request.setAttribute(
508 "liferay-ui:breadcrumb:breadcrumbString",
509 getBreadcrumbString(request));
510 request.setAttribute("liferay-ui:breadcrumb:portletURL", _portletURL);
511 request.setAttribute("liferay-ui:breadcrumb:selLayout", _selLayout);
512 request.setAttribute(
513 "liferay-ui:breadcrumb:selLayoutParam", _selLayoutParam);
514 request.setAttribute(
515 "liferay-ui:breadcrumb:showCurrentGroup",
516 String.valueOf(_showCurrentGroup));
517 request.setAttribute(
518 "liferay-ui:breadcrumb:showCurrentPortlet",
519 String.valueOf(_showCurrentPortlet));
520 request.setAttribute(
521 "liferay-ui:breadcrumb:showGuestGroup",
522 String.valueOf(_showGuestGroup));
523 request.setAttribute(
524 "liferay-ui:breadcrumb:showLayout", String.valueOf(_showLayout));
525 request.setAttribute(
526 "liferay-ui:breadcrumb:showParentGroups",
527 String.valueOf(_showParentGroups));
528 request.setAttribute(
529 "liferay-ui:breadcrumb:showPortletBreadcrumb",
530 String.valueOf(_showPortletBreadcrumb));
531 }
532
533 private static final String _PAGE = "/html/taglib/ui/breadcrumb/page.jsp";
534
535 private static final boolean _SHOW_GUEST_GROUP = GetterUtil.getBoolean(
536 PropsUtil.get(PropsKeys.BREADCRUMB_SHOW_GUEST_GROUP));
537
538 private static final boolean _SHOW_PARENT_GROUPS = GetterUtil.getBoolean(
539 PropsUtil.get(PropsKeys.BREADCRUMB_SHOW_PARENT_GROUPS));
540
541 private static Log _log = LogFactoryUtil.getLog(BreadcrumbTag.class);
542
543 private PortletURL _portletURL;
544 private Layout _selLayout;
545 private String _selLayoutParam;
546 private boolean _showCurrentGroup = true;
547 private boolean _showCurrentPortlet = true;
548 private boolean _showGuestGroup = _SHOW_GUEST_GROUP;
549 private boolean _showLayout = true;
550 private Boolean _showParentGroups = null;
551 private boolean _showPortletBreadcrumb = true;
552
553 }