1   /**
2    * Copyright (c) 2000-2008 Liferay, Inc. All rights reserved.
3    *
4    * Permission is hereby granted, free of charge, to any person obtaining a copy
5    * of this software and associated documentation files (the "Software"), to deal
6    * in the Software without restriction, including without limitation the rights
7    * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8    * copies of the Software, and to permit persons to whom the Software is
9    * furnished to do so, subject to the following conditions:
10   *
11   * The above copyright notice and this permission notice shall be included in
12   * all copies or substantial portions of the Software.
13   *
14   * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15   * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16   * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17   * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18   * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
19   * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
20   * SOFTWARE.
21   */
22  
23  package com.liferay.portal.action;
24  
25  import com.liferay.portal.kernel.json.JSONFactoryUtil;
26  import com.liferay.portal.kernel.json.JSONObject;
27  import com.liferay.portal.kernel.servlet.StringServletResponse;
28  import com.liferay.portal.kernel.util.Constants;
29  import com.liferay.portal.kernel.util.InstancePool;
30  import com.liferay.portal.kernel.util.ParamUtil;
31  import com.liferay.portal.kernel.util.Validator;
32  import com.liferay.portal.model.Layout;
33  import com.liferay.portal.model.LayoutTypePortlet;
34  import com.liferay.portal.model.Portlet;
35  import com.liferay.portal.model.PortletConstants;
36  import com.liferay.portal.model.ResourceConstants;
37  import com.liferay.portal.security.permission.ActionKeys;
38  import com.liferay.portal.security.permission.PermissionChecker;
39  import com.liferay.portal.service.LayoutServiceUtil;
40  import com.liferay.portal.service.PortletLocalServiceUtil;
41  import com.liferay.portal.service.ResourceLocalServiceUtil;
42  import com.liferay.portal.service.permission.LayoutPermissionUtil;
43  import com.liferay.portal.service.permission.PortletPermissionUtil;
44  import com.liferay.portal.servlet.NamespaceServletRequest;
45  import com.liferay.portal.struts.ActionConstants;
46  import com.liferay.portal.theme.ThemeDisplay;
47  import com.liferay.portal.util.LayoutClone;
48  import com.liferay.portal.util.LayoutCloneFactory;
49  import com.liferay.portal.util.PortalUtil;
50  import com.liferay.portal.util.WebKeys;
51  import com.liferay.portlet.PortletPreferencesFactoryUtil;
52  import com.liferay.util.servlet.DynamicServletRequest;
53  import com.liferay.util.servlet.ServletResponseUtil;
54  
55  import javax.portlet.PortletPreferences;
56  
57  import javax.servlet.http.HttpServletRequest;
58  import javax.servlet.http.HttpServletResponse;
59  
60  import org.apache.struts.action.Action;
61  import org.apache.struts.action.ActionForm;
62  import org.apache.struts.action.ActionForward;
63  import org.apache.struts.action.ActionMapping;
64  
65  /**
66   * <a href="UpdateLayoutAction.java.html"><b><i>View Source</i></b></a>
67   *
68   * @author Brian Wing Shun Chan
69   *
70   */
71  public class UpdateLayoutAction extends Action {
72  
73      public ActionForward execute(
74              ActionMapping mapping, ActionForm form, HttpServletRequest request,
75              HttpServletResponse response)
76          throws Exception {
77  
78          ThemeDisplay themeDisplay = (ThemeDisplay)request.getAttribute(
79              WebKeys.THEME_DISPLAY);
80  
81          long userId = themeDisplay.getUserId();
82  
83          Layout layout = themeDisplay.getLayout();
84          LayoutTypePortlet layoutTypePortlet =
85              themeDisplay.getLayoutTypePortlet();
86  
87          PermissionChecker permissionChecker =
88              themeDisplay.getPermissionChecker();
89  
90          String cmd = ParamUtil.getString(request, Constants.CMD);
91  
92          String portletId = ParamUtil.getString(request, "p_p_id");
93  
94          boolean updateLayout = true;
95          boolean deletePortlet = false;
96  
97          if (cmd.equals(Constants.ADD)) {
98              portletId = layoutTypePortlet.addPortletId(userId, portletId);
99  
100             String columnId = ParamUtil.getString(request, "p_p_col_id");
101             int columnPos = ParamUtil.getInteger(request, "p_p_col_pos");
102 
103             if (Validator.isNotNull(columnId)) {
104                 layoutTypePortlet.movePortletId(
105                     userId, portletId, columnId, columnPos);
106             }
107         }
108         else if (cmd.equals(Constants.DELETE)) {
109             if (layoutTypePortlet.hasPortletId(portletId)) {
110                 deletePortlet = true;
111 
112                 layoutTypePortlet.removePortletId(portletId);
113             }
114         }
115         else if (cmd.equals("drag")) {
116             if (LayoutPermissionUtil.contains(
117                     permissionChecker, layout.getGroupId(),
118                     layout.isPrivateLayout(), layout.getLayoutId(),
119                     ActionKeys.UPDATE)) {
120 
121                 String height = ParamUtil.getString(request, "height");
122                 String width = ParamUtil.getString(request, "width");
123                 String top = ParamUtil.getString(request, "top");
124                 String left = ParamUtil.getString(request, "left");
125 
126                 PortletPreferences prefs =
127                     PortletPreferencesFactoryUtil.getLayoutPortletSetup(
128                         layout, portletId);
129 
130                 StringBuilder sb = new StringBuilder();
131 
132                 sb.append("height=" + height + "\n");
133                 sb.append("width=" + width + "\n");
134                 sb.append("top=" + top + "\n");
135                 sb.append("left=" + left + "\n");
136 
137                 prefs.setValue("portlet-freeform-styles", sb.toString());
138 
139                 prefs.store();
140             }
141         }
142         else if (cmd.equals("minimize")) {
143             boolean restore = ParamUtil.getBoolean(request, "p_p_restore");
144 
145             if (restore) {
146                 layoutTypePortlet.removeStateMinPortletId(portletId);
147             }
148             else {
149                 layoutTypePortlet.addStateMinPortletId(portletId);
150             }
151 
152             updateLayout = false;
153         }
154         else if (cmd.equals("move")) {
155             String columnId = ParamUtil.getString(request, "p_p_col_id");
156             int columnPos = ParamUtil.getInteger(request, "p_p_col_pos");
157 
158             layoutTypePortlet.movePortletId(
159                 userId, portletId, columnId, columnPos);
160         }
161         else if (cmd.equals("template")) {
162             String layoutTemplateId = ParamUtil.getString(
163                 request, "layoutTemplateId");
164 
165             layoutTypePortlet.setLayoutTemplateId(userId, layoutTemplateId);
166         }
167 
168         if (updateLayout) {
169 
170             // LEP-3648
171 
172             layoutTypePortlet.resetStates();
173 
174             LayoutServiceUtil.updateLayout(
175                 layout.getGroupId(), layout.isPrivateLayout(),
176                 layout.getLayoutId(), layout.getTypeSettings());
177 
178             // See LEP-1411. Delay the delete of extraneous portlet resources
179             // only after the user has proven that he has the valid permissions.
180 
181             if (deletePortlet) {
182                 String rootPortletId = PortletConstants.getRootPortletId(
183                     portletId);
184 
185                 ResourceLocalServiceUtil.deleteResource(
186                     layout.getCompanyId(), rootPortletId,
187                     ResourceConstants.SCOPE_INDIVIDUAL,
188                     PortletPermissionUtil.getPrimaryKey(
189                         layout.getPlid(), portletId));
190             }
191         }
192         else {
193             LayoutClone layoutClone = LayoutCloneFactory.getInstance();
194 
195             if (layoutClone != null) {
196                 layoutClone.update(
197                     request, layout.getPlid(), layout.getTypeSettings());
198             }
199         }
200 
201         // The check for the refresh variable can be removed in the future. See
202         // LEP-6910.
203 
204         if (ParamUtil.getBoolean(request, "refresh")) {
205             return mapping.findForward(ActionConstants.COMMON_REFERER);
206         }
207         else {
208             if (cmd.equals(Constants.ADD) && (portletId != null)) {
209                 addPortlet(mapping, form, request, response, portletId);
210             }
211 
212             return null;
213         }
214     }
215 
216     protected void addPortlet(
217             ActionMapping mapping, ActionForm form, HttpServletRequest request,
218             HttpServletResponse response, String portletId)
219         throws Exception {
220 
221         // Run the render portlet action to add a portlet without refreshing.
222 
223         Action renderPortletAction = (Action)InstancePool.get(
224             RenderPortletAction.class.getName());
225 
226         // Pass in the portlet id because the portlet id may be the instance id.
227         // Namespace the request if necessary. See LEP-4644.
228 
229         long companyId = PortalUtil.getCompanyId(request);
230 
231         Portlet portlet = PortletLocalServiceUtil.getPortletById(
232             companyId, portletId);
233 
234         DynamicServletRequest dynamicRequest = null;
235 
236         if (portlet.isPrivateRequestAttributes()) {
237             String portletNamespace =
238                 PortalUtil.getPortletNamespace(portlet.getPortletId());
239 
240             dynamicRequest = new NamespaceServletRequest(
241                 request, portletNamespace, portletNamespace);
242         }
243         else {
244             dynamicRequest = new DynamicServletRequest(request);
245         }
246 
247         dynamicRequest.setParameter("p_p_id", portletId);
248 
249         String dataType = ParamUtil.getString(request, "dataType");
250 
251         if (dataType.equals("json")) {
252             JSONObject jsonObj = JSONFactoryUtil.createJSONObject();
253 
254             if (portlet.isAjaxable()) {
255                 StringServletResponse stringResponse =
256                     new StringServletResponse(response);
257 
258                 renderPortletAction.execute(
259                     mapping, form, dynamicRequest, stringResponse);
260 
261                 jsonObj.put("refresh", false);
262                 jsonObj.put("portletHTML", stringResponse.getString().trim());
263             }
264             else {
265                 jsonObj.put("refresh", true);
266             }
267 
268             ServletResponseUtil.write(response, jsonObj.toString());
269         }
270         else {
271             renderPortletAction.execute(
272                 mapping, form, dynamicRequest, response);
273         }
274     }
275 
276 }