001    /**
002     * Copyright (c) 2000-2013 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.portlet.wiki.action;
016    
017    import com.liferay.portal.kernel.portlet.LiferayPortletConfig;
018    import com.liferay.portal.kernel.servlet.SessionErrors;
019    import com.liferay.portal.kernel.servlet.SessionMessages;
020    import com.liferay.portal.kernel.util.Constants;
021    import com.liferay.portal.kernel.util.ParamUtil;
022    import com.liferay.portal.kernel.util.StringPool;
023    import com.liferay.portal.kernel.util.StringUtil;
024    import com.liferay.portal.kernel.util.Validator;
025    import com.liferay.portal.security.auth.PrincipalException;
026    import com.liferay.portal.service.ServiceContext;
027    import com.liferay.portal.service.ServiceContextFactory;
028    import com.liferay.portal.struts.PortletAction;
029    import com.liferay.portal.theme.ThemeDisplay;
030    import com.liferay.portal.util.WebKeys;
031    import com.liferay.portlet.wiki.DuplicateNodeNameException;
032    import com.liferay.portlet.wiki.NoSuchNodeException;
033    import com.liferay.portlet.wiki.NodeNameException;
034    import com.liferay.portlet.wiki.RequiredNodeException;
035    import com.liferay.portlet.wiki.model.WikiNode;
036    import com.liferay.portlet.wiki.service.WikiNodeLocalServiceUtil;
037    import com.liferay.portlet.wiki.service.WikiNodeServiceUtil;
038    import com.liferay.portlet.wiki.util.WikiCacheThreadLocal;
039    import com.liferay.portlet.wiki.util.WikiCacheUtil;
040    
041    import java.util.HashMap;
042    import java.util.Map;
043    
044    import javax.portlet.ActionRequest;
045    import javax.portlet.ActionResponse;
046    import javax.portlet.PortletConfig;
047    import javax.portlet.PortletPreferences;
048    import javax.portlet.RenderRequest;
049    import javax.portlet.RenderResponse;
050    
051    import org.apache.struts.action.ActionForm;
052    import org.apache.struts.action.ActionForward;
053    import org.apache.struts.action.ActionMapping;
054    
055    /**
056     * @author Brian Wing Shun Chan
057     */
058    public class EditNodeAction extends PortletAction {
059    
060            @Override
061            public void processAction(
062                            ActionMapping actionMapping, ActionForm actionForm,
063                            PortletConfig portletConfig, ActionRequest actionRequest,
064                            ActionResponse actionResponse)
065                    throws Exception {
066    
067                    String cmd = ParamUtil.getString(actionRequest, Constants.CMD);
068    
069                    try {
070                            if (cmd.equals(Constants.ADD) || cmd.equals(Constants.UPDATE)) {
071                                    updateNode(actionRequest);
072                            }
073                            else if (cmd.equals(Constants.DELETE)) {
074                                    deleteNode(
075                                            (LiferayPortletConfig)portletConfig, actionRequest, false);
076                            }
077                            else if (cmd.equals(Constants.MOVE_TO_TRASH)) {
078                                    deleteNode(
079                                            (LiferayPortletConfig)portletConfig, actionRequest, true);
080                            }
081                            else if (cmd.equals(Constants.RESTORE)) {
082                                    restoreNode(actionRequest);
083                            }
084                            else if (cmd.equals(Constants.SUBSCRIBE)) {
085                                    subscribeNode(actionRequest);
086                            }
087                            else if (cmd.equals(Constants.UNSUBSCRIBE)) {
088                                    unsubscribeNode(actionRequest);
089                            }
090    
091                            sendRedirect(actionRequest, actionResponse);
092                    }
093                    catch (Exception e) {
094                            if (e instanceof NoSuchNodeException ||
095                                    e instanceof PrincipalException) {
096    
097                                    SessionErrors.add(actionRequest, e.getClass());
098    
099                                    setForward(actionRequest, "portlet.wiki.error");
100                            }
101                            else if (e instanceof DuplicateNodeNameException ||
102                                             e instanceof NodeNameException) {
103    
104                                    SessionErrors.add(actionRequest, e.getClass());
105                            }
106                            else {
107                                    throw e;
108                            }
109                    }
110            }
111    
112            @Override
113            public ActionForward render(
114                            ActionMapping actionMapping, ActionForm actionForm,
115                            PortletConfig portletConfig, RenderRequest renderRequest,
116                            RenderResponse renderResponse)
117                    throws Exception {
118    
119                    try {
120                            long nodeId = ParamUtil.getLong(renderRequest, "nodeId");
121    
122                            if (nodeId > 0) {
123                                    ActionUtil.getNode(renderRequest);
124                            }
125                    }
126                    catch (Exception e) {
127                            if (e instanceof NoSuchNodeException ||
128                                    e instanceof PrincipalException) {
129    
130                                    SessionErrors.add(renderRequest, e.getClass());
131    
132                                    return actionMapping.findForward("portlet.wiki.error");
133                            }
134                            else {
135                                    throw e;
136                            }
137                    }
138    
139                    return actionMapping.findForward(
140                            getForward(renderRequest, "portlet.wiki.edit_node"));
141            }
142    
143            protected void deleteNode(
144                            LiferayPortletConfig liferayPortletConfig,
145                            ActionRequest actionRequest, boolean moveToTrash)
146                    throws Exception {
147    
148                    ThemeDisplay themeDisplay = (ThemeDisplay)actionRequest.getAttribute(
149                            WebKeys.THEME_DISPLAY);
150    
151                    int nodeCount = WikiNodeLocalServiceUtil.getNodesCount(
152                            themeDisplay.getScopeGroupId());
153    
154                    if (nodeCount == 1) {
155                            SessionErrors.add(actionRequest, RequiredNodeException.class);
156    
157                            return;
158                    }
159    
160                    long nodeId = ParamUtil.getLong(actionRequest, "nodeId");
161    
162                    String oldName = getNodeName(nodeId);
163    
164                    WikiCacheThreadLocal.setClearCache(false);
165    
166                    String deleteEntryTitle = null;
167    
168                    if (moveToTrash) {
169                            WikiNode node = WikiNodeServiceUtil.moveNodeToTrash(nodeId);
170    
171                            deleteEntryTitle = node.getName();
172                    }
173                    else {
174                            WikiNodeServiceUtil.deleteNode(nodeId);
175                    }
176    
177                    WikiCacheUtil.clearCache(nodeId);
178    
179                    WikiCacheThreadLocal.setClearCache(true);
180    
181                    updatePreferences(actionRequest, oldName, StringPool.BLANK);
182    
183                    if (moveToTrash) {
184                            Map<String, String[]> data = new HashMap<String, String[]>();
185    
186                            data.put(
187                                    "deleteEntryClassName",
188                                    new String[] {WikiNode.class.getName()});
189    
190                            if (Validator.isNotNull(deleteEntryTitle)) {
191                                    data.put("deleteEntryTitle", new String[] {deleteEntryTitle});
192                            }
193    
194                            data.put("restoreEntryIds", new String[] {String.valueOf(nodeId)});
195    
196                            SessionMessages.add(
197                                    actionRequest,
198                                    liferayPortletConfig.getPortletId() +
199                                            SessionMessages.KEY_SUFFIX_DELETE_SUCCESS_DATA, data);
200    
201                            hideDefaultSuccessMessage(liferayPortletConfig, actionRequest);
202                    }
203            }
204    
205            protected String getNodeName(long nodeId) throws Exception {
206                    WikiNode node = WikiNodeServiceUtil.getNode(nodeId);
207    
208                    return node.getName();
209            }
210    
211            protected void restoreNode(ActionRequest actionRequest) throws Exception {
212                    long[] restoreEntryIds = StringUtil.split(
213                            ParamUtil.getString(actionRequest, "restoreEntryIds"), 0L);
214    
215                    for (long restoreEntryId : restoreEntryIds) {
216                            WikiNodeServiceUtil.restoreNodeFromTrash(restoreEntryId);
217                    }
218            }
219    
220            protected void subscribeNode(ActionRequest actionRequest) throws Exception {
221                    long nodeId = ParamUtil.getLong(actionRequest, "nodeId");
222    
223                    WikiNodeServiceUtil.subscribeNode(nodeId);
224            }
225    
226            protected void unsubscribeNode(ActionRequest actionRequest)
227                    throws Exception {
228    
229                    long nodeId = ParamUtil.getLong(actionRequest, "nodeId");
230    
231                    WikiNodeServiceUtil.unsubscribeNode(nodeId);
232            }
233    
234            protected void updateNode(ActionRequest actionRequest) throws Exception {
235                    long nodeId = ParamUtil.getLong(actionRequest, "nodeId");
236    
237                    String name = ParamUtil.getString(actionRequest, "name");
238                    String description = ParamUtil.getString(actionRequest, "description");
239    
240                    ServiceContext serviceContext = ServiceContextFactory.getInstance(
241                            WikiNode.class.getName(), actionRequest);
242    
243                    if (nodeId <= 0) {
244    
245                            // Add node
246    
247                            WikiNodeServiceUtil.addNode(name, description, serviceContext);
248                    }
249                    else {
250    
251                            // Update node
252    
253                            String oldName = getNodeName(nodeId);
254    
255                            WikiNodeServiceUtil.updateNode(
256                                    nodeId, name, description, serviceContext);
257    
258                            updatePreferences(actionRequest, oldName, name);
259                    }
260            }
261    
262            protected void updatePreferences(
263                            ActionRequest actionRequest, String oldName, String newName)
264                    throws Exception {
265    
266                    PortletPreferences portletPreferences = actionRequest.getPreferences();
267    
268                    String hiddenNodes = portletPreferences.getValue(
269                            "hiddenNodes", StringPool.BLANK);
270                    String visibleNodes = portletPreferences.getValue(
271                            "visibleNodes", StringPool.BLANK);
272    
273                    String regex = oldName + ",?";
274    
275                    portletPreferences.setValue(
276                            "hiddenNodes", hiddenNodes.replaceFirst(regex, newName));
277                    portletPreferences.setValue(
278                            "visibleNodes",
279                            visibleNodes.replaceFirst(regex, newName));
280    
281                    portletPreferences.store();
282            }
283    
284    }