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.portal.lar;
016    
017    import com.liferay.portal.LARFileException;
018    import com.liferay.portal.LARTypeException;
019    import com.liferay.portal.LayoutImportException;
020    import com.liferay.portal.LocaleException;
021    import com.liferay.portal.MissingReferenceException;
022    import com.liferay.portal.PortletIdException;
023    import com.liferay.portal.kernel.backgroundtask.BackgroundTaskThreadLocal;
024    import com.liferay.portal.kernel.exception.PortalException;
025    import com.liferay.portal.kernel.exception.SystemException;
026    import com.liferay.portal.kernel.language.LanguageUtil;
027    import com.liferay.portal.kernel.lar.ExportImportHelperUtil;
028    import com.liferay.portal.kernel.lar.ExportImportPathUtil;
029    import com.liferay.portal.kernel.lar.ExportImportThreadLocal;
030    import com.liferay.portal.kernel.lar.ManifestSummary;
031    import com.liferay.portal.kernel.lar.MissingReference;
032    import com.liferay.portal.kernel.lar.MissingReferences;
033    import com.liferay.portal.kernel.lar.PortletDataContext;
034    import com.liferay.portal.kernel.lar.PortletDataContextFactoryUtil;
035    import com.liferay.portal.kernel.lar.PortletDataHandler;
036    import com.liferay.portal.kernel.lar.PortletDataHandlerKeys;
037    import com.liferay.portal.kernel.lar.PortletDataHandlerStatusMessageSenderUtil;
038    import com.liferay.portal.kernel.lar.UserIdStrategy;
039    import com.liferay.portal.kernel.log.Log;
040    import com.liferay.portal.kernel.log.LogFactoryUtil;
041    import com.liferay.portal.kernel.search.Indexer;
042    import com.liferay.portal.kernel.search.IndexerRegistryUtil;
043    import com.liferay.portal.kernel.staging.MergeLayoutPrototypesThreadLocal;
044    import com.liferay.portal.kernel.util.ArrayUtil;
045    import com.liferay.portal.kernel.util.GetterUtil;
046    import com.liferay.portal.kernel.util.LocaleUtil;
047    import com.liferay.portal.kernel.util.MapUtil;
048    import com.liferay.portal.kernel.util.ReleaseInfo;
049    import com.liferay.portal.kernel.util.StringBundler;
050    import com.liferay.portal.kernel.util.StringPool;
051    import com.liferay.portal.kernel.util.StringUtil;
052    import com.liferay.portal.kernel.util.Validator;
053    import com.liferay.portal.kernel.xml.Document;
054    import com.liferay.portal.kernel.xml.DocumentException;
055    import com.liferay.portal.kernel.xml.Element;
056    import com.liferay.portal.kernel.xml.Node;
057    import com.liferay.portal.kernel.xml.SAXReaderUtil;
058    import com.liferay.portal.kernel.zip.ZipReader;
059    import com.liferay.portal.kernel.zip.ZipReaderFactoryUtil;
060    import com.liferay.portal.model.Group;
061    import com.liferay.portal.model.Layout;
062    import com.liferay.portal.model.LayoutConstants;
063    import com.liferay.portal.model.Lock;
064    import com.liferay.portal.model.Portlet;
065    import com.liferay.portal.model.PortletConstants;
066    import com.liferay.portal.model.PortletItem;
067    import com.liferay.portal.model.PortletPreferences;
068    import com.liferay.portal.model.User;
069    import com.liferay.portal.security.permission.PermissionCacheUtil;
070    import com.liferay.portal.service.GroupLocalServiceUtil;
071    import com.liferay.portal.service.LayoutLocalServiceUtil;
072    import com.liferay.portal.service.PortletItemLocalServiceUtil;
073    import com.liferay.portal.service.PortletLocalServiceUtil;
074    import com.liferay.portal.service.PortletPreferencesLocalServiceUtil;
075    import com.liferay.portal.service.ServiceContext;
076    import com.liferay.portal.service.ServiceContextThreadLocal;
077    import com.liferay.portal.service.UserLocalServiceUtil;
078    import com.liferay.portal.service.persistence.PortletPreferencesUtil;
079    import com.liferay.portal.service.persistence.UserUtil;
080    import com.liferay.portal.servlet.filters.cache.CacheUtil;
081    import com.liferay.portal.util.PortalUtil;
082    import com.liferay.portal.util.PortletKeys;
083    import com.liferay.portlet.PortletPreferencesFactoryUtil;
084    import com.liferay.portlet.PortletPreferencesImpl;
085    import com.liferay.portlet.asset.NoSuchTagException;
086    import com.liferay.portlet.asset.model.AssetCategory;
087    import com.liferay.portlet.asset.model.AssetCategoryConstants;
088    import com.liferay.portlet.asset.model.AssetEntry;
089    import com.liferay.portlet.asset.model.AssetLink;
090    import com.liferay.portlet.asset.model.AssetTag;
091    import com.liferay.portlet.asset.model.AssetTagConstants;
092    import com.liferay.portlet.asset.model.AssetVocabulary;
093    import com.liferay.portlet.asset.service.AssetCategoryLocalServiceUtil;
094    import com.liferay.portlet.asset.service.AssetEntryLocalServiceUtil;
095    import com.liferay.portlet.asset.service.AssetLinkLocalServiceUtil;
096    import com.liferay.portlet.asset.service.AssetTagLocalServiceUtil;
097    import com.liferay.portlet.asset.service.AssetVocabularyLocalServiceUtil;
098    import com.liferay.portlet.asset.service.persistence.AssetCategoryUtil;
099    import com.liferay.portlet.asset.service.persistence.AssetTagUtil;
100    import com.liferay.portlet.asset.service.persistence.AssetVocabularyUtil;
101    import com.liferay.portlet.expando.NoSuchTableException;
102    import com.liferay.portlet.expando.model.ExpandoColumn;
103    import com.liferay.portlet.expando.model.ExpandoTable;
104    import com.liferay.portlet.expando.service.ExpandoColumnLocalServiceUtil;
105    import com.liferay.portlet.expando.service.ExpandoTableLocalServiceUtil;
106    import com.liferay.portlet.expando.util.ExpandoConverterUtil;
107    import com.liferay.portlet.journalcontent.util.JournalContentUtil;
108    import com.liferay.portlet.messageboards.model.MBMessage;
109    import com.liferay.portlet.ratings.model.RatingsEntry;
110    
111    import java.io.File;
112    import java.io.Serializable;
113    
114    import java.util.ArrayList;
115    import java.util.Enumeration;
116    import java.util.HashMap;
117    import java.util.List;
118    import java.util.Locale;
119    import java.util.Map;
120    
121    import org.apache.commons.lang.time.StopWatch;
122    
123    /**
124     * @author Brian Wing Shun Chan
125     * @author Joel Kozikowski
126     * @author Charles May
127     * @author Raymond Aug??
128     * @author Jorge Ferrer
129     * @author Bruno Farache
130     * @author Zsigmond Rab
131     * @author Douglas Wong
132     * @author Mate Thurzo
133     */
134    public class PortletImporter {
135    
136            public String importPortletData(
137                            PortletDataContext portletDataContext, String portletId,
138                            PortletPreferences portletPreferences, Element portletDataElement)
139                    throws Exception {
140    
141                    Portlet portlet = PortletLocalServiceUtil.getPortletById(
142                            portletDataContext.getCompanyId(), portletId);
143    
144                    if (portlet == null) {
145                            if (_log.isDebugEnabled()) {
146                                    _log.debug(
147                                            "Do not import portlet data for " + portletId +
148                                                    " because the portlet does not exist");
149                            }
150    
151                            return null;
152                    }
153    
154                    PortletDataHandler portletDataHandler =
155                            portlet.getPortletDataHandlerInstance();
156    
157                    if ((portletDataHandler == null) ||
158                            portletDataHandler.isDataPortletInstanceLevel()) {
159    
160                            if (_log.isDebugEnabled()) {
161                                    _log.debug(
162                                            "Do not import portlet data for " + portletId +
163                                                    " because the portlet does not have a " +
164                                                            "PortletDataHandler");
165                            }
166    
167                            return null;
168                    }
169    
170                    if (_log.isDebugEnabled()) {
171                            _log.debug("Importing data for " + portletId);
172                    }
173    
174                    PortletPreferencesImpl portletPreferencesImpl = null;
175    
176                    if (portletPreferences != null) {
177                            portletPreferencesImpl =
178                                    (PortletPreferencesImpl)
179                                            PortletPreferencesFactoryUtil.fromDefaultXML(
180                                                    portletPreferences.getPreferences());
181                    }
182    
183                    String portletData = portletDataContext.getZipEntryAsString(
184                            portletDataElement.attributeValue("path"));
185    
186                    if (Validator.isNull(portletData)) {
187                            return null;
188                    }
189    
190                    portletPreferencesImpl =
191                            (PortletPreferencesImpl)portletDataHandler.importData(
192                                    portletDataContext, portletId, portletPreferencesImpl,
193                                    portletData);
194    
195                    if (portletPreferencesImpl == null) {
196                            return null;
197                    }
198    
199                    return PortletPreferencesFactoryUtil.toXML(portletPreferencesImpl);
200            }
201    
202            public void importPortletInfo(
203                            long userId, long plid, long groupId, String portletId,
204                            Map<String, String[]> parameterMap, File file)
205                    throws Exception {
206    
207                    try {
208                            ExportImportThreadLocal.setPortletImportInProcess(true);
209    
210                            doImportPortletInfo(
211                                    userId, plid, groupId, portletId, parameterMap, file);
212                    }
213                    finally {
214                            ExportImportThreadLocal.setPortletImportInProcess(false);
215    
216                            CacheUtil.clearCache();
217                            JournalContentUtil.clearCache();
218                            PermissionCacheUtil.clearCache();
219                    }
220            }
221    
222            public MissingReferences validateFile(
223                            long userId, long plid, long groupId, String portletId,
224                            Map<String, String[]> parameterMap, File file)
225                    throws Exception {
226    
227                    ZipReader zipReader = null;
228    
229                    try {
230                            ExportImportThreadLocal.setPortletValidationInProcess(true);
231    
232                            Layout layout = LayoutLocalServiceUtil.getLayout(plid);
233    
234                            zipReader = ZipReaderFactoryUtil.getZipReader(file);
235    
236                            PortletDataContext portletDataContext =
237                                    PortletDataContextFactoryUtil.createImportPortletDataContext(
238                                            layout.getCompanyId(), groupId, parameterMap, null,
239                                            zipReader);
240    
241                            validateFile(portletDataContext, portletId);
242    
243                            MissingReferences missingReferences =
244                                    ExportImportHelperUtil.validateMissingReferences(
245                                            userId, groupId, parameterMap, file);
246    
247                            Map<String, MissingReference> dependencyMissingReferences =
248                                    missingReferences.getDependencyMissingReferences();
249    
250                            if (!dependencyMissingReferences.isEmpty()) {
251                                    throw new MissingReferenceException(missingReferences);
252                            }
253    
254                            return missingReferences;
255                    }
256                    finally {
257                            ExportImportThreadLocal.setPortletValidationInProcess(false);
258    
259                            if (zipReader != null) {
260                                    zipReader.close();
261                            }
262                    }
263            }
264    
265            protected void deletePortletData(
266                            PortletDataContext portletDataContext, String portletId, long plid)
267                    throws Exception {
268    
269                    long ownerId = PortletKeys.PREFS_OWNER_ID_DEFAULT;
270                    int ownerType = PortletKeys.PREFS_OWNER_TYPE_LAYOUT;
271    
272                    PortletPreferences portletPreferences =
273                            PortletPreferencesUtil.fetchByO_O_P_P(
274                                    ownerId, ownerType, plid, portletId);
275    
276                    if (portletPreferences == null) {
277                            portletPreferences =
278                                    new com.liferay.portal.model.impl.PortletPreferencesImpl();
279                    }
280    
281                    String xml = deletePortletData(
282                            portletDataContext, portletId, portletPreferences);
283    
284                    if (xml != null) {
285                            PortletPreferencesLocalServiceUtil.updatePreferences(
286                                    ownerId, ownerType, plid, portletId, xml);
287                    }
288            }
289    
290            protected String deletePortletData(
291                            PortletDataContext portletDataContext, String portletId,
292                            PortletPreferences portletPreferences)
293                    throws Exception {
294    
295                    Portlet portlet = PortletLocalServiceUtil.getPortletById(
296                            portletDataContext.getCompanyId(), portletId);
297    
298                    if (portlet == null) {
299                            if (_log.isDebugEnabled()) {
300                                    _log.debug(
301                                            "Do not delete portlet data for " + portletId +
302                                                    " because the portlet does not exist");
303                            }
304    
305                            return null;
306                    }
307    
308                    PortletDataHandler portletDataHandler =
309                            portlet.getPortletDataHandlerInstance();
310    
311                    if (portletDataHandler == null) {
312                            if (_log.isDebugEnabled()) {
313                                    _log.debug(
314                                            "Do not delete portlet data for " + portletId +
315                                                    " because the portlet does not have a " +
316                                                            "PortletDataHandler");
317                            }
318    
319                            return null;
320                    }
321    
322                    if (_log.isDebugEnabled()) {
323                            _log.debug("Deleting data for " + portletId);
324                    }
325    
326                    PortletPreferencesImpl portletPreferencesImpl =
327                            (PortletPreferencesImpl)
328                                    PortletPreferencesFactoryUtil.fromDefaultXML(
329                                            portletPreferences.getPreferences());
330    
331                    try {
332                            portletPreferencesImpl =
333                                    (PortletPreferencesImpl)portletDataHandler.deleteData(
334                                            portletDataContext, portletId, portletPreferencesImpl);
335                    }
336                    finally {
337                            portletDataContext.setGroupId(portletDataContext.getScopeGroupId());
338                    }
339    
340                    if (portletPreferencesImpl == null) {
341                            return null;
342                    }
343    
344                    return PortletPreferencesFactoryUtil.toXML(portletPreferencesImpl);
345            }
346    
347            protected void doImportPortletInfo(
348                            long userId, long plid, long groupId, String portletId,
349                            Map<String, String[]> parameterMap, File file)
350                    throws Exception {
351    
352                    boolean deletePortletData = MapUtil.getBoolean(
353                            parameterMap, PortletDataHandlerKeys.DELETE_PORTLET_DATA);
354                    boolean importPermissions = MapUtil.getBoolean(
355                            parameterMap, PortletDataHandlerKeys.PERMISSIONS);
356                    String userIdStrategyString = MapUtil.getString(
357                            parameterMap, PortletDataHandlerKeys.USER_ID_STRATEGY);
358    
359                    StopWatch stopWatch = new StopWatch();
360    
361                    stopWatch.start();
362    
363                    User user = UserUtil.findByPrimaryKey(userId);
364    
365                    ServiceContext serviceContext =
366                            ServiceContextThreadLocal.getServiceContext();
367    
368                    if (serviceContext == null) {
369                            serviceContext = new ServiceContext();
370    
371                            serviceContext.setCompanyId(user.getCompanyId());
372                            serviceContext.setSignedIn(false);
373                            serviceContext.setUserId(userId);
374    
375                            ServiceContextThreadLocal.pushServiceContext(serviceContext);
376                    }
377    
378                    Layout layout = LayoutLocalServiceUtil.getLayout(plid);
379    
380                    UserIdStrategy userIdStrategy = getUserIdStrategy(
381                            user, userIdStrategyString);
382    
383                    ZipReader zipReader = ZipReaderFactoryUtil.getZipReader(file);
384    
385                    PortletDataContext portletDataContext =
386                            PortletDataContextFactoryUtil.createImportPortletDataContext(
387                                    layout.getCompanyId(), groupId, parameterMap, userIdStrategy,
388                                    zipReader);
389    
390                    portletDataContext.setPortetDataContextListener(
391                            new PortletDataContextListenerImpl(portletDataContext));
392    
393                    portletDataContext.setPlid(plid);
394                    portletDataContext.setPrivateLayout(layout.isPrivateLayout());
395                    portletDataContext.setRootPortletId(
396                            PortletConstants.getRootPortletId(portletId));
397    
398                    // Manifest
399    
400                    validateFile(portletDataContext, portletId);
401    
402                    ManifestSummary manifestSummary =
403                            ExportImportHelperUtil.getManifestSummary(
404                                    userId, groupId, parameterMap, file);
405    
406                    if (BackgroundTaskThreadLocal.hasBackgroundTask()) {
407                            PortletDataHandlerStatusMessageSenderUtil.sendStatusMessage(
408                                    "portlet", portletId, manifestSummary);
409                    }
410    
411                    portletDataContext.setManifestSummary(manifestSummary);
412    
413                    // Company id
414    
415                    long sourceCompanyId = GetterUtil.getLong(
416                            _headerElement.attributeValue("company-id"));
417    
418                    portletDataContext.setSourceCompanyId(sourceCompanyId);
419    
420                    // Company group id
421    
422                    long sourceCompanyGroupId = GetterUtil.getLong(
423                            _headerElement.attributeValue("company-group-id"));
424    
425                    portletDataContext.setSourceCompanyGroupId(sourceCompanyGroupId);
426    
427                    // Group id
428    
429                    long sourceGroupId = GetterUtil.getLong(
430                            _headerElement.attributeValue("group-id"));
431    
432                    portletDataContext.setSourceGroupId(sourceGroupId);
433    
434                    // User personal site group id
435    
436                    long sourceUserPersonalSiteGroupId = GetterUtil.getLong(
437                            _headerElement.attributeValue("user-personal-site-group-id"));
438    
439                    portletDataContext.setSourceUserPersonalSiteGroupId(
440                            sourceUserPersonalSiteGroupId);
441    
442                    Element missingReferencesElement = _rootElement.element(
443                            "missing-references");
444    
445                    if (missingReferencesElement != null) {
446                            portletDataContext.setMissingReferencesElement(
447                                    missingReferencesElement);
448                    }
449    
450                    // Deletion system events
451    
452                    _deletionSystemEventImporter.importDeletionSystemEvents(
453                            portletDataContext);
454    
455                    // Read asset categories, asset tags, comments, locks, and ratings
456                    // entries to make them available to the data handlers through the
457                    // portlet data context
458    
459                    Element portletElement = null;
460    
461                    try {
462                            portletElement = _rootElement.element("portlet");
463    
464                            Document portletDocument = SAXReaderUtil.read(
465                                    portletDataContext.getZipEntryAsString(
466                                            portletElement.attributeValue("path")));
467    
468                            portletElement = portletDocument.getRootElement();
469                    }
470                    catch (DocumentException de) {
471                            throw new SystemException(de);
472                    }
473    
474                    LayoutCache layoutCache = new LayoutCache();
475    
476                    if (importPermissions) {
477                            _permissionImporter.checkRoles(
478                                    layoutCache, layout.getCompanyId(), groupId, userId,
479                                    portletElement);
480    
481                            _permissionImporter.readPortletDataPermissions(portletDataContext);
482                    }
483    
484                    readAssetCategories(portletDataContext);
485                    readAssetTags(portletDataContext);
486                    readComments(portletDataContext);
487                    readExpandoTables(portletDataContext);
488                    readLocks(portletDataContext);
489                    readRatingsEntries(portletDataContext);
490    
491                    // Delete portlet data
492    
493                    if (_log.isDebugEnabled()) {
494                            _log.debug("Deleting portlet data");
495                    }
496    
497                    if (deletePortletData) {
498                            deletePortletData(portletDataContext, portletId, plid);
499                    }
500    
501                    Element portletDataElement = portletElement.element("portlet-data");
502    
503                    Map<String, Boolean> importPortletControlsMap =
504                            LayoutImporter.getImportPortletControlsMap(
505                                    layout.getCompanyId(), portletId, parameterMap,
506                                    portletDataElement, manifestSummary);
507    
508                    try {
509    
510                            // Portlet preferences
511    
512                            importPortletPreferences(
513                                    portletDataContext, layout.getCompanyId(), groupId, layout,
514                                    portletId, portletElement, true,
515                                    importPortletControlsMap.get(
516                                            PortletDataHandlerKeys.PORTLET_ARCHIVED_SETUPS),
517                                    importPortletControlsMap.get(
518                                            PortletDataHandlerKeys.PORTLET_DATA),
519                                    importPortletControlsMap.get(
520                                            PortletDataHandlerKeys.PORTLET_SETUP),
521                                    importPortletControlsMap.get(
522                                            PortletDataHandlerKeys.PORTLET_USER_PREFERENCES));
523    
524                            // Portlet data
525    
526                            if (importPortletControlsMap.get(
527                                            PortletDataHandlerKeys.PORTLET_DATA)) {
528    
529                                    if (_log.isDebugEnabled()) {
530                                            _log.debug("Importing portlet data");
531                                    }
532    
533                                    importPortletData(
534                                            portletDataContext, portletId, plid, portletDataElement);
535                            }
536                    }
537                    finally {
538                            resetPortletScope(portletDataContext, groupId);
539                    }
540    
541                    // Portlet permissions
542    
543                    if (importPermissions) {
544                            if (_log.isDebugEnabled()) {
545                                    _log.debug("Importing portlet permissions");
546                            }
547    
548                            _permissionImporter.importPortletPermissions(
549                                    layoutCache, layout.getCompanyId(), groupId, userId, layout,
550                                    portletElement, portletId);
551    
552                            if (userId > 0) {
553                                    Indexer indexer = IndexerRegistryUtil.nullSafeGetIndexer(
554                                            User.class);
555    
556                                    indexer.reindex(userId);
557                            }
558                    }
559    
560                    // Asset links
561    
562                    if (_log.isDebugEnabled()) {
563                            _log.debug("Importing asset links");
564                    }
565    
566                    readAssetLinks(portletDataContext);
567    
568                    if (_log.isInfoEnabled()) {
569                            _log.info("Importing portlet takes " + stopWatch.getTime() + " ms");
570                    }
571    
572                    zipReader.close();
573    
574                    ExportImportHelperUtil.reindex(portletDataContext, userId);
575            }
576    
577            protected String getAssetCategoryName(
578                            String uuid, long groupId, long parentCategoryId, String name,
579                            long vocabularyId, int count)
580                    throws Exception {
581    
582                    AssetCategory assetCategory = AssetCategoryUtil.fetchByG_P_N_V_First(
583                            groupId, parentCategoryId, name, vocabularyId, null);
584    
585                    if ((assetCategory == null) ||
586                            (Validator.isNotNull(uuid) &&
587                             uuid.equals(assetCategory.getUuid()))) {
588    
589                            return name;
590                    }
591    
592                    name = StringUtil.appendParentheticalSuffix(name, count);
593    
594                    return getAssetCategoryName(
595                            uuid, groupId, parentCategoryId, name, vocabularyId, ++count);
596            }
597    
598            protected String getAssetCategoryPath(
599                    PortletDataContext portletDataContext, long assetCategoryId) {
600    
601                    StringBundler sb = new StringBundler(6);
602    
603                    sb.append(ExportImportPathUtil.getRootPath(portletDataContext));
604                    sb.append("/categories/");
605                    sb.append(assetCategoryId);
606                    sb.append(".xml");
607    
608                    return sb.toString();
609            }
610    
611            protected Map<Locale, String> getAssetCategoryTitleMap(
612                            long groupId, AssetCategory assetCategory, String name)
613                    throws PortalException, SystemException {
614    
615                    Map<Locale, String> titleMap = assetCategory.getTitleMap();
616    
617                    if (titleMap == null) {
618                            titleMap = new HashMap<Locale, String>();
619                    }
620    
621                    titleMap.put(PortalUtil.getSiteDefaultLocale(groupId), name);
622    
623                    return titleMap;
624            }
625    
626            protected String getAssetVocabularyName(
627                            String uuid, long groupId, String name, int count)
628                    throws Exception {
629    
630                    AssetVocabulary assetVocabulary = AssetVocabularyUtil.fetchByG_N(
631                            groupId, name);
632    
633                    if (assetVocabulary == null) {
634                            return name;
635                    }
636    
637                    if (Validator.isNotNull(uuid) &&
638                            uuid.equals(assetVocabulary.getUuid())) {
639    
640                            return name;
641                    }
642    
643                    name = StringUtil.appendParentheticalSuffix(name, count);
644    
645                    return getAssetVocabularyName(uuid, groupId, name, ++count);
646            }
647    
648            protected Map<Locale, String> getAssetVocabularyTitleMap(
649                            long groupId, AssetVocabulary assetVocabulary, String name)
650                    throws PortalException, SystemException {
651    
652                    Map<Locale, String> titleMap = assetVocabulary.getTitleMap();
653    
654                    if (titleMap == null) {
655                            titleMap = new HashMap<Locale, String>();
656                    }
657    
658                    titleMap.put(PortalUtil.getSiteDefaultLocale(groupId), name);
659    
660                    return titleMap;
661            }
662    
663            protected UserIdStrategy getUserIdStrategy(
664                    User user, String userIdStrategy) {
665    
666                    if (UserIdStrategy.ALWAYS_CURRENT_USER_ID.equals(userIdStrategy)) {
667                            return new AlwaysCurrentUserIdStrategy(user);
668                    }
669    
670                    return new CurrentUserIdStrategy(user);
671            }
672    
673            protected void importAssetCategory(
674                            PortletDataContext portletDataContext,
675                            Map<Long, Long> assetVocabularyPKs,
676                            Map<Long, Long> assetCategoryPKs,
677                            Map<String, String> assetCategoryUuids,
678                            Element assetCategoryElement, AssetCategory assetCategory)
679                    throws Exception {
680    
681                    long userId = portletDataContext.getUserId(assetCategory.getUserUuid());
682                    long groupId = portletDataContext.getGroupId();
683                    long assetVocabularyId = MapUtil.getLong(
684                            assetVocabularyPKs, assetCategory.getVocabularyId(),
685                            assetCategory.getVocabularyId());
686                    long parentAssetCategoryId = MapUtil.getLong(
687                            assetCategoryPKs, assetCategory.getParentCategoryId(),
688                            assetCategory.getParentCategoryId());
689    
690                    if ((parentAssetCategoryId !=
691                                    AssetCategoryConstants.DEFAULT_PARENT_CATEGORY_ID) &&
692                            (parentAssetCategoryId == assetCategory.getParentCategoryId())) {
693    
694                            String path = getAssetCategoryPath(
695                                    portletDataContext, parentAssetCategoryId);
696    
697                            AssetCategory parentAssetCategory =
698                                    (AssetCategory)portletDataContext.getZipEntryAsObject(path);
699    
700                            Node parentCategoryNode =
701                                    assetCategoryElement.getParent().selectSingleNode(
702                                            "./category[@path='" + path + "']");
703    
704                            if (parentCategoryNode != null) {
705                                    importAssetCategory(
706                                            portletDataContext, assetVocabularyPKs, assetCategoryPKs,
707                                            assetCategoryUuids, (Element)parentCategoryNode,
708                                            parentAssetCategory);
709    
710                                    parentAssetCategoryId = MapUtil.getLong(
711                                            assetCategoryPKs, assetCategory.getParentCategoryId(),
712                                            assetCategory.getParentCategoryId());
713                            }
714                    }
715    
716                    ServiceContext serviceContext = new ServiceContext();
717    
718                    serviceContext.setAddGroupPermissions(true);
719                    serviceContext.setAddGuestPermissions(true);
720                    serviceContext.setCreateDate(assetCategory.getCreateDate());
721                    serviceContext.setModifiedDate(assetCategory.getModifiedDate());
722                    serviceContext.setScopeGroupId(portletDataContext.getScopeGroupId());
723    
724                    AssetCategory importedAssetCategory = null;
725    
726                    if ((parentAssetCategoryId !=
727                                    AssetCategoryConstants.DEFAULT_PARENT_CATEGORY_ID) &&
728                            (AssetCategoryUtil.fetchByPrimaryKey(parentAssetCategoryId) ==
729                                    null)) {
730    
731                            _log.error(
732                                    "Could not find the parent category for category " +
733                                            assetCategory.getCategoryId());
734    
735                            return;
736                    }
737    
738                    List<Element> propertyElements = assetCategoryElement.elements(
739                            "property");
740    
741                    String[] properties = new String[propertyElements.size()];
742    
743                    for (int i = 0; i < propertyElements.size(); i++) {
744                            Element propertyElement = propertyElements.get(i);
745    
746                            String key = propertyElement.attributeValue("key");
747                            String value = propertyElement.attributeValue("value");
748    
749                            properties[i] = key.concat(
750                                    AssetCategoryConstants.PROPERTY_KEY_VALUE_SEPARATOR).concat(
751                                            value);
752                    }
753    
754                    AssetCategory existingAssetCategory = AssetCategoryUtil.fetchByUUID_G(
755                            assetCategory.getUuid(), groupId);
756    
757                    if (existingAssetCategory == null) {
758                            existingAssetCategory = AssetCategoryUtil.fetchByUUID_G(
759                                    assetCategory.getUuid(),
760                                    portletDataContext.getCompanyGroupId());
761                    }
762    
763                    if (existingAssetCategory == null) {
764                            existingAssetCategory = AssetCategoryUtil.fetchByG_P_N_V_First(
765                                    groupId, parentAssetCategoryId, assetCategory.getName(),
766                                    assetVocabularyId, null);
767                    }
768    
769                    if (existingAssetCategory == null) {
770                            serviceContext.setUuid(assetCategory.getUuid());
771    
772                            importedAssetCategory = AssetCategoryLocalServiceUtil.addCategory(
773                                    userId, parentAssetCategoryId,
774                                    getAssetCategoryTitleMap(
775                                            groupId, assetCategory, assetCategory.getName()),
776                                    assetCategory.getDescriptionMap(), assetVocabularyId,
777                                    properties, serviceContext);
778                    }
779                    else if (portletDataContext.isCompanyStagedGroupedModel(
780                                            existingAssetCategory)) {
781    
782                            return;
783                    }
784                    else {
785                            String name = getAssetCategoryName(
786                                    existingAssetCategory.getUuid(), groupId, parentAssetCategoryId,
787                                    assetCategory.getName(), assetVocabularyId, 2);
788    
789                            if (!Validator.equals(existingAssetCategory.getName(), name)) {
790                                    List<AssetEntry> assetCategoryAssetEntries =
791                                            AssetEntryLocalServiceUtil.getAssetCategoryAssetEntries(
792                                                    existingAssetCategory.getCategoryId());
793    
794                                    for (AssetEntry assetCategoryAssetEntry :
795                                                    assetCategoryAssetEntries) {
796    
797                                            String className = PortalUtil.getClassName(
798                                                    assetCategoryAssetEntry.getClassNameId());
799    
800                                            Map<Long, Long> newPrimaryKeysMap =
801                                                    (Map<Long, Long>)
802                                                            portletDataContext.getNewPrimaryKeysMap(className);
803    
804                                            // Force reindex
805    
806                                            newPrimaryKeysMap.put(
807                                                    assetCategoryAssetEntry.getClassPK(),
808                                                    assetCategoryAssetEntry.getClassPK());
809                                    }
810                            }
811    
812                            importedAssetCategory =
813                                    AssetCategoryLocalServiceUtil.updateCategory(
814                                            userId, existingAssetCategory.getCategoryId(),
815                                            parentAssetCategoryId,
816                                            getAssetCategoryTitleMap(groupId, assetCategory, name),
817                                            assetCategory.getDescriptionMap(), assetVocabularyId,
818                                            properties, serviceContext);
819    
820                            String assetCategoryUuid = assetCategory.getUuid();
821    
822                            if (!assetCategoryUuid.equals(importedAssetCategory.getUuid())) {
823                                    importedAssetCategory.setUuid(assetCategory.getUuid());
824    
825                                    AssetCategoryLocalServiceUtil.updateAssetCategory(
826                                            importedAssetCategory);
827                            }
828                    }
829    
830                    assetCategoryPKs.put(
831                            assetCategory.getCategoryId(),
832                            importedAssetCategory.getCategoryId());
833    
834                    assetCategoryUuids.put(
835                            assetCategory.getUuid(), importedAssetCategory.getUuid());
836    
837                    portletDataContext.importPermissions(
838                            AssetCategory.class, assetCategory.getCategoryId(),
839                            importedAssetCategory.getCategoryId());
840            }
841    
842            protected void importAssetTag(
843                            PortletDataContext portletDataContext, Map<Long, Long> assetTagPKs,
844                            Element assetTagElement, AssetTag assetTag)
845                    throws PortalException, SystemException {
846    
847                    long userId = portletDataContext.getUserId(assetTag.getUserUuid());
848    
849                    ServiceContext serviceContext = new ServiceContext();
850    
851                    serviceContext.setAddGroupPermissions(true);
852                    serviceContext.setAddGuestPermissions(true);
853                    serviceContext.setCreateDate(assetTag.getCreateDate());
854                    serviceContext.setModifiedDate(assetTag.getModifiedDate());
855                    serviceContext.setScopeGroupId(portletDataContext.getScopeGroupId());
856    
857                    AssetTag importedAssetTag = null;
858    
859                    List<Element> propertyElements = assetTagElement.elements("property");
860    
861                    String[] properties = new String[propertyElements.size()];
862    
863                    for (int i = 0; i < propertyElements.size(); i++) {
864                            Element propertyElement = propertyElements.get(i);
865    
866                            String key = propertyElement.attributeValue("key");
867                            String value = propertyElement.attributeValue("value");
868    
869                            properties[i] = key.concat(
870                                    AssetTagConstants.PROPERTY_KEY_VALUE_SEPARATOR).concat(value);
871                    }
872    
873                    AssetTag existingAssetTag = null;
874    
875                    try {
876                            existingAssetTag = AssetTagUtil.findByG_N(
877                                    portletDataContext.getScopeGroupId(), assetTag.getName());
878                    }
879                    catch (NoSuchTagException nste) {
880                            if (_log.isDebugEnabled()) {
881                                    StringBundler sb = new StringBundler(5);
882    
883                                    sb.append("No AssetTag exists with the key {groupId=");
884                                    sb.append(portletDataContext.getScopeGroupId());
885                                    sb.append(", name=");
886                                    sb.append(assetTag.getName());
887                                    sb.append("}");
888    
889                                    _log.debug(sb.toString());
890                            }
891                    }
892    
893                    try {
894                            if (existingAssetTag == null) {
895                                    importedAssetTag = AssetTagLocalServiceUtil.addTag(
896                                            userId, assetTag.getName(), properties, serviceContext);
897                            }
898                            else {
899                                    importedAssetTag = AssetTagLocalServiceUtil.updateTag(
900                                            userId, existingAssetTag.getTagId(), assetTag.getName(),
901                                            properties, serviceContext);
902                            }
903    
904                            assetTagPKs.put(assetTag.getTagId(), importedAssetTag.getTagId());
905    
906                            portletDataContext.importPermissions(
907                                    AssetTag.class, assetTag.getTagId(),
908                                    importedAssetTag.getTagId());
909                    }
910                    catch (NoSuchTagException nste) {
911                            _log.error(
912                                    "Could not find the parent category for category " +
913                                            assetTag.getTagId());
914                    }
915            }
916    
917            protected void importAssetVocabulary(
918                            PortletDataContext portletDataContext,
919                            Map<Long, Long> assetVocabularyPKs, Element assetVocabularyElement,
920                            AssetVocabulary assetVocabulary)
921                    throws Exception {
922    
923                    long userId = portletDataContext.getUserId(
924                            assetVocabulary.getUserUuid());
925                    long groupId = portletDataContext.getScopeGroupId();
926    
927                    ServiceContext serviceContext = new ServiceContext();
928    
929                    serviceContext.setAddGroupPermissions(true);
930                    serviceContext.setAddGuestPermissions(true);
931                    serviceContext.setCreateDate(assetVocabulary.getCreateDate());
932                    serviceContext.setModifiedDate(assetVocabulary.getModifiedDate());
933                    serviceContext.setScopeGroupId(portletDataContext.getScopeGroupId());
934    
935                    AssetVocabulary importedAssetVocabulary = null;
936    
937                    AssetVocabulary existingAssetVocabulary =
938                            AssetVocabularyUtil.fetchByUUID_G(
939                                    assetVocabulary.getUuid(), groupId);
940    
941                    if (existingAssetVocabulary == null) {
942                            existingAssetVocabulary = AssetVocabularyUtil.fetchByUUID_G(
943                                    assetVocabulary.getUuid(),
944                                    portletDataContext.getCompanyGroupId());
945                    }
946    
947                    if (existingAssetVocabulary == null) {
948                            existingAssetVocabulary = AssetVocabularyUtil.fetchByG_N(
949                                    groupId, assetVocabulary.getName());
950                    }
951    
952                    if (existingAssetVocabulary == null) {
953                            serviceContext.setUuid(assetVocabulary.getUuid());
954    
955                            importedAssetVocabulary =
956                                    AssetVocabularyLocalServiceUtil.addVocabulary(
957                                            userId, StringPool.BLANK,
958                                            getAssetVocabularyTitleMap(
959                                                    groupId, assetVocabulary, assetVocabulary.getName()),
960                                            assetVocabulary.getDescriptionMap(),
961                                            assetVocabulary.getSettings(), serviceContext);
962                    }
963                    else if (portletDataContext.isCompanyStagedGroupedModel(
964                                            existingAssetVocabulary)) {
965    
966                            return;
967                    }
968                    else {
969                            String name = getAssetVocabularyName(
970                                    existingAssetVocabulary.getUuid(), groupId,
971                                    assetVocabulary.getName(), 2);
972    
973                            importedAssetVocabulary =
974                                    AssetVocabularyLocalServiceUtil.updateVocabulary(
975                                            existingAssetVocabulary.getVocabularyId(), StringPool.BLANK,
976                                            getAssetVocabularyTitleMap(groupId, assetVocabulary, name),
977                                            assetVocabulary.getDescriptionMap(),
978                                            assetVocabulary.getSettings(), serviceContext);
979    
980                            String assetVocabularyUuid = assetVocabulary.getUuid();
981    
982                            if (!assetVocabularyUuid.equals(
983                                            importedAssetVocabulary.getUuid())) {
984    
985                                    importedAssetVocabulary.setUuid(assetVocabulary.getUuid());
986    
987                                    AssetVocabularyLocalServiceUtil.updateAssetVocabulary(
988                                            importedAssetVocabulary);
989                            }
990                    }
991    
992                    assetVocabularyPKs.put(
993                            assetVocabulary.getVocabularyId(),
994                            importedAssetVocabulary.getVocabularyId());
995    
996                    portletDataContext.importPermissions(
997                            AssetVocabulary.class, assetVocabulary.getVocabularyId(),
998                            importedAssetVocabulary.getVocabularyId());
999            }
1000    
1001            protected void importPortletData(
1002                            PortletDataContext portletDataContext, String portletId, long plid,
1003                            Element portletDataElement)
1004                    throws Exception {
1005    
1006                    long ownerId = PortletKeys.PREFS_OWNER_ID_DEFAULT;
1007                    int ownerType = PortletKeys.PREFS_OWNER_TYPE_LAYOUT;
1008    
1009                    PortletPreferences portletPreferences =
1010                            PortletPreferencesUtil.fetchByO_O_P_P(
1011                                    ownerId, ownerType, plid, portletId);
1012    
1013                    if (portletPreferences == null) {
1014                            portletPreferences =
1015                                    new com.liferay.portal.model.impl.PortletPreferencesImpl();
1016                    }
1017    
1018                    String xml = importPortletData(
1019                            portletDataContext, portletId, portletPreferences,
1020                            portletDataElement);
1021    
1022                    if (Validator.isNotNull(xml)) {
1023                            PortletPreferencesLocalServiceUtil.updatePreferences(
1024                                    ownerId, ownerType, plid, portletId, xml);
1025                    }
1026            }
1027    
1028            protected void importPortletPreferences(
1029                            PortletDataContext portletDataContext, long companyId, long groupId,
1030                            Layout layout, String portletId, Element parentElement,
1031                            boolean preserveScopeLayoutId, boolean importPortletArchivedSetups,
1032                            boolean importPortletData, boolean importPortletSetup,
1033                            boolean importPortletUserPreferences)
1034                    throws Exception {
1035    
1036                    if (portletId == null) {
1037                            portletId = parentElement.attributeValue("portlet-id");
1038                    }
1039    
1040                    long plid = LayoutConstants.DEFAULT_PLID;
1041                    String scopeType = StringPool.BLANK;
1042                    String scopeLayoutUuid = StringPool.BLANK;
1043    
1044                    if (layout != null) {
1045                            plid = layout.getPlid();
1046    
1047                            if (preserveScopeLayoutId && (portletId != null)) {
1048                                    javax.portlet.PortletPreferences jxPortletPreferences =
1049                                            PortletPreferencesFactoryUtil.getLayoutPortletSetup(
1050                                                    layout, portletId);
1051    
1052                                    scopeType = GetterUtil.getString(
1053                                            jxPortletPreferences.getValue("lfrScopeType", null));
1054                                    scopeLayoutUuid = GetterUtil.getString(
1055                                            jxPortletPreferences.getValue("lfrScopeLayoutUuid", null));
1056    
1057                                    portletDataContext.setScopeType(scopeType);
1058                                    portletDataContext.setScopeLayoutUuid(scopeLayoutUuid);
1059                            }
1060                    }
1061    
1062                    List<Element> portletPreferencesElements = parentElement.elements(
1063                            "portlet-preferences");
1064    
1065                    for (Element portletPreferencesElement : portletPreferencesElements) {
1066                            String path = portletPreferencesElement.attributeValue("path");
1067    
1068                            if (portletDataContext.isPathNotProcessed(path)) {
1069                                    String xml = null;
1070    
1071                                    Element element = null;
1072    
1073                                    try {
1074                                            xml = portletDataContext.getZipEntryAsString(path);
1075    
1076                                            Document preferencesDocument = SAXReaderUtil.read(xml);
1077    
1078                                            element = preferencesDocument.getRootElement();
1079                                    }
1080                                    catch (DocumentException de) {
1081                                            throw new SystemException(de);
1082                                    }
1083    
1084                                    long ownerId = GetterUtil.getLong(
1085                                            element.attributeValue("owner-id"));
1086                                    int ownerType = GetterUtil.getInteger(
1087                                            element.attributeValue("owner-type"));
1088    
1089                                    if ((ownerType == PortletKeys.PREFS_OWNER_TYPE_COMPANY) ||
1090                                            !importPortletSetup) {
1091    
1092                                            continue;
1093                                    }
1094    
1095                                    if ((ownerType == PortletKeys.PREFS_OWNER_TYPE_ARCHIVED) &&
1096                                            !importPortletArchivedSetups) {
1097    
1098                                            continue;
1099                                    }
1100    
1101                                    if ((ownerType == PortletKeys.PREFS_OWNER_TYPE_USER) &&
1102                                            (ownerId != PortletKeys.PREFS_OWNER_ID_DEFAULT) &&
1103                                            !importPortletUserPreferences) {
1104    
1105                                            continue;
1106                                    }
1107    
1108                                    long curPlid = plid;
1109                                    String curPortletId = portletId;
1110    
1111                                    if (ownerType == PortletKeys.PREFS_OWNER_TYPE_GROUP) {
1112                                            curPlid = PortletKeys.PREFS_PLID_SHARED;
1113                                            curPortletId = PortletConstants.getRootPortletId(portletId);
1114                                            ownerId = portletDataContext.getScopeGroupId();
1115                                    }
1116    
1117                                    if (ownerType == PortletKeys.PREFS_OWNER_TYPE_ARCHIVED) {
1118                                            String userUuid = element.attributeValue(
1119                                                    "archive-user-uuid");
1120    
1121                                            long userId = portletDataContext.getUserId(userUuid);
1122    
1123                                            String name = element.attributeValue("archive-name");
1124    
1125                                            curPortletId = PortletConstants.getRootPortletId(portletId);
1126    
1127                                            PortletItem portletItem =
1128                                                    PortletItemLocalServiceUtil.updatePortletItem(
1129                                                            userId, groupId, name, curPortletId,
1130                                                            PortletPreferences.class.getName());
1131    
1132                                            curPlid = LayoutConstants.DEFAULT_PLID;
1133                                            ownerId = portletItem.getPortletItemId();
1134                                    }
1135    
1136                                    if (ownerType == PortletKeys.PREFS_OWNER_TYPE_USER) {
1137                                            String userUuid = element.attributeValue("user-uuid");
1138    
1139                                            ownerId = portletDataContext.getUserId(userUuid);
1140                                    }
1141    
1142                                    boolean defaultUser = GetterUtil.getBoolean(
1143                                            element.attributeValue("default-user"));
1144    
1145                                    if (defaultUser) {
1146                                            ownerId = UserLocalServiceUtil.getDefaultUserId(companyId);
1147                                    }
1148    
1149                                    javax.portlet.PortletPreferences jxPortletPreferences =
1150                                            PortletPreferencesFactoryUtil.fromXML(
1151                                                    companyId, ownerId, ownerType, curPlid, curPortletId,
1152                                                    xml);
1153    
1154                                    Element importDataRootElement =
1155                                            portletDataContext.getImportDataRootElement();
1156    
1157                                    try {
1158                                            Element preferenceDataElement =
1159                                                    portletPreferencesElement.element("preference-data");
1160    
1161                                            if (preferenceDataElement != null) {
1162                                                    portletDataContext.setImportDataRootElement(
1163                                                            preferenceDataElement);
1164                                            }
1165    
1166                                            Portlet portlet = PortletLocalServiceUtil.getPortletById(
1167                                                    portletDataContext.getCompanyId(), curPortletId);
1168    
1169                                            PortletDataHandler portletDataHandler =
1170                                                    portlet.getPortletDataHandlerInstance();
1171    
1172                                            jxPortletPreferences =
1173                                                    portletDataHandler.processImportPortletPreferences(
1174                                                            portletDataContext, curPortletId,
1175                                                            jxPortletPreferences);
1176                                    }
1177                                    finally {
1178                                            portletDataContext.setImportDataRootElement(
1179                                                    importDataRootElement);
1180                                    }
1181    
1182                                    updatePortletPreferences(
1183                                            portletDataContext, ownerId, ownerType, curPlid,
1184                                            curPortletId,
1185                                            PortletPreferencesFactoryUtil.toXML(jxPortletPreferences),
1186                                            importPortletData);
1187                            }
1188                    }
1189    
1190                    if (preserveScopeLayoutId && (layout != null)) {
1191                            javax.portlet.PortletPreferences jxPortletPreferences =
1192                                    PortletPreferencesFactoryUtil.getLayoutPortletSetup(
1193                                            layout, portletId);
1194    
1195                            try {
1196                                    jxPortletPreferences.setValue("lfrScopeType", scopeType);
1197                                    jxPortletPreferences.setValue(
1198                                            "lfrScopeLayoutUuid", scopeLayoutUuid);
1199    
1200                                    jxPortletPreferences.store();
1201                            }
1202                            finally {
1203                                    portletDataContext.setScopeType(scopeType);
1204                                    portletDataContext.setScopeLayoutUuid(scopeLayoutUuid);
1205                            }
1206                    }
1207            }
1208    
1209            protected void readAssetCategories(PortletDataContext portletDataContext)
1210                    throws Exception {
1211    
1212                    String xml = portletDataContext.getZipEntryAsString(
1213                            ExportImportPathUtil.getSourceRootPath(portletDataContext) +
1214                                    "/categories-hierarchy.xml");
1215    
1216                    if (xml == null) {
1217                            return;
1218                    }
1219    
1220                    Document document = SAXReaderUtil.read(xml);
1221    
1222                    Element rootElement = document.getRootElement();
1223    
1224                    Element assetVocabulariesElement = rootElement.element("vocabularies");
1225    
1226                    List<Element> assetVocabularyElements =
1227                            assetVocabulariesElement.elements("vocabulary");
1228    
1229                    Map<Long, Long> assetVocabularyPKs =
1230                            (Map<Long, Long>)portletDataContext.getNewPrimaryKeysMap(
1231                                    AssetVocabulary.class);
1232    
1233                    for (Element assetVocabularyElement : assetVocabularyElements) {
1234                            String path = assetVocabularyElement.attributeValue("path");
1235    
1236                            if (!portletDataContext.isPathNotProcessed(path)) {
1237                                    continue;
1238                            }
1239    
1240                            AssetVocabulary assetVocabulary =
1241                                    (AssetVocabulary)portletDataContext.getZipEntryAsObject(path);
1242    
1243                            importAssetVocabulary(
1244                                    portletDataContext, assetVocabularyPKs, assetVocabularyElement,
1245                                    assetVocabulary);
1246                    }
1247    
1248                    Element assetCategoriesElement = rootElement.element("categories");
1249    
1250                    List<Element> assetCategoryElements = assetCategoriesElement.elements(
1251                            "category");
1252    
1253                    Map<Long, Long> assetCategoryPKs =
1254                            (Map<Long, Long>)portletDataContext.getNewPrimaryKeysMap(
1255                                    AssetCategory.class);
1256    
1257                    Map<String, String> assetCategoryUuids =
1258                            (Map<String, String>)portletDataContext.getNewPrimaryKeysMap(
1259                                    AssetCategory.class + ".uuid");
1260    
1261                    for (Element assetCategoryElement : assetCategoryElements) {
1262                            String path = assetCategoryElement.attributeValue("path");
1263    
1264                            if (!portletDataContext.isPathNotProcessed(path)) {
1265                                    continue;
1266                            }
1267    
1268                            AssetCategory assetCategory =
1269                                    (AssetCategory)portletDataContext.getZipEntryAsObject(path);
1270    
1271                            importAssetCategory(
1272                                    portletDataContext, assetVocabularyPKs, assetCategoryPKs,
1273                                    assetCategoryUuids, assetCategoryElement, assetCategory);
1274                    }
1275    
1276                    Element assetsElement = rootElement.element("assets");
1277    
1278                    List<Element> assetElements = assetsElement.elements("asset");
1279    
1280                    for (Element assetElement : assetElements) {
1281                            String className = GetterUtil.getString(
1282                                    assetElement.attributeValue("class-name"));
1283                            long classPK = GetterUtil.getLong(
1284                                    assetElement.attributeValue("class-pk"));
1285                            String[] assetCategoryUuidArray = StringUtil.split(
1286                                    GetterUtil.getString(
1287                                            assetElement.attributeValue("category-uuids")));
1288    
1289                            long[] assetCategoryIds = new long[0];
1290    
1291                            for (String assetCategoryUuid : assetCategoryUuidArray) {
1292                                    assetCategoryUuid = MapUtil.getString(
1293                                            assetCategoryUuids, assetCategoryUuid, assetCategoryUuid);
1294    
1295                                    AssetCategory assetCategory = AssetCategoryUtil.fetchByUUID_G(
1296                                            assetCategoryUuid, portletDataContext.getScopeGroupId());
1297    
1298                                    if (assetCategory == null) {
1299                                            Group companyGroup = GroupLocalServiceUtil.getCompanyGroup(
1300                                                    portletDataContext.getCompanyId());
1301    
1302                                            assetCategory = AssetCategoryUtil.fetchByUUID_G(
1303                                                    assetCategoryUuid, companyGroup.getGroupId());
1304                                    }
1305    
1306                                    if (assetCategory != null) {
1307                                            assetCategoryIds = ArrayUtil.append(
1308                                                    assetCategoryIds, assetCategory.getCategoryId());
1309                                    }
1310                            }
1311    
1312                            portletDataContext.addAssetCategories(
1313                                    className, classPK, assetCategoryIds);
1314                    }
1315            }
1316    
1317            protected void readAssetLinks(PortletDataContext portletDataContext)
1318                    throws Exception {
1319    
1320                    String xml = portletDataContext.getZipEntryAsString(
1321                            ExportImportPathUtil.getSourceRootPath(portletDataContext) +
1322                                    "/links.xml");
1323    
1324                    if (xml == null) {
1325                            return;
1326                    }
1327    
1328                    Document document = SAXReaderUtil.read(xml);
1329    
1330                    Element rootElement = document.getRootElement();
1331    
1332                    List<Element> assetLinkGroupElements = rootElement.elements(
1333                            "asset-link-group");
1334    
1335                    for (Element assetLinkGroupElement : assetLinkGroupElements) {
1336                            String sourceUuid = assetLinkGroupElement.attributeValue(
1337                                    "source-uuid");
1338    
1339                            AssetEntry sourceAssetEntry = AssetEntryLocalServiceUtil.fetchEntry(
1340                                    portletDataContext.getScopeGroupId(), sourceUuid);
1341    
1342                            if (sourceAssetEntry == null) {
1343                                    sourceAssetEntry = AssetEntryLocalServiceUtil.fetchEntry(
1344                                            portletDataContext.getCompanyGroupId(), sourceUuid);
1345                            }
1346    
1347                            if (sourceAssetEntry == null) {
1348                                    if (_log.isWarnEnabled()) {
1349                                            _log.warn(
1350                                                    "Unable to find asset entry with uuid " + sourceUuid);
1351                                    }
1352    
1353                                    continue;
1354                            }
1355    
1356                            List<Element> assetLinksElements = assetLinkGroupElement.elements(
1357                                    "asset-link");
1358    
1359                            for (Element assetLinkElement : assetLinksElements) {
1360                                    String path = assetLinkElement.attributeValue("path");
1361    
1362                                    if (!portletDataContext.isPathNotProcessed(path)) {
1363                                            continue;
1364                                    }
1365    
1366                                    String targetUuid = assetLinkElement.attributeValue(
1367                                            "target-uuid");
1368    
1369                                    AssetEntry targetAssetEntry =
1370                                            AssetEntryLocalServiceUtil.fetchEntry(
1371                                                    portletDataContext.getScopeGroupId(), targetUuid);
1372    
1373                                    if (targetAssetEntry == null) {
1374                                            targetAssetEntry = AssetEntryLocalServiceUtil.fetchEntry(
1375                                                    portletDataContext.getCompanyGroupId(), targetUuid);
1376                                    }
1377    
1378                                    if (targetAssetEntry == null) {
1379                                            if (_log.isWarnEnabled()) {
1380                                                    _log.warn(
1381                                                            "Unable to find asset entry with uuid " +
1382                                                                    targetUuid);
1383                                            }
1384    
1385                                            continue;
1386                                    }
1387    
1388                                    AssetLink assetLink =
1389                                            (AssetLink)portletDataContext.getZipEntryAsObject(path);
1390    
1391                                    long userId = portletDataContext.getUserId(
1392                                            assetLink.getUserUuid());
1393    
1394                                    AssetLinkLocalServiceUtil.updateLink(
1395                                            userId, sourceAssetEntry.getEntryId(),
1396                                            targetAssetEntry.getEntryId(), assetLink.getType(),
1397                                            assetLink.getWeight());
1398                            }
1399                    }
1400            }
1401    
1402            protected void readAssetTags(PortletDataContext portletDataContext)
1403                    throws Exception {
1404    
1405                    String xml = portletDataContext.getZipEntryAsString(
1406                            ExportImportPathUtil.getSourceRootPath(portletDataContext) +
1407                                    "/tags.xml");
1408    
1409                    if (xml == null) {
1410                            return;
1411                    }
1412    
1413                    Document document = SAXReaderUtil.read(xml);
1414    
1415                    Element rootElement = document.getRootElement();
1416    
1417                    List<Element> assetTagElements = rootElement.elements("tag");
1418    
1419                    for (Element assetTagElement : assetTagElements) {
1420                            String path = assetTagElement.attributeValue("path");
1421    
1422                            if (!portletDataContext.isPathNotProcessed(path)) {
1423                                    continue;
1424                            }
1425    
1426                            AssetTag assetTag =
1427                                    (AssetTag)portletDataContext.getZipEntryAsObject(path);
1428    
1429                            Map<Long, Long> assetTagPKs =
1430                                    (Map<Long, Long>)portletDataContext.getNewPrimaryKeysMap(
1431                                            AssetTag.class);
1432    
1433                            importAssetTag(
1434                                    portletDataContext, assetTagPKs, assetTagElement, assetTag);
1435                    }
1436    
1437                    List<Element> assetElements = rootElement.elements("asset");
1438    
1439                    for (Element assetElement : assetElements) {
1440                            String className = GetterUtil.getString(
1441                                    assetElement.attributeValue("class-name"));
1442                            long classPK = GetterUtil.getLong(
1443                                    assetElement.attributeValue("class-pk"));
1444                            String assetTagNames = GetterUtil.getString(
1445                                    assetElement.attributeValue("tags"));
1446    
1447                            portletDataContext.addAssetTags(
1448                                    className, classPK, StringUtil.split(assetTagNames));
1449                    }
1450            }
1451    
1452            protected void readComments(PortletDataContext portletDataContext)
1453                    throws Exception {
1454    
1455                    String xml = portletDataContext.getZipEntryAsString(
1456                            ExportImportPathUtil.getSourceRootPath(portletDataContext) +
1457                                    "/comments.xml");
1458    
1459                    if (xml == null) {
1460                            return;
1461                    }
1462    
1463                    Document document = SAXReaderUtil.read(xml);
1464    
1465                    Element rootElement = document.getRootElement();
1466    
1467                    List<Element> assetElements = rootElement.elements("asset");
1468    
1469                    for (Element assetElement : assetElements) {
1470                            String path = assetElement.attributeValue("path");
1471                            String className = assetElement.attributeValue("class-name");
1472                            long classPK = GetterUtil.getLong(
1473                                    assetElement.attributeValue("class-pk"));
1474    
1475                            List<String> zipFolderEntries =
1476                                    portletDataContext.getZipFolderEntries(path);
1477    
1478                            List<MBMessage> mbMessages = new ArrayList<MBMessage>();
1479    
1480                            for (String zipFolderEntry : zipFolderEntries) {
1481                                    MBMessage mbMessage =
1482                                            (MBMessage)portletDataContext.getZipEntryAsObject(
1483                                                    zipFolderEntry);
1484    
1485                                    if (mbMessage != null) {
1486                                            mbMessages.add(mbMessage);
1487                                    }
1488                            }
1489    
1490                            portletDataContext.addComments(className, classPK, mbMessages);
1491                    }
1492            }
1493    
1494            protected void readExpandoTables(PortletDataContext portletDataContext)
1495                    throws Exception {
1496    
1497                    String xml = portletDataContext.getZipEntryAsString(
1498                            ExportImportPathUtil.getSourceRootPath(portletDataContext) +
1499                                    "/expando-tables.xml");
1500    
1501                    if (xml == null) {
1502                            return;
1503                    }
1504    
1505                    Document document = SAXReaderUtil.read(xml);
1506    
1507                    Element rootElement = document.getRootElement();
1508    
1509                    List<Element> expandoTableElements = rootElement.elements(
1510                            "expando-table");
1511    
1512                    for (Element expandoTableElement : expandoTableElements) {
1513                            String className = expandoTableElement.attributeValue("class-name");
1514    
1515                            ExpandoTable expandoTable = null;
1516    
1517                            try {
1518                                    expandoTable = ExpandoTableLocalServiceUtil.getDefaultTable(
1519                                            portletDataContext.getCompanyId(), className);
1520                            }
1521                            catch (NoSuchTableException nste) {
1522                                    expandoTable = ExpandoTableLocalServiceUtil.addDefaultTable(
1523                                            portletDataContext.getCompanyId(), className);
1524                            }
1525    
1526                            List<Element> expandoColumnElements = expandoTableElement.elements(
1527                                    "expando-column");
1528    
1529                            for (Element expandoColumnElement : expandoColumnElements) {
1530                                    long columnId = GetterUtil.getLong(
1531                                            expandoColumnElement.attributeValue("column-id"));
1532                                    String name = expandoColumnElement.attributeValue("name");
1533                                    int type = GetterUtil.getInteger(
1534                                            expandoColumnElement.attributeValue("type"));
1535                                    String defaultData = expandoColumnElement.elementText(
1536                                            "default-data");
1537                                    String typeSettings = expandoColumnElement.elementText(
1538                                            "type-settings");
1539    
1540                                    Serializable defaultDataObject =
1541                                            ExpandoConverterUtil.getAttributeFromString(
1542                                                    type, defaultData);
1543    
1544                                    ExpandoColumn expandoColumn =
1545                                            ExpandoColumnLocalServiceUtil.getColumn(
1546                                                    expandoTable.getTableId(), name);
1547    
1548                                    if (expandoColumn != null) {
1549                                            ExpandoColumnLocalServiceUtil.updateColumn(
1550                                                    expandoColumn.getColumnId(), name, type,
1551                                                    defaultDataObject);
1552                                    }
1553                                    else {
1554                                            expandoColumn = ExpandoColumnLocalServiceUtil.addColumn(
1555                                                    expandoTable.getTableId(), name, type,
1556                                                    defaultDataObject);
1557                                    }
1558    
1559                                    ExpandoColumnLocalServiceUtil.updateTypeSettings(
1560                                            expandoColumn.getColumnId(), typeSettings);
1561    
1562                                    portletDataContext.importPermissions(
1563                                            ExpandoColumn.class, columnId, expandoColumn.getColumnId());
1564                            }
1565                    }
1566            }
1567    
1568            protected void readLocks(PortletDataContext portletDataContext)
1569                    throws Exception {
1570    
1571                    String xml = portletDataContext.getZipEntryAsString(
1572                            ExportImportPathUtil.getSourceRootPath(portletDataContext) +
1573                                    "/locks.xml");
1574    
1575                    if (xml == null) {
1576                            return;
1577                    }
1578    
1579                    Document document = SAXReaderUtil.read(xml);
1580    
1581                    Element rootElement = document.getRootElement();
1582    
1583                    List<Element> assetElements = rootElement.elements("asset");
1584    
1585                    for (Element assetElement : assetElements) {
1586                            String path = assetElement.attributeValue("path");
1587                            String className = assetElement.attributeValue("class-name");
1588                            String key = assetElement.attributeValue("key");
1589    
1590                            Lock lock = (Lock)portletDataContext.getZipEntryAsObject(path);
1591    
1592                            if (lock != null) {
1593                                    portletDataContext.addLocks(className, key, lock);
1594                            }
1595                    }
1596            }
1597    
1598            protected void readRatingsEntries(PortletDataContext portletDataContext)
1599                    throws Exception {
1600    
1601                    String xml = portletDataContext.getZipEntryAsString(
1602                            ExportImportPathUtil.getSourceRootPath(portletDataContext) +
1603                                    "/ratings.xml");
1604    
1605                    if (xml == null) {
1606                            return;
1607                    }
1608    
1609                    Document document = SAXReaderUtil.read(xml);
1610    
1611                    Element rootElement = document.getRootElement();
1612    
1613                    List<Element> assetElements = rootElement.elements("asset");
1614    
1615                    for (Element assetElement : assetElements) {
1616                            String path = assetElement.attributeValue("path");
1617                            String className = assetElement.attributeValue("class-name");
1618                            long classPK = GetterUtil.getLong(
1619                                    assetElement.attributeValue("class-pk"));
1620    
1621                            List<String> zipFolderEntries =
1622                                    portletDataContext.getZipFolderEntries(path);
1623    
1624                            List<RatingsEntry> ratingsEntries = new ArrayList<RatingsEntry>();
1625    
1626                            for (String zipFolderEntry : zipFolderEntries) {
1627                                    RatingsEntry ratingsEntry =
1628                                            (RatingsEntry)portletDataContext.getZipEntryAsObject(
1629                                                    zipFolderEntry);
1630    
1631                                    if (ratingsEntry != null) {
1632                                            ratingsEntries.add(ratingsEntry);
1633                                    }
1634                            }
1635    
1636                            portletDataContext.addRatingsEntries(
1637                                    className, classPK, ratingsEntries);
1638                    }
1639            }
1640    
1641            protected void readXML(PortletDataContext portletDataContext)
1642                    throws Exception {
1643    
1644                    if ((_rootElement != null) && (_headerElement != null)) {
1645                            return;
1646                    }
1647    
1648                    String xml = portletDataContext.getZipEntryAsString("/manifest.xml");
1649    
1650                    if (xml == null) {
1651                            throw new LARFileException("manifest.xml not found in the LAR");
1652                    }
1653    
1654                    try {
1655                            Document document = SAXReaderUtil.read(xml);
1656    
1657                            _rootElement = document.getRootElement();
1658    
1659                            portletDataContext.setImportDataRootElement(_rootElement);
1660                    }
1661                    catch (Exception e) {
1662                            throw new LARFileException(e);
1663                    }
1664    
1665                    _headerElement = _rootElement.element("header");
1666            }
1667    
1668            protected void resetPortletScope(
1669                    PortletDataContext portletDataContext, long groupId) {
1670    
1671                    portletDataContext.setScopeGroupId(groupId);
1672                    portletDataContext.setScopeLayoutUuid(StringPool.BLANK);
1673                    portletDataContext.setScopeType(StringPool.BLANK);
1674            }
1675    
1676            protected void updatePortletPreferences(
1677                            PortletDataContext portletDataContext, long ownerId, int ownerType,
1678                            long plid, String portletId, String xml, boolean importData)
1679                    throws Exception {
1680    
1681                    Portlet portlet = PortletLocalServiceUtil.getPortletById(
1682                            portletDataContext.getCompanyId(), portletId);
1683    
1684                    if (portlet == null) {
1685                            if (_log.isDebugEnabled()) {
1686                                    _log.debug(
1687                                            "Do not update portlet preferences for " + portletId +
1688                                                    " because the portlet does not exist");
1689                            }
1690    
1691                            return;
1692                    }
1693    
1694                    PortletDataHandler portletDataHandler =
1695                            portlet.getPortletDataHandlerInstance();
1696    
1697                    if (importData || !MergeLayoutPrototypesThreadLocal.isInProgress()) {
1698                            PortletPreferencesLocalServiceUtil.updatePreferences(
1699                                    ownerId, ownerType, plid, portletId, xml);
1700    
1701                            return;
1702                    }
1703    
1704                    // Portlet preferences to be updated only when importing data
1705    
1706                    String[] dataPortletPreferences =
1707                            portletDataHandler.getDataPortletPreferences();
1708    
1709                    // Current portlet preferences
1710    
1711                    javax.portlet.PortletPreferences portletPreferences =
1712                            PortletPreferencesLocalServiceUtil.getPreferences(
1713                                    portletDataContext.getCompanyId(), ownerId, ownerType, plid,
1714                                    portletId);
1715    
1716                    // New portlet preferences
1717    
1718                    javax.portlet.PortletPreferences jxPortletPreferences =
1719                            PortletPreferencesFactoryUtil.fromXML(
1720                                    portletDataContext.getCompanyId(), ownerId, ownerType, plid,
1721                                    portletId, xml);
1722    
1723                    Enumeration<String> enu = jxPortletPreferences.getNames();
1724    
1725                    while (enu.hasMoreElements()) {
1726                            String name = enu.nextElement();
1727    
1728                            String scopeLayoutUuid = portletDataContext.getScopeLayoutUuid();
1729                            String scopeType = portletDataContext.getScopeType();
1730    
1731                            if (!ArrayUtil.contains(dataPortletPreferences, name) ||
1732                                    (Validator.isNull(scopeLayoutUuid) &&
1733                                     scopeType.equals("company"))) {
1734    
1735                                    String[] values = jxPortletPreferences.getValues(name, null);
1736    
1737                                    portletPreferences.setValues(name, values);
1738                            }
1739                    }
1740    
1741                    PortletPreferencesLocalServiceUtil.updatePreferences(
1742                            ownerId, ownerType, plid, portletId, portletPreferences);
1743            }
1744    
1745            protected void validateFile(
1746                            PortletDataContext portletDataContext, String portletId)
1747                    throws Exception {
1748    
1749                    // Build compatibility
1750    
1751                    readXML(portletDataContext);
1752    
1753                    int buildNumber = ReleaseInfo.getBuildNumber();
1754    
1755                    int importBuildNumber = GetterUtil.getInteger(
1756                            _headerElement.attributeValue("build-number"));
1757    
1758                    if (buildNumber != importBuildNumber) {
1759                            throw new LayoutImportException(
1760                                    "LAR build number " + importBuildNumber + " does not match " +
1761                                            "portal build number " + buildNumber);
1762                    }
1763    
1764                    // Type
1765    
1766                    String larType = _headerElement.attributeValue("type");
1767    
1768                    if (!larType.equals("portlet")) {
1769                            throw new LARTypeException(larType);
1770                    }
1771    
1772                    // Portlet compatibility
1773    
1774                    String rootPortletId = _headerElement.attributeValue("root-portlet-id");
1775    
1776                    if (!PortletConstants.getRootPortletId(portletId).equals(
1777                                    rootPortletId)) {
1778    
1779                            throw new PortletIdException("Invalid portlet id " + rootPortletId);
1780                    }
1781    
1782                    // Available locales
1783    
1784                    Portlet portlet = PortletLocalServiceUtil.getPortletById(
1785                            portletDataContext.getCompanyId(), portletId);
1786    
1787                    PortletDataHandler portletDataHandler =
1788                            portlet.getPortletDataHandlerInstance();
1789    
1790                    if (portletDataHandler.isDataLocalized()) {
1791                            Locale[] sourceAvailableLocales = LocaleUtil.fromLanguageIds(
1792                                    StringUtil.split(
1793                                            _headerElement.attributeValue("available-locales")));
1794    
1795                            Locale[] targetAvailableLocales = LanguageUtil.getAvailableLocales(
1796                                    PortalUtil.getSiteGroupId(
1797                                            portletDataContext.getScopeGroupId()));
1798    
1799                            for (Locale sourceAvailableLocale : sourceAvailableLocales) {
1800                                    if (!ArrayUtil.contains(
1801                                                    targetAvailableLocales, sourceAvailableLocale)) {
1802    
1803                                            LocaleException le = new LocaleException(
1804                                                    LocaleException.TYPE_EXPORT_IMPORT,
1805                                                    "Locale " + sourceAvailableLocale + " is not " +
1806                                                            "available in company " +
1807                                                                    portletDataContext.getCompanyId());
1808    
1809                                            le.setSourceAvailableLocales(sourceAvailableLocales);
1810                                            le.setTargetAvailableLocales(targetAvailableLocales);
1811    
1812                                            throw le;
1813                                    }
1814                            }
1815                    }
1816            }
1817    
1818            private static Log _log = LogFactoryUtil.getLog(PortletImporter.class);
1819    
1820            private DeletionSystemEventImporter _deletionSystemEventImporter =
1821                    new DeletionSystemEventImporter();
1822            private Element _headerElement;
1823            private PermissionImporter _permissionImporter = new PermissionImporter();
1824            private Element _rootElement;
1825    
1826    }