001    /**
002     * Copyright (c) 2000-present Liferay, Inc. All rights reserved.
003     *
004     * This library is free software; you can redistribute it and/or modify it under
005     * the terms of the GNU Lesser General Public License as published by the Free
006     * Software Foundation; either version 2.1 of the License, or (at your option)
007     * any later version.
008     *
009     * This library is distributed in the hope that it will be useful, but WITHOUT
010     * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
011     * FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
012     * details.
013     */
014    
015    package com.liferay.portal.kernel.templateparser;
016    
017    import com.liferay.portal.kernel.log.Log;
018    import com.liferay.portal.kernel.log.LogFactoryUtil;
019    import com.liferay.portal.kernel.util.CharPool;
020    import com.liferay.portal.kernel.util.GetterUtil;
021    import com.liferay.portal.kernel.util.StringBundler;
022    import com.liferay.portal.kernel.util.StringPool;
023    import com.liferay.portal.kernel.util.Validator;
024    import com.liferay.portal.model.Group;
025    import com.liferay.portal.model.Layout;
026    import com.liferay.portal.service.GroupLocalServiceUtil;
027    import com.liferay.portal.service.LayoutLocalServiceUtil;
028    import com.liferay.portal.theme.ThemeDisplay;
029    import com.liferay.portal.util.PortalUtil;
030    
031    import java.util.ArrayList;
032    import java.util.LinkedHashMap;
033    import java.util.List;
034    import java.util.Map;
035    
036    /**
037     * @author Alexander Chow
038     * @author Raymond Aug??
039     */
040    public class TemplateNode extends LinkedHashMap<String, Object> {
041    
042            public TemplateNode(
043                    ThemeDisplay themeDisplay, String name, String data, String type,
044                    Map<String, String> attributes) {
045    
046                    _themeDisplay = themeDisplay;
047    
048                    put("attributes", attributes);
049                    put("name", name);
050                    put("data", data);
051                    put("type", type);
052                    put("options", new ArrayList<String>());
053            }
054    
055            public void appendChild(TemplateNode templateNode) {
056                    _childTemplateNodes.put(templateNode.getName(), templateNode);
057    
058                    put(templateNode.getName(), templateNode);
059            }
060    
061            public void appendChildren(List<TemplateNode> templateNodes) {
062                    for (TemplateNode templateNode : templateNodes) {
063                            appendChild(templateNode);
064                    }
065            }
066    
067            public void appendOption(String option) {
068                    List<String> options = getOptions();
069    
070                    options.add(option);
071            }
072    
073            public void appendOptions(List<String> options) {
074                    List<String> curOptions = getOptions();
075    
076                    curOptions.addAll(options);
077            }
078    
079            public void appendSibling(TemplateNode templateNode) {
080                    _siblingTemplateNodes.add(templateNode);
081            }
082    
083            public String getAttribute(String name) {
084                    Map<String, String> attributes = getAttributes();
085    
086                    if (attributes == null) {
087                            return StringPool.BLANK;
088                    }
089    
090                    return attributes.get(name);
091            }
092    
093            public Map<String, String> getAttributes() {
094                    return (Map<String, String>)get("attributes");
095            }
096    
097            public TemplateNode getChild(String name) {
098                    return _childTemplateNodes.get(name);
099            }
100    
101            public List<TemplateNode> getChildren() {
102                    return new ArrayList<>(_childTemplateNodes.values());
103            }
104    
105            public String getData() {
106                    String type = getType();
107    
108                    if (type.equals("link_to_layout")) {
109                            String data = (String)get("data");
110    
111                            int pos = data.indexOf(CharPool.AT);
112    
113                            if (pos != -1) {
114                                    data = data.substring(0, pos);
115                            }
116    
117                            return data;
118                    }
119                    else {
120                            return (String)get("data");
121                    }
122            }
123    
124            public String getFriendlyUrl() {
125                    if (_themeDisplay == null) {
126                            return getUrl();
127                    }
128    
129                    String type = getType();
130    
131                    if (!type.equals("link_to_layout")) {
132                            return StringPool.BLANK;
133                    }
134    
135                    String layoutType = getLayoutType();
136    
137                    if (Validator.isNull(layoutType)) {
138                            return StringPool.BLANK;
139                    }
140    
141                    long groupId = getLayoutGroupId();
142    
143                    if (groupId == 0) {
144                            groupId = _themeDisplay.getScopeGroupId();
145                    }
146    
147                    boolean privateLayout = layoutType.startsWith("private");
148    
149                    try {
150                            Layout layout = LayoutLocalServiceUtil.getLayout(
151                                    groupId, privateLayout, getLayoutId());
152    
153                            return PortalUtil.getLayoutFriendlyURL(layout, _themeDisplay);
154                    }
155                    catch (Exception e) {
156                            if (_log.isDebugEnabled()) {
157                                    _log.debug(
158                                            "Error finding friendly URL on page " +
159                                                    _themeDisplay.getURLCurrent(),
160                                            e);
161                            }
162    
163                            return getUrl();
164                    }
165            }
166    
167            public String getName() {
168                    return (String)get("name");
169            }
170    
171            public List<String> getOptions() {
172                    return (List<String>)get("options");
173            }
174    
175            public List<TemplateNode> getSiblings() {
176                    return _siblingTemplateNodes;
177            }
178    
179            public String getType() {
180                    return (String)get("type");
181            }
182    
183            public String getUrl() {
184                    String type = getType();
185    
186                    if (!type.equals("link_to_layout")) {
187                            return StringPool.BLANK;
188                    }
189    
190                    StringBundler sb = new StringBundler(5);
191    
192                    String layoutType = getLayoutType();
193    
194                    if (Validator.isNull(layoutType)) {
195                            return StringPool.BLANK;
196                    }
197    
198                    if (layoutType.equals(_LAYOUT_TYPE_PRIVATE_GROUP)) {
199                            sb.append(PortalUtil.getPathFriendlyURLPrivateGroup());
200                    }
201                    else if (layoutType.equals(_LAYOUT_TYPE_PRIVATE_USER)) {
202                            sb.append(PortalUtil.getPathFriendlyURLPrivateUser());
203                    }
204                    else if (layoutType.equals(_LAYOUT_TYPE_PUBLIC)) {
205                            sb.append(PortalUtil.getPathFriendlyURLPublic());
206                    }
207                    else {
208                            sb.append("@friendly_url_current@");
209                    }
210    
211                    sb.append(StringPool.SLASH);
212    
213                    try {
214                            Group group = GroupLocalServiceUtil.getGroup(getLayoutGroupId());
215    
216                            String name = group.getFriendlyURL();
217    
218                            name = name.substring(1);
219    
220                            sb.append(name);
221                    }
222                    catch (Exception e) {
223                            sb.append("@group_id@");
224                    }
225    
226                    sb.append(StringPool.SLASH);
227                    sb.append(getLayoutId());
228    
229                    return sb.toString();
230            }
231    
232            protected long getLayoutGroupId() {
233                    String data = (String)get("data");
234    
235                    int pos = data.lastIndexOf(CharPool.AT);
236    
237                    if (pos != -1) {
238                            data = data.substring(pos + 1);
239                    }
240    
241                    return GetterUtil.getLong(data);
242            }
243    
244            protected long getLayoutId() {
245                    String data = (String)get("data");
246    
247                    int pos = data.indexOf(CharPool.AT);
248    
249                    if (pos != -1) {
250                            data = data.substring(0, pos);
251                    }
252    
253                    return GetterUtil.getLong(data);
254            }
255    
256            protected String getLayoutType() {
257                    String data = (String)get("data");
258    
259                    int x = data.indexOf(CharPool.AT);
260                    int y = data.lastIndexOf(CharPool.AT);
261    
262                    if ((x != -1) && (y != -1)) {
263                            if (x == y) {
264                                    data = data.substring(x + 1);
265                            }
266                            else {
267                                    data = data.substring(x + 1, y);
268                            }
269                    }
270    
271                    return data;
272            }
273    
274            private static final String _LAYOUT_TYPE_PRIVATE_GROUP = "private-group";
275    
276            private static final String _LAYOUT_TYPE_PRIVATE_USER = "private-user";
277    
278            private static final String _LAYOUT_TYPE_PUBLIC = "public";
279    
280            private static final Log _log = LogFactoryUtil.getLog(TemplateNode.class);
281    
282            private final Map<String, TemplateNode> _childTemplateNodes =
283                    new LinkedHashMap<>();
284            private final List<TemplateNode> _siblingTemplateNodes = new ArrayList<>();
285            private ThemeDisplay _themeDisplay;
286    
287    }