/**
* Copyright (c) 2000-present Liferay, Inc. All rights reserved.
*
* This library is free software; you can redistribute it and/or modify it under
* the terms of the GNU Lesser General Public License as published by the Free
* Software Foundation; either version 2.1 of the License, or (at your option)
* any later version.
*
* This library is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
* FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
* details.
*/
package com.liferay.portal.action;
import com.liferay.asset.kernel.model.AssetEntry;
import com.liferay.exportimport.kernel.staging.StagingUtil;
import com.liferay.portal.kernel.json.JSONFactoryUtil;
import com.liferay.portal.kernel.json.JSONObject;
import com.liferay.portal.kernel.model.Layout;
import com.liferay.portal.kernel.model.LayoutRevision;
import com.liferay.portal.kernel.model.LayoutTypePortlet;
import com.liferay.portal.kernel.model.Portlet;
import com.liferay.portal.kernel.portlet.AddPortletProvider;
import com.liferay.portal.kernel.portlet.PortletJSONUtil;
import com.liferay.portal.kernel.portlet.PortletPreferencesFactoryUtil;
import com.liferay.portal.kernel.security.permission.ActionKeys;
import com.liferay.portal.kernel.security.permission.PermissionChecker;
import com.liferay.portal.kernel.service.LayoutRevisionLocalServiceUtil;
import com.liferay.portal.kernel.service.LayoutServiceUtil;
import com.liferay.portal.kernel.service.PortletLocalServiceUtil;
import com.liferay.portal.kernel.service.ServiceContext;
import com.liferay.portal.kernel.service.ServiceContextFactory;
import com.liferay.portal.kernel.service.permission.LayoutPermissionUtil;
import com.liferay.portal.kernel.servlet.BufferCacheServletResponse;
import com.liferay.portal.kernel.servlet.DynamicServletRequest;
import com.liferay.portal.kernel.servlet.ServletResponseUtil;
import com.liferay.portal.kernel.theme.ThemeDisplay;
import com.liferay.portal.kernel.util.Constants;
import com.liferay.portal.kernel.util.ContentTypes;
import com.liferay.portal.kernel.util.GetterUtil;
import com.liferay.portal.kernel.util.InstancePool;
import com.liferay.portal.kernel.util.ParamUtil;
import com.liferay.portal.kernel.util.PortalUtil;
import com.liferay.portal.kernel.util.PropertiesParamUtil;
import com.liferay.portal.kernel.util.StringBundler;
import com.liferay.portal.kernel.util.StringPool;
import com.liferay.portal.kernel.util.StringUtil;
import com.liferay.portal.kernel.util.UnicodeProperties;
import com.liferay.portal.kernel.util.Validator;
import com.liferay.portal.kernel.util.WebKeys;
import com.liferay.portal.kernel.workflow.WorkflowConstants;
import com.liferay.portal.servlet.NamespaceServletRequest;
import com.liferay.portal.struts.JSONAction;
import com.liferay.portal.util.LayoutClone;
import com.liferay.portal.util.LayoutCloneFactory;
import com.liferay.registry.collections.ServiceTrackerCollections;
import com.liferay.registry.collections.ServiceTrackerMap;
import javax.portlet.PortletPreferences;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.struts.action.Action;
import org.apache.struts.action.ActionForm;
import org.apache.struts.action.ActionMapping;
/**
* @author Brian Wing Shun Chan
*/
public class UpdateLayoutAction extends JSONAction {
@Override
public String getJSON(
ActionMapping actionMapping, ActionForm actionForm,
HttpServletRequest request, HttpServletResponse response)
throws Exception {
ThemeDisplay themeDisplay = (ThemeDisplay)request.getAttribute(
WebKeys.THEME_DISPLAY);
long userId = themeDisplay.getUserId();
Layout layout = themeDisplay.getLayout();
LayoutTypePortlet layoutTypePortlet =
themeDisplay.getLayoutTypePortlet();
PermissionChecker permissionChecker =
themeDisplay.getPermissionChecker();
String cmd = ParamUtil.getString(request, Constants.CMD);
String portletId = ParamUtil.getString(request, "p_p_id");
boolean updateLayout = true;
if (cmd.equals(Constants.ADD)) {
String columnId = ParamUtil.getString(request, "p_p_col_id", null);
int columnPos = ParamUtil.getInteger(request, "p_p_col_pos", -1);
portletId = layoutTypePortlet.addPortletId(
userId, portletId, columnId, columnPos);
storeAddContentPortletPreferences(
request, layout, portletId, themeDisplay);
if (layoutTypePortlet.isCustomizable() &&
layoutTypePortlet.isCustomizedView() &&
!layoutTypePortlet.isColumnDisabled(columnId)) {
updateLayout = false;
}
}
else if (cmd.equals(Constants.DELETE)) {
if (layoutTypePortlet.hasPortletId(portletId)) {
layoutTypePortlet.removePortletId(userId, portletId);
if (layoutTypePortlet.isCustomizable() &&
layoutTypePortlet.isCustomizedView()) {
updateLayout = false;
}
}
}
else if (cmd.equals("drag")) {
if (LayoutPermissionUtil.contains(
permissionChecker, layout, ActionKeys.UPDATE)) {
String height = ParamUtil.getString(request, "height");
String width = ParamUtil.getString(request, "width");
String top = ParamUtil.getString(request, "top");
String left = ParamUtil.getString(request, "left");
PortletPreferences portletPreferences =
PortletPreferencesFactoryUtil.getLayoutPortletSetup(
layout, portletId);
StringBundler sb = new StringBundler(12);
sb.append("height=");
sb.append(height);
sb.append("\n");
sb.append("width=");
sb.append(width);
sb.append("\n");
sb.append("top=");
sb.append(top);
sb.append("\n");
sb.append("left=");
sb.append(left);
sb.append("\n");
portletPreferences.setValue(
"portlet-freeform-styles", sb.toString());
portletPreferences.store();
}
}
else if (cmd.equals("minimize")) {
boolean restore = ParamUtil.getBoolean(request, "p_p_restore");
if (restore) {
layoutTypePortlet.removeStateMinPortletId(portletId);
}
else {
layoutTypePortlet.addStateMinPortletId(portletId);
}
updateLayout = false;
}
else if (cmd.equals("move")) {
String columnId = ParamUtil.getString(request, "p_p_col_id");
int columnPos = ParamUtil.getInteger(request, "p_p_col_pos");
layoutTypePortlet.movePortletId(
userId, portletId, columnId, columnPos);
if (layoutTypePortlet.isCustomizable() &&
layoutTypePortlet.isCustomizedView() &&
!layoutTypePortlet.isColumnDisabled(columnId)) {
updateLayout = false;
}
}
else if (cmd.equals("redo_layout_revision")) {
long layoutRevisionId = ParamUtil.getLong(
request, "layoutRevisionId");
long layoutSetBranchId = ParamUtil.getLong(
request, "layoutSetBranchId");
ServiceContext serviceContext = ServiceContextFactory.getInstance(
request);
LayoutRevisionLocalServiceUtil.updateStatus(
userId, layoutRevisionId, WorkflowConstants.STATUS_DRAFT,
serviceContext);
StagingUtil.setRecentLayoutRevisionId(
request, layoutSetBranchId, layout.getPlid(), layoutRevisionId);
updateLayout = false;
}
else if (cmd.equals("select_layout_revision")) {
long layoutRevisionId = ParamUtil.getLong(
request, "layoutRevisionId");
long layoutSetBranchId = ParamUtil.getLong(
request, "layoutSetBranchId");
StagingUtil.setRecentLayoutRevisionId(
request, layoutSetBranchId, layout.getPlid(), layoutRevisionId);
updateLayout = false;
}
else if (cmd.equals("update_type_settings")) {
UnicodeProperties layoutTypeSettingsProperties =
layout.getTypeSettingsProperties();
UnicodeProperties formTypeSettingsProperties =
PropertiesParamUtil.getProperties(
request, "TypeSettingsProperties--");
layoutTypeSettingsProperties.putAll(formTypeSettingsProperties);
}
else if (cmd.equals("undo_layout_revision")) {
long layoutRevisionId = ParamUtil.getLong(
request, "layoutRevisionId");
long layoutSetBranchId = ParamUtil.getLong(
request, "layoutSetBranchId");
ServiceContext serviceContext = ServiceContextFactory.getInstance(
request);
LayoutRevision layoutRevision =
LayoutRevisionLocalServiceUtil.updateStatus(
userId, layoutRevisionId, WorkflowConstants.STATUS_INACTIVE,
serviceContext);
StagingUtil.setRecentLayoutRevisionId(
request, layoutSetBranchId, layout.getPlid(),
layoutRevision.getParentLayoutRevisionId());
updateLayout = false;
}
if (updateLayout) {
// LEP-3648
layoutTypePortlet.resetModes();
layoutTypePortlet.resetStates();
layout = LayoutServiceUtil.updateLayout(
layout.getGroupId(), layout.isPrivateLayout(),
layout.getLayoutId(), layout.getTypeSettings());
}
else {
LayoutClone layoutClone = LayoutCloneFactory.getInstance();
if (layoutClone != null) {
layoutClone.update(
request, layout.getPlid(), layout.getTypeSettings());
}
}
if (cmd.equals(Constants.ADD) && (portletId != null)) {
addPortlet(actionMapping, actionForm, request, response, portletId);
}
return StringPool.BLANK;
}
protected void addPortlet(
ActionMapping actionMapping, ActionForm actionForm,
HttpServletRequest request, HttpServletResponse response,
String portletId)
throws Exception {
// Run the render portlet action to add a portlet without refreshing.
Action renderPortletAction = (Action)InstancePool.get(
RenderPortletAction.class.getName());
// Pass in the portlet id because the portlet id may be the instance id.
// Namespace the request if necessary. See LEP-4644.
long companyId = PortalUtil.getCompanyId(request);
Portlet portlet = PortletLocalServiceUtil.getPortletById(
companyId, portletId);
DynamicServletRequest dynamicRequest = null;
if (portlet.isPrivateRequestAttributes()) {
String portletNamespace = PortalUtil.getPortletNamespace(
portlet.getPortletId());
dynamicRequest = new NamespaceServletRequest(
request, portletNamespace, portletNamespace);
}
else {
dynamicRequest = new DynamicServletRequest(request);
}
dynamicRequest.setParameter("p_p_id", portletId);
String dataType = StringUtil.toLowerCase(
ParamUtil.getString(request, "dataType"));
if (dataType.equals("json")) {
JSONObject jsonObject = JSONFactoryUtil.createJSONObject();
BufferCacheServletResponse bufferCacheServletResponse =
new BufferCacheServletResponse(response);
renderPortletAction.execute(
actionMapping, actionForm, dynamicRequest,
bufferCacheServletResponse);
String portletHTML = bufferCacheServletResponse.getString();
portletHTML = portletHTML.trim();
PortletJSONUtil.populatePortletJSONObject(
request, portletHTML, portlet, jsonObject);
response.setContentType(ContentTypes.APPLICATION_JSON);
ServletResponseUtil.write(response, jsonObject.toString());
}
else {
renderPortletAction.execute(
actionMapping, actionForm, dynamicRequest, response);
}
}
protected void storeAddContentPortletPreferences(
HttpServletRequest request, Layout layout, String portletId,
ThemeDisplay themeDisplay)
throws Exception {
// We need to get the portlet setup before doing anything else to ensure
// that it is created in the database
PortletPreferences portletSetup =
PortletPreferencesFactoryUtil.getLayoutPortletSetup(
layout, portletId);
String[] portletData = StringUtil.split(
ParamUtil.getString(request, "portletData"));
if (portletData.length == 0) {
return;
}
long classPK = GetterUtil.getLong(portletData[0]);
String className = GetterUtil.getString(portletData[1]);
if ((classPK <= 0) || Validator.isNull(className)) {
return;
}
AddPortletProvider addPortletProvider = _serviceTrackerMap.getService(
className);
if (addPortletProvider == null) {
addPortletProvider = _serviceTrackerMap.getService(
AssetEntry.class.getName());
}
if (addPortletProvider != null) {
addPortletProvider.updatePortletPreferences(
portletSetup, portletId, className, classPK, themeDisplay);
}
portletSetup.store();
}
private static final ServiceTrackerMap<String, AddPortletProvider>
_serviceTrackerMap = ServiceTrackerCollections.openSingleValueMap(
AddPortletProvider.class, "model.class.name");
}