001    /**
002     * Copyright (c) 2000-2012 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.journal.lar;
016    
017    import com.liferay.portal.kernel.lar.BasePortletDataHandler;
018    import com.liferay.portal.kernel.lar.PortletDataContext;
019    import com.liferay.portal.kernel.lar.PortletDataHandlerBoolean;
020    import com.liferay.portal.kernel.lar.PortletDataHandlerControl;
021    import com.liferay.portal.kernel.log.Log;
022    import com.liferay.portal.kernel.log.LogFactoryUtil;
023    import com.liferay.portal.kernel.util.GetterUtil;
024    import com.liferay.portal.kernel.util.MapUtil;
025    import com.liferay.portal.kernel.util.StringPool;
026    import com.liferay.portal.kernel.util.Validator;
027    import com.liferay.portal.kernel.workflow.WorkflowConstants;
028    import com.liferay.portal.kernel.xml.Document;
029    import com.liferay.portal.kernel.xml.Element;
030    import com.liferay.portal.kernel.xml.SAXReaderUtil;
031    import com.liferay.portal.model.Layout;
032    import com.liferay.portal.service.LayoutLocalServiceUtil;
033    import com.liferay.portlet.documentlibrary.lar.DLPortletDataHandlerImpl;
034    import com.liferay.portlet.journal.NoSuchArticleException;
035    import com.liferay.portlet.journal.model.JournalArticle;
036    import com.liferay.portlet.journal.model.JournalTemplate;
037    import com.liferay.portlet.journal.service.JournalArticleLocalServiceUtil;
038    import com.liferay.portlet.journal.service.JournalContentSearchLocalServiceUtil;
039    
040    import java.util.Map;
041    
042    import javax.portlet.PortletPreferences;
043    
044    /**
045     * <p>
046     * Provides the Journal Content portlet export and import functionality, which
047     * is to clone the article, structure, and template referenced in the Journal
048     * Content portlet if the article is associated with the layout's group. Upon
049     * import, a new instance of the corresponding article, structure, and template
050     * will be created or updated. The author of the newly created objects are
051     * determined by the JournalCreationStrategy class defined in
052     * <i>portal.properties</i>.
053     * </p>
054     *
055     * <p>
056     * This <code>PortletDataHandler</code> differs from from
057     * <code>JournalPortletDataHandlerImpl</code> in that it only exports articles
058     * referenced in Journal Content portlets. Articles not displayed in Journal
059     * Content portlets will not be exported unless
060     * <code>JournalPortletDataHandlerImpl</code> is activated.
061     * </p>
062     *
063     * @author Joel Kozikowski
064     * @author Raymond Augé
065     * @author Bruno Farache
066     * @see    com.liferay.portal.kernel.lar.PortletDataHandler
067     * @see    com.liferay.portlet.journal.lar.JournalCreationStrategy
068     * @see    com.liferay.portlet.journal.lar.JournalPortletDataHandlerImpl
069     */
070    public class JournalContentPortletDataHandlerImpl
071            extends BasePortletDataHandler {
072    
073            @Override
074            public PortletDataHandlerControl[] getExportControls() {
075                    return new PortletDataHandlerControl[] {
076                            _selectedArticles, _embeddedAssets
077                    };
078            }
079    
080            @Override
081            public PortletDataHandlerControl[] getExportMetadataControls() {
082                    return new PortletDataHandlerControl[] {
083                             new PortletDataHandlerBoolean(
084                                    _NAMESPACE, "web-content", true,
085                                    JournalPortletDataHandlerImpl.getMetadataControls()),
086                            new PortletDataHandlerBoolean(
087                                    _NAMESPACE, "folders-and-documents", true,
088                                    DLPortletDataHandlerImpl.getMetadataControls()
089                            )
090                    };
091            }
092    
093            @Override
094            public PortletDataHandlerControl[] getImportControls() {
095                    return new PortletDataHandlerControl[] {
096                            _selectedArticles
097                    };
098            }
099    
100            @Override
101            public PortletDataHandlerControl[] getImportMetadataControls() {
102                    return new PortletDataHandlerControl[] {
103                             new PortletDataHandlerBoolean(
104                                    _NAMESPACE, "web-content", true,
105                                    JournalPortletDataHandlerImpl.getMetadataControls()),
106                            new PortletDataHandlerBoolean(
107                                    _NAMESPACE, "folders-and-documents", true,
108                                    DLPortletDataHandlerImpl.getMetadataControls()
109                            )
110                    };
111            }
112    
113            @Override
114            public boolean isAlwaysExportable() {
115                    return _ALWAYS_EXPORTABLE;
116            }
117    
118            @Override
119            public boolean isAlwaysStaged() {
120                    return _ALWAYS_STAGED;
121            }
122    
123            @Override
124            public boolean isPublishToLiveByDefault() {
125                    return _PUBLISH_TO_LIVE_BY_DEFAULT;
126            }
127    
128            @Override
129            protected PortletPreferences doDeleteData(
130                            PortletDataContext portletDataContext, String portletId,
131                            PortletPreferences portletPreferences)
132                    throws Exception {
133    
134                    portletPreferences.setValue("groupId", StringPool.BLANK);
135                    portletPreferences.setValue("articleId", StringPool.BLANK);
136    
137                    return portletPreferences;
138            }
139    
140            @Override
141            protected String doExportData(
142                            PortletDataContext portletDataContext, String portletId,
143                            PortletPreferences portletPreferences)
144                    throws Exception {
145    
146                    portletDataContext.addPermissions(
147                            "com.liferay.portlet.journal",
148                            portletDataContext.getScopeGroupId());
149    
150                    String articleId = portletPreferences.getValue("articleId", null);
151    
152                    if (articleId == null) {
153                            if (_log.isDebugEnabled()) {
154                                    _log.debug(
155                                            "No article id found in preferences of portlet " +
156                                                    portletId);
157                            }
158    
159                            return StringPool.BLANK;
160                    }
161    
162                    long articleGroupId = GetterUtil.getLong(
163                            portletPreferences.getValue("groupId", StringPool.BLANK));
164    
165                    if (articleGroupId <= 0) {
166                            if (_log.isWarnEnabled()) {
167                                    _log.warn(
168                                            "No group id found in preferences of portlet " + portletId);
169                            }
170    
171                            return StringPool.BLANK;
172                    }
173    
174                    long previousScopeGroupId = portletDataContext.getScopeGroupId();
175    
176                    if (articleGroupId != portletDataContext.getScopeGroupId()) {
177                            portletDataContext.setScopeGroupId(articleGroupId);
178                    }
179    
180                    JournalArticle article = null;
181    
182                    try {
183                            article = JournalArticleLocalServiceUtil.getLatestArticle(
184                                    articleGroupId, articleId, WorkflowConstants.STATUS_APPROVED);
185                    }
186                    catch (NoSuchArticleException nsae) {
187                    }
188    
189                    if (article == null) {
190                            try {
191                                    article = JournalArticleLocalServiceUtil.getLatestArticle(
192                                            articleGroupId, articleId,
193                                            WorkflowConstants.STATUS_EXPIRED);
194                            }
195                            catch (NoSuchArticleException nsae) {
196                            }
197                    }
198    
199                    Document document = SAXReaderUtil.createDocument();
200    
201                    Element rootElement = document.addElement("journal-content-data");
202    
203                    if (article == null) {
204                            portletDataContext.setScopeGroupId(previousScopeGroupId);
205    
206                            return document.formattedString();
207                    }
208    
209                    String path = JournalPortletDataHandlerImpl.getArticlePath(
210                            portletDataContext, article);
211    
212                    Element articleElement = rootElement.addElement("article");
213    
214                    articleElement.addAttribute("path", path);
215    
216                    Element dlFileEntryTypesElement = rootElement.addElement(
217                            "dl-file-entry-types");
218                    Element dlFoldersElement = rootElement.addElement("dl-folders");
219                    Element dlFilesElement = rootElement.addElement("dl-file-entries");
220                    Element dlFileRanksElement = rootElement.addElement("dl-file-ranks");
221    
222                    JournalPortletDataHandlerImpl.exportArticle(
223                            portletDataContext, rootElement, rootElement, rootElement,
224                            dlFileEntryTypesElement, dlFoldersElement, dlFilesElement,
225                            dlFileRanksElement, article, false);
226    
227                    portletDataContext.setScopeGroupId(previousScopeGroupId);
228    
229                    return document.formattedString();
230            }
231    
232            @Override
233            protected PortletPreferences doImportData(
234                            PortletDataContext portletDataContext, String portletId,
235                            PortletPreferences portletPreferences, String data)
236                    throws Exception {
237    
238                    portletDataContext.importPermissions(
239                            "com.liferay.portlet.journal",
240                            portletDataContext.getSourceGroupId(),
241                            portletDataContext.getScopeGroupId());
242    
243                    if (Validator.isNull(data)) {
244                            return null;
245                    }
246    
247                    long previousScopeGroupId = portletDataContext.getScopeGroupId();
248    
249                    long importGroupId = GetterUtil.getLong(
250                            portletPreferences.getValue("groupId", null));
251    
252                    if (importGroupId == portletDataContext.getSourceGroupId()) {
253                            portletDataContext.setScopeGroupId(portletDataContext.getGroupId());
254                    }
255    
256                    Document document = SAXReaderUtil.read(data);
257    
258                    Element rootElement = document.getRootElement();
259    
260                    JournalPortletDataHandlerImpl.importReferencedData(
261                            portletDataContext, rootElement);
262    
263                    Element structureElement = rootElement.element("structure");
264    
265                    if (structureElement != null) {
266                            JournalPortletDataHandlerImpl.importStructure(
267                                    portletDataContext, structureElement);
268                    }
269    
270                    Element templateElement = rootElement.element("template");
271    
272                    if (templateElement != null) {
273                            JournalPortletDataHandlerImpl.importTemplate(
274                                    portletDataContext, templateElement);
275                    }
276    
277                    Element articleElement = rootElement.element("article");
278    
279                    if (articleElement != null) {
280                            JournalPortletDataHandlerImpl.importArticle(
281                                    portletDataContext, articleElement);
282                    }
283    
284                    String articleId = portletPreferences.getValue("articleId", null);
285    
286                    if (Validator.isNotNull(articleId) && (articleElement != null)) {
287                            String importedArticleGroupId = articleElement.attributeValue(
288                                    "imported-article-group-id");
289    
290                            if (Validator.isNull(importedArticleGroupId)) {
291                                    importedArticleGroupId = String.valueOf(
292                                            portletDataContext.getScopeGroupId());
293                            }
294    
295                            portletPreferences.setValue("groupId", importedArticleGroupId);
296    
297                            Map<String, String> articleIds =
298                                    (Map<String, String>)portletDataContext.getNewPrimaryKeysMap(
299                                            JournalArticle.class + ".articleId");
300    
301                            articleId = MapUtil.getString(articleIds, articleId, articleId);
302    
303                            portletPreferences.setValue("articleId", articleId);
304    
305                            Layout layout = LayoutLocalServiceUtil.getLayout(
306                                    portletDataContext.getPlid());
307    
308                            JournalContentSearchLocalServiceUtil.updateContentSearch(
309                                    portletDataContext.getScopeGroupId(), layout.isPrivateLayout(),
310                                    layout.getLayoutId(), portletId, articleId, true);
311                    }
312                    else {
313                            portletPreferences.setValue("groupId", StringPool.BLANK);
314                            portletPreferences.setValue("articleId", StringPool.BLANK);
315                    }
316    
317                    String templateId = portletPreferences.getValue("templateId", null);
318    
319                    if (Validator.isNotNull(templateId)) {
320                            Map<String, String> templateIds =
321                                    (Map<String, String>)portletDataContext.getNewPrimaryKeysMap(
322                                            JournalTemplate.class + ".templateId");
323    
324                            templateId = MapUtil.getString(templateIds, templateId, templateId);
325    
326                            portletPreferences.setValue("templateId", templateId);
327                    }
328                    else {
329                            portletPreferences.setValue("templateId", StringPool.BLANK);
330                    }
331    
332                    portletDataContext.setScopeGroupId(previousScopeGroupId);
333    
334                    return portletPreferences;
335            }
336    
337            private static final boolean _ALWAYS_EXPORTABLE = true;
338    
339            private static final boolean _ALWAYS_STAGED = true;
340    
341            private static final String _NAMESPACE = "journal";
342    
343            private static final boolean _PUBLISH_TO_LIVE_BY_DEFAULT = true;
344    
345            private static Log _log = LogFactoryUtil.getLog(
346                    JournalContentPortletDataHandlerImpl.class);
347    
348            private static PortletDataHandlerBoolean _embeddedAssets =
349                    new PortletDataHandlerBoolean(_NAMESPACE, "embedded-assets");
350    
351            private static PortletDataHandlerBoolean _selectedArticles =
352                    new PortletDataHandlerBoolean(
353                            _NAMESPACE, "selected-web-content", true, true);
354    
355    }