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.assetpublisher.lar;
016    
017    import com.liferay.portal.NoSuchGroupException;
018    import com.liferay.portal.kernel.lar.DataLevel;
019    import com.liferay.portal.kernel.lar.DefaultConfigurationPortletDataHandler;
020    import com.liferay.portal.kernel.lar.ExportImportHelperUtil;
021    import com.liferay.portal.kernel.lar.PortletDataContext;
022    import com.liferay.portal.kernel.log.Log;
023    import com.liferay.portal.kernel.log.LogFactoryUtil;
024    import com.liferay.portal.kernel.util.GetterUtil;
025    import com.liferay.portal.kernel.util.StringPool;
026    import com.liferay.portal.kernel.util.StringUtil;
027    import com.liferay.portal.kernel.xml.Element;
028    import com.liferay.portal.model.Company;
029    import com.liferay.portal.model.Group;
030    import com.liferay.portal.model.Layout;
031    import com.liferay.portal.model.Portlet;
032    import com.liferay.portal.security.permission.PermissionThreadLocal;
033    import com.liferay.portal.service.CompanyLocalServiceUtil;
034    import com.liferay.portal.service.LayoutLocalServiceUtil;
035    import com.liferay.portal.service.PortletLocalServiceUtil;
036    import com.liferay.portal.util.PortalUtil;
037    import com.liferay.portlet.asset.model.AssetCategory;
038    import com.liferay.portlet.asset.model.AssetVocabulary;
039    import com.liferay.portlet.assetpublisher.util.AssetPublisher;
040    import com.liferay.portlet.assetpublisher.util.AssetPublisherUtil;
041    import com.liferay.portlet.documentlibrary.model.DLFileEntry;
042    import com.liferay.portlet.documentlibrary.model.DLFileEntryType;
043    import com.liferay.portlet.dynamicdatamapping.model.DDMStructure;
044    import com.liferay.portlet.journal.model.JournalArticle;
045    
046    import java.util.ArrayList;
047    import java.util.Enumeration;
048    import java.util.List;
049    
050    import javax.portlet.PortletPreferences;
051    
052    /**
053     * @author Julio Camarero
054     */
055    public class AssetPublisherPortletDataHandler
056            extends DefaultConfigurationPortletDataHandler {
057    
058            public AssetPublisherPortletDataHandler() {
059                    setDataLevel(DataLevel.PORTLET_INSTANCE);
060                    setPublishToLiveByDefault(true);
061            }
062    
063            @Override
064            protected PortletPreferences doProcessExportPortletPreferences(
065                            PortletDataContext portletDataContext, String portletId,
066                            PortletPreferences portletPreferences, Element rootElement)
067                    throws Exception {
068    
069                    return updateExportPortletPreferences(
070                            portletDataContext, portletId, portletPreferences, rootElement);
071            }
072    
073            @Override
074            protected PortletPreferences doProcessImportPortletPreferences(
075                            PortletDataContext portletDataContext, String portletId,
076                            PortletPreferences portletPreferences)
077                    throws Exception {
078    
079                    return updateImportPortletPreferences(
080                            portletDataContext, portletId, portletPreferences);
081            }
082    
083            protected void updateExportClassNameIds(
084                            PortletPreferences portletPreferences, String key)
085                    throws Exception {
086    
087                    String[] oldValues = portletPreferences.getValues(key, null);
088    
089                    if (oldValues == null) {
090                            return;
091                    }
092    
093                    String[] newValues = new String[oldValues.length];
094    
095                    int i = 0;
096    
097                    for (String oldValue : oldValues) {
098                            if (key.equals("anyAssetType") &&
099                                    (oldValue.equals("false") || oldValue.equals("true"))) {
100    
101                                    newValues[i++] = oldValue;
102    
103                                    continue;
104                            }
105    
106                            try {
107                                    long classNameId = GetterUtil.getLong(oldValue);
108    
109                                    String className = PortalUtil.getClassName(classNameId);
110    
111                                    newValues[i++] = className;
112                            }
113                            catch (Exception e) {
114                                    if (_log.isWarnEnabled()) {
115                                            _log.warn(
116                                                    "Unable to get class name ID for class name " +
117                                                            oldValue);
118                                    }
119                            }
120                    }
121    
122                    portletPreferences.setValues(key, newValues);
123            }
124    
125            protected PortletPreferences updateExportPortletPreferences(
126                            PortletDataContext portletDataContext, String portletId,
127                            PortletPreferences portletPreferences, Element rootElement)
128                    throws Exception {
129    
130                    String anyAssetTypeClassName = StringPool.BLANK;
131    
132                    long anyAssetType = GetterUtil.getLong(
133                            portletPreferences.getValue("anyAssetType", null));
134    
135                    if (anyAssetType > 0) {
136                            anyAssetTypeClassName = PortalUtil.getClassName(anyAssetType);
137                    }
138    
139                    Portlet portlet = PortletLocalServiceUtil.getPortletById(
140                            portletDataContext.getCompanyId(), portletId);
141    
142                    Enumeration<String> enu = portletPreferences.getNames();
143    
144                    while (enu.hasMoreElements()) {
145                            String name = enu.nextElement();
146    
147                            String value = GetterUtil.getString(
148                                    portletPreferences.getValue(name, null));
149    
150                            if (name.equals("anyAssetType") || name.equals("classNameIds")) {
151                                    updateExportClassNameIds(portletPreferences, name);
152                            }
153                            else if (name.equals(
154                                                    "anyClassTypeDLFileEntryAssetRendererFactory") ||
155                                             (name.equals("classTypeIds") &&
156                                              anyAssetTypeClassName.equals(
157                                                      DLFileEntry.class.getName())) ||
158                                             name.equals(
159                                                    "classTypeIdsDLFileEntryAssetRendererFactory")) {
160    
161                                    ExportImportHelperUtil.updateExportPortletPreferencesClassPKs(
162                                            portletDataContext, portlet, portletPreferences, name,
163                                            DLFileEntryType.class.getName(), rootElement);
164                            }
165                            else if (name.equals(
166                                                    "anyClassTypeJournalArticleAssetRendererFactory") ||
167                                             (name.equals("classTypeIds") &&
168                                              anyAssetTypeClassName.equals(
169                                                      JournalArticle.class.getName())) ||
170                                             name.equals(
171                                                    "classTypeIdsJournalArticleAssetRendererFactory")) {
172    
173                                    ExportImportHelperUtil.updateExportPortletPreferencesClassPKs(
174                                            portletDataContext, portlet, portletPreferences, name,
175                                            DDMStructure.class.getName(), rootElement);
176                            }
177                            else if (name.equals("assetVocabularyId")) {
178                                    ExportImportHelperUtil.updateExportPortletPreferencesClassPKs(
179                                            portletDataContext, portlet, portletPreferences, name,
180                                            AssetVocabulary.class.getName(), rootElement);
181                            }
182                            else if (name.startsWith("queryName") &&
183                                             value.equalsIgnoreCase("assetCategories")) {
184    
185                                    String index = name.substring(9);
186    
187                                    ExportImportHelperUtil.updateExportPortletPreferencesClassPKs(
188                                            portletDataContext, portlet, portletPreferences,
189                                            "queryValues" + index, AssetCategory.class.getName(),
190                                            rootElement);
191                            }
192                            else if (name.equals("scopeIds")) {
193                                    updateExportScopeIds(
194                                            portletDataContext, portletPreferences, name,
195                                            portletDataContext.getPlid());
196                            }
197                    }
198    
199                    return portletPreferences;
200            }
201    
202            protected void updateExportScopeIds(
203                            PortletDataContext portletDataContext,
204                            PortletPreferences portletPreferences, String key, long plid)
205                    throws Exception {
206    
207                    String[] oldValues = portletPreferences.getValues(key, null);
208    
209                    if (oldValues == null) {
210                            return;
211                    }
212    
213                    Layout layout = LayoutLocalServiceUtil.getLayout(plid);
214    
215                    String companyGroupScopeId =
216                            AssetPublisher.SCOPE_ID_GROUP_PREFIX +
217                                    portletDataContext.getCompanyGroupId();
218    
219                    String[] newValues = new String[oldValues.length];
220    
221                    for (int i = 0; i < oldValues.length; i++) {
222                            String oldValue = oldValues[i];
223    
224                            if (oldValue.startsWith(AssetPublisher.SCOPE_ID_GROUP_PREFIX)) {
225                                    newValues[i] = StringUtil.replace(
226                                            oldValue, companyGroupScopeId,
227                                            "[$COMPANY_GROUP_SCOPE_ID$]");
228                            }
229                            else if (oldValue.startsWith(
230                                                    AssetPublisher.SCOPE_ID_LAYOUT_PREFIX)) {
231    
232                                    // Legacy preferences
233    
234                                    String scopeIdSuffix = oldValue.substring(
235                                            AssetPublisher.SCOPE_ID_LAYOUT_PREFIX.length());
236    
237                                    long scopeIdLayoutId = GetterUtil.getLong(scopeIdSuffix);
238    
239                                    Layout scopeIdLayout = LayoutLocalServiceUtil.getLayout(
240                                            layout.getGroupId(), layout.isPrivateLayout(),
241                                            scopeIdLayoutId);
242    
243                                    newValues[i] =
244                                            AssetPublisher.SCOPE_ID_LAYOUT_UUID_PREFIX +
245                                                    scopeIdLayout.getUuid();
246                            }
247                            else {
248                                    newValues[i] = oldValue;
249                            }
250                    }
251    
252                    portletPreferences.setValues(key, newValues);
253            }
254    
255            protected void updateImportClassNameIds(
256                            PortletPreferences portletPreferences, String key)
257                    throws Exception {
258    
259                    String[] oldValues = portletPreferences.getValues(key, null);
260    
261                    if (oldValues == null) {
262                            return;
263                    }
264    
265                    String[] newValues = new String[oldValues.length];
266    
267                    int i = 0;
268    
269                    for (String oldValue : oldValues) {
270                            if (key.equals("anyAssetType") &&
271                                    (oldValue.equals("false") || oldValue.equals("true"))) {
272    
273                                    newValues[i++] = oldValue;
274    
275                                    continue;
276                            }
277    
278                            try {
279                                    long classNameId = PortalUtil.getClassNameId(oldValue);
280    
281                                    newValues[i++] = String.valueOf(classNameId);
282                            }
283                            catch (Exception e) {
284                                    if (_log.isWarnEnabled()) {
285                                            _log.warn(
286                                                    "Unable to find class name ID for class name " +
287                                                            oldValue);
288                                    }
289                            }
290                    }
291    
292                    portletPreferences.setValues(key, newValues);
293            }
294    
295            protected PortletPreferences updateImportPortletPreferences(
296                            PortletDataContext portletDataContext, String portletId,
297                            PortletPreferences portletPreferences)
298                    throws Exception {
299    
300                    Company company = CompanyLocalServiceUtil.getCompanyById(
301                            portletDataContext.getCompanyId());
302    
303                    Group companyGroup = company.getGroup();
304    
305                    String anyAssetTypeClassName = portletPreferences.getValue(
306                            "anyAssetType", StringPool.BLANK);
307    
308                    Enumeration<String> enu = portletPreferences.getNames();
309    
310                    while (enu.hasMoreElements()) {
311                            String name = enu.nextElement();
312    
313                            String value = GetterUtil.getString(
314                                    portletPreferences.getValue(name, null));
315    
316                            if (name.equals("anyAssetType") || name.equals("classNameIds")) {
317                                    updateImportClassNameIds(portletPreferences, name);
318                            }
319                            else if (name.equals(
320                                                    "anyClassTypeDLFileEntryAssetRendererFactory") ||
321                                             (name.equals("classTypeIds") &&
322                                              anyAssetTypeClassName.equals(
323                                                      DLFileEntry.class.getName())) ||
324                                             name.equals(
325                                                    "classTypeIdsDLFileEntryAssetRendererFactory")) {
326    
327                                    ExportImportHelperUtil.updateImportPortletPreferencesClassPKs(
328                                            portletDataContext, portletPreferences, name,
329                                            DLFileEntryType.class, companyGroup.getGroupId());
330                            }
331                            else if (name.equals(
332                                                    "anyClassTypeJournalArticleAssetRendererFactory") ||
333                                             (name.equals("classTypeIds") &&
334                                              anyAssetTypeClassName.equals(
335                                                      JournalArticle.class.getName())) ||
336                                             name.equals(
337                                                    "classTypeIdsJournalArticleAssetRendererFactory")) {
338    
339                                    ExportImportHelperUtil.updateImportPortletPreferencesClassPKs(
340                                            portletDataContext, portletPreferences, name,
341                                            DDMStructure.class, companyGroup.getGroupId());
342                            }
343                            else if (name.equals("assetVocabularyId")) {
344                                    ExportImportHelperUtil.updateImportPortletPreferencesClassPKs(
345                                            portletDataContext, portletPreferences, name,
346                                            AssetVocabulary.class, companyGroup.getGroupId());
347                            }
348                            else if (name.startsWith("queryName") &&
349                                             value.equalsIgnoreCase("assetCategories")) {
350    
351                                    String index = name.substring(9, name.length());
352    
353                                    ExportImportHelperUtil.updateImportPortletPreferencesClassPKs(
354                                            portletDataContext, portletPreferences,
355                                            "queryValues" + index, AssetCategory.class,
356                                            companyGroup.getGroupId());
357                            }
358                            else if (name.equals("scopeIds")) {
359                                    updateImportScopeIds(
360                                            portletPreferences, name, companyGroup.getGroupId(),
361                                            portletDataContext.getPlid());
362                            }
363                    }
364    
365                    return portletPreferences;
366            }
367    
368            protected void updateImportScopeIds(
369                            PortletPreferences portletPreferences, String key,
370                            long companyGroupId, long plid)
371                    throws Exception {
372    
373                    String[] oldValues = portletPreferences.getValues(key, null);
374    
375                    if (oldValues == null) {
376                            return;
377                    }
378    
379                    Layout layout = LayoutLocalServiceUtil.getLayout(plid);
380    
381                    String companyGroupScopeId =
382                            AssetPublisher.SCOPE_ID_GROUP_PREFIX + companyGroupId;
383    
384                    List<String> newValues = new ArrayList<String>(oldValues.length);
385    
386                    for (String oldValue : oldValues) {
387                            String newValue = StringUtil.replace(
388                                    oldValue, "[$COMPANY_GROUP_SCOPE_ID$]", companyGroupScopeId);
389    
390                            try {
391                                    if (!AssetPublisherUtil.isScopeIdSelectable(
392                                                    PermissionThreadLocal.getPermissionChecker(), newValue,
393                                                    companyGroupId, layout)) {
394    
395                                            continue;
396                                    }
397    
398                                    newValues.add(newValue);
399                            }
400                            catch (NoSuchGroupException nsge) {
401                                    if (_log.isInfoEnabled()) {
402                                            _log.info(
403                                                    "Ignoring scope " + newValue + "because the " +
404                                                            "referenced group was not found");
405                                    }
406                            }
407                    }
408    
409                    portletPreferences.setValues(
410                            key, newValues.toArray(new String[newValues.size()]));
411            }
412    
413            private static Log _log = LogFactoryUtil.getLog(
414                    AssetPublisherPortletDataHandler.class);
415    
416    }