001    /**
002     * Copyright (c) 2000-present 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.service.impl;
016    
017    import com.liferay.portal.NoSuchLayoutException;
018    import com.liferay.portal.RequiredLayoutException;
019    import com.liferay.portal.SitemapChangeFrequencyException;
020    import com.liferay.portal.SitemapIncludeException;
021    import com.liferay.portal.SitemapPagePriorityException;
022    import com.liferay.portal.kernel.bean.BeanReference;
023    import com.liferay.portal.kernel.dao.orm.QueryUtil;
024    import com.liferay.portal.kernel.exception.PortalException;
025    import com.liferay.portal.kernel.exception.SystemException;
026    import com.liferay.portal.kernel.systemevent.SystemEvent;
027    import com.liferay.portal.kernel.systemevent.SystemEventHierarchyEntry;
028    import com.liferay.portal.kernel.systemevent.SystemEventHierarchyEntryThreadLocal;
029    import com.liferay.portal.kernel.util.ContentTypes;
030    import com.liferay.portal.kernel.util.GetterUtil;
031    import com.liferay.portal.kernel.util.ListUtil;
032    import com.liferay.portal.kernel.util.LocaleUtil;
033    import com.liferay.portal.kernel.util.ParamUtil;
034    import com.liferay.portal.kernel.util.StringBundler;
035    import com.liferay.portal.kernel.util.StringPool;
036    import com.liferay.portal.kernel.util.StringUtil;
037    import com.liferay.portal.kernel.util.UnicodeProperties;
038    import com.liferay.portal.kernel.util.Validator;
039    import com.liferay.portal.model.Group;
040    import com.liferay.portal.model.Layout;
041    import com.liferay.portal.model.LayoutConstants;
042    import com.liferay.portal.model.LayoutFriendlyURL;
043    import com.liferay.portal.model.LayoutPrototype;
044    import com.liferay.portal.model.LayoutReference;
045    import com.liferay.portal.model.LayoutSet;
046    import com.liferay.portal.model.LayoutSetPrototype;
047    import com.liferay.portal.model.LayoutType;
048    import com.liferay.portal.model.LayoutTypePortlet;
049    import com.liferay.portal.model.PortletConstants;
050    import com.liferay.portal.model.ResourceConstants;
051    import com.liferay.portal.model.ResourcePermission;
052    import com.liferay.portal.model.SystemEventConstants;
053    import com.liferay.portal.model.User;
054    import com.liferay.portal.model.UserGroup;
055    import com.liferay.portal.model.impl.VirtualLayout;
056    import com.liferay.portal.service.ServiceContext;
057    import com.liferay.portal.service.base.LayoutLocalServiceBaseImpl;
058    import com.liferay.portal.util.PortalUtil;
059    import com.liferay.portal.util.PropsValues;
060    import com.liferay.portal.util.comparator.LayoutComparator;
061    import com.liferay.portal.util.comparator.LayoutPriorityComparator;
062    import com.liferay.portlet.exportimport.lar.MissingReferences;
063    import com.liferay.portlet.exportimport.model.ExportImportConfiguration;
064    import com.liferay.portlet.sites.util.Sites;
065    import com.liferay.portlet.sites.util.SitesUtil;
066    
067    import java.io.File;
068    import java.io.InputStream;
069    
070    import java.util.ArrayList;
071    import java.util.Date;
072    import java.util.HashMap;
073    import java.util.HashSet;
074    import java.util.LinkedHashSet;
075    import java.util.List;
076    import java.util.Locale;
077    import java.util.Map;
078    import java.util.Set;
079    
080    /**
081     * Provides the local service for accessing, adding, deleting, exporting,
082     * importing, and updating layouts.
083     *
084     * @author Brian Wing Shun Chan
085     * @author Jorge Ferrer
086     * @author Joel Kozikowski
087     * @author Charles May
088     * @author Raymond Aug??
089     * @author Jorge Ferrer
090     * @author Bruno Farache
091     * @author Vilmos Papp
092     * @author James Lefeu
093     * @author Tibor Lipusz
094     */
095    public class LayoutLocalServiceImpl extends LayoutLocalServiceBaseImpl {
096    
097            /**
098             * Returns the object counter's name.
099             *
100             * @param  groupId the primary key of the group
101             * @param  privateLayout whether layout is private to the group
102             * @return the object counter's name
103             */
104            public static String getCounterName(long groupId, boolean privateLayout) {
105                    StringBundler sb = new StringBundler(5);
106    
107                    sb.append(Layout.class.getName());
108                    sb.append(StringPool.POUND);
109                    sb.append(groupId);
110                    sb.append(StringPool.POUND);
111                    sb.append(privateLayout);
112    
113                    return sb.toString();
114            }
115    
116            /**
117             * Adds a layout.
118             *
119             * <p>
120             * This method handles the creation of the layout including its resources,
121             * metadata, and internal data structures. It is not necessary to make
122             * subsequent calls to any methods to setup default groups, resources, ...
123             * etc.
124             * </p>
125             *
126             * @param      userId the primary key of the user
127             * @param      groupId the primary key of the group
128             * @param      privateLayout whether the layout is private to the group
129             * @param      parentLayoutId the primary key of the parent layout
130             *             (optionally {@link LayoutConstants#DEFAULT_PARENT_LAYOUT_ID})
131             * @param      nameMap the layout's locales and localized names
132             * @param      titleMap the layout's locales and localized titles
133             * @param      descriptionMap the layout's locales and localized
134             *             descriptions
135             * @param      keywordsMap the layout's locales and localized keywords
136             * @param      robotsMap the layout's locales and localized robots
137             * @param      type the layout's type (optionally {@link
138             *             LayoutConstants#TYPE_PORTLET}). The possible types can be
139             *             found in {@link LayoutConstants}.
140             * @param      hidden whether the layout is hidden
141             * @param      friendlyURL the layout's friendly URL (optionally {@link
142             *             PropsValues#DEFAULT_USER_PRIVATE_LAYOUT_FRIENDLY_URL} or
143             *             {@link PropsValues#DEFAULT_USER_PUBLIC_LAYOUT_FRIENDLY_URL}).
144             *             The default values can be overridden in
145             *             <code>portal-ext.properties</code> by specifying new values
146             *             for the corresponding properties defined in {@link
147             *             PropsValues}. To see how the URL is normalized when accessed,
148             *             see {@link
149             *             com.liferay.portal.kernel.util.FriendlyURLNormalizerUtil#normalize(
150             *             String)}.
151             * @param      serviceContext the service context to be applied. Must set
152             *             the UUID for the layout. Can set the creation date,
153             *             modification date and the expando bridge attributes for the
154             *             layout. For layouts that belong to a layout set prototype, an
155             *             attribute named <code>layoutUpdateable</code> can be set to
156             *             specify whether site administrators can modify this page
157             *             within their site. For layouts that are created from a layout
158             *             prototype, attributes named <code>layoutPrototypeUuid</code>
159             *             and <code>layoutPrototypeLinkedEnabled</code> can be
160             *             specified to provide the unique identifier of the source
161             *             prototype and a boolean to determine whether a link to it
162             *             should be enabled to activate propagation of changes made to
163             *             the linked page in the prototype.
164             * @return     the layout
165             * @deprecated As of 6.2.0, replaced by {@link #addLayout(long, long,
166             *             boolean, long, Map, Map, Map, Map, Map, String, String,
167             *             boolean, Map, ServiceContext)}
168             */
169            @Deprecated
170            @Override
171            public Layout addLayout(
172                            long userId, long groupId, boolean privateLayout,
173                            long parentLayoutId, Map<Locale, String> nameMap,
174                            Map<Locale, String> titleMap, Map<Locale, String> descriptionMap,
175                            Map<Locale, String> keywordsMap, Map<Locale, String> robotsMap,
176                            String type, boolean hidden, String friendlyURL,
177                            ServiceContext serviceContext)
178                    throws PortalException {
179    
180                    Map<Locale, String> friendlyURLMap = new HashMap<>();
181    
182                    friendlyURLMap.put(LocaleUtil.getSiteDefault(), friendlyURL);
183    
184                    return addLayout(
185                            userId, groupId, privateLayout, parentLayoutId, nameMap, titleMap,
186                            descriptionMap, keywordsMap, robotsMap, type, StringPool.BLANK,
187                            hidden, friendlyURLMap, serviceContext);
188            }
189    
190            /**
191             * Adds a layout with additional parameters.
192             *
193             * <p>
194             * This method handles the creation of the layout including its resources,
195             * metadata, and internal data structures. It is not necessary to make
196             * subsequent calls to any methods to setup default groups, resources, ...
197             * etc.
198             * </p>
199             *
200             * @param  userId the primary key of the user
201             * @param  groupId the primary key of the group
202             * @param  privateLayout whether the layout is private to the group
203             * @param  parentLayoutId the primary key of the parent layout (optionally
204             *         {@link LayoutConstants#DEFAULT_PARENT_LAYOUT_ID})
205             * @param  nameMap the layout's locales and localized names
206             * @param  titleMap the layout's locales and localized titles
207             * @param  descriptionMap the layout's locales and localized descriptions
208             * @param  keywordsMap the layout's locales and localized keywords
209             * @param  robotsMap the layout's locales and localized robots
210             * @param  type the layout's type (optionally {@link
211             *         LayoutConstants#TYPE_PORTLET}). The possible types can be found
212             *         in {@link LayoutConstants}.
213             * @param  typeSettings the settings to load the unicode properties object.
214             *         See {@link UnicodeProperties #fastLoad(String)}.
215             * @param  hidden whether the layout is hidden
216             * @param  friendlyURLMap the layout's locales and localized friendly URLs.
217             *         To see how the URL is normalized when accessed, see {@link
218             *         com.liferay.portal.kernel.util.FriendlyURLNormalizerUtil#normalize(
219             *         String)}.
220             * @param  serviceContext the service context to be applied. Must set the
221             *         UUID for the layout. Can set the creation date, modification
222             *         date, and expando bridge attributes for the layout. For layouts
223             *         that belong to a layout set prototype, an attribute named
224             *         <code>layoutUpdateable</code> can be set to specify whether site
225             *         administrators can modify this page within their site. For
226             *         layouts that are created from a layout prototype, attributes
227             *         named <code>layoutPrototypeUuid</code> and
228             *         <code>layoutPrototypeLinkedEnabled</code> can be specified to
229             *         provide the unique identifier of the source prototype and a
230             *         boolean to determine whether a link to it should be enabled to
231             *         activate propagation of changes made to the linked page in the
232             *         prototype.
233             * @return the layout
234             */
235            @Override
236            public Layout addLayout(
237                            long userId, long groupId, boolean privateLayout,
238                            long parentLayoutId, Map<Locale, String> nameMap,
239                            Map<Locale, String> titleMap, Map<Locale, String> descriptionMap,
240                            Map<Locale, String> keywordsMap, Map<Locale, String> robotsMap,
241                            String type, String typeSettings, boolean hidden,
242                            Map<Locale, String> friendlyURLMap, ServiceContext serviceContext)
243                    throws PortalException {
244    
245                    // Layout
246    
247                    User user = userPersistence.findByPrimaryKey(userId);
248                    long layoutId = getNextLayoutId(groupId, privateLayout);
249                    parentLayoutId = layoutLocalServiceHelper.getParentLayoutId(
250                            groupId, privateLayout, parentLayoutId);
251                    String name = nameMap.get(LocaleUtil.getSiteDefault());
252                    friendlyURLMap = layoutLocalServiceHelper.getFriendlyURLMap(
253                            groupId, privateLayout, layoutId, name, friendlyURLMap);
254    
255                    String friendlyURL = friendlyURLMap.get(LocaleUtil.getSiteDefault());
256    
257                    int priority = layoutLocalServiceHelper.getNextPriority(
258                            groupId, privateLayout, parentLayoutId, null, -1);
259    
260                    layoutLocalServiceHelper.validate(
261                            groupId, privateLayout, layoutId, parentLayoutId, name, type,
262                            hidden, friendlyURLMap, serviceContext);
263    
264                    Date now = new Date();
265    
266                    long plid = counterLocalService.increment();
267    
268                    Layout layout = layoutPersistence.create(plid);
269    
270                    layout.setUuid(serviceContext.getUuid());
271                    layout.setGroupId(groupId);
272                    layout.setCompanyId(user.getCompanyId());
273                    layout.setUserId(user.getUserId());
274                    layout.setUserName(user.getFullName());
275                    layout.setCreateDate(serviceContext.getCreateDate(now));
276                    layout.setModifiedDate(serviceContext.getModifiedDate(now));
277                    layout.setPrivateLayout(privateLayout);
278                    layout.setLayoutId(layoutId);
279                    layout.setParentLayoutId(parentLayoutId);
280                    layout.setNameMap(nameMap);
281                    layout.setTitleMap(titleMap);
282                    layout.setDescriptionMap(descriptionMap);
283                    layout.setKeywordsMap(keywordsMap);
284                    layout.setRobotsMap(robotsMap);
285                    layout.setType(type);
286                    layout.setHidden(hidden);
287                    layout.setFriendlyURL(friendlyURL);
288                    layout.setPriority(priority);
289    
290                    boolean layoutUpdateable = ParamUtil.getBoolean(
291                            serviceContext, Sites.LAYOUT_UPDATEABLE, true);
292    
293                    UnicodeProperties typeSettingsProperties = new UnicodeProperties();
294    
295                    typeSettingsProperties.fastLoad(typeSettings);
296    
297                    if (!layoutUpdateable) {
298                            typeSettingsProperties.put(
299                                    Sites.LAYOUT_UPDATEABLE, String.valueOf(layoutUpdateable));
300                    }
301    
302                    if (privateLayout) {
303                            typeSettingsProperties.put(
304                                    "privateLayout", String.valueOf(privateLayout));
305                    }
306    
307                    validateTypeSettingsProperties(typeSettingsProperties);
308    
309                    layout.setTypeSettingsProperties(typeSettingsProperties);
310    
311                    String layoutPrototypeUuid = ParamUtil.getString(
312                            serviceContext, "layoutPrototypeUuid");
313                    boolean layoutPrototypeLinkEnabled = ParamUtil.getBoolean(
314                            serviceContext, "layoutPrototypeLinkEnabled",
315                            PropsValues.LAYOUT_PROTOTYPE_LINK_ENABLED_DEFAULT);
316    
317                    if (Validator.isNotNull(layoutPrototypeUuid)) {
318                            layout.setLayoutPrototypeUuid(layoutPrototypeUuid);
319                            layout.setLayoutPrototypeLinkEnabled(layoutPrototypeLinkEnabled);
320                    }
321    
322                    if (type.equals(LayoutConstants.TYPE_PORTLET)) {
323                            LayoutTypePortlet layoutTypePortlet =
324                                    (LayoutTypePortlet)layout.getLayoutType();
325    
326                            if (Validator.isNull(layoutTypePortlet.getLayoutTemplateId())) {
327                                    layoutTypePortlet.setLayoutTemplateId(
328                                            0, PropsValues.LAYOUT_DEFAULT_TEMPLATE_ID, false);
329                            }
330                    }
331    
332                    layout.setExpandoBridgeAttributes(serviceContext);
333    
334                    layoutPersistence.update(layout);
335    
336                    // Layout friendly URLs
337    
338                    layoutFriendlyURLLocalService.updateLayoutFriendlyURLs(
339                            user.getUserId(), user.getCompanyId(), groupId, plid, privateLayout,
340                            friendlyURLMap, serviceContext);
341    
342                    // Layout prototype
343    
344                    if (Validator.isNotNull(layoutPrototypeUuid) &&
345                            !layoutPrototypeLinkEnabled) {
346    
347                            LayoutPrototype layoutPrototype =
348                                    layoutPrototypeLocalService.
349                                            getLayoutPrototypeByUuidAndCompanyId(
350                                                    layoutPrototypeUuid, layout.getCompanyId());
351    
352                            try {
353                                    SitesUtil.applyLayoutPrototype(
354                                            layoutPrototype, layout, layoutPrototypeLinkEnabled);
355                            }
356                            catch (PortalException pe) {
357                                    throw pe;
358                            }
359                            catch (SystemException se) {
360                                    throw se;
361                            }
362                            catch (Exception e) {
363                                    throw new SystemException(e);
364                            }
365                    }
366    
367                    // Resources
368    
369                    boolean addGroupPermissions = true;
370    
371                    Group group = groupLocalService.getGroup(groupId);
372    
373                    if (privateLayout && group.isUser()) {
374                            addGroupPermissions = false;
375                    }
376    
377                    boolean addGuestPermissions = false;
378    
379                    if (!privateLayout || type.equals(LayoutConstants.TYPE_CONTROL_PANEL) ||
380                            group.isLayoutSetPrototype()) {
381    
382                            addGuestPermissions = true;
383                    }
384    
385                    resourceLocalService.addResources(
386                            user.getCompanyId(), groupId, user.getUserId(),
387                            Layout.class.getName(), layout.getPlid(), false,
388                            addGroupPermissions, addGuestPermissions);
389    
390                    // Group
391    
392                    groupLocalService.updateSite(groupId, true);
393    
394                    // Layout set
395    
396                    layoutSetLocalService.updatePageCount(groupId, privateLayout);
397    
398                    LayoutSet layoutSet = layoutSetPersistence.findByG_P(
399                            groupId, privateLayout);
400    
401                    layout.setLayoutSet(layoutSet);
402    
403                    // Asset
404    
405                    updateAsset(
406                            userId, layout, serviceContext.getAssetCategoryIds(),
407                            serviceContext.getAssetTagNames());
408    
409                    return layout;
410            }
411    
412            /**
413             * Adds a layout with single entry maps for name, title, and description to
414             * the default locale.
415             *
416             * <p>
417             * This method handles the creation of the layout including its resources,
418             * metadata, and internal data structures. It is not necessary to make
419             * subsequent calls to any methods to setup default groups, resources, ...
420             * etc.
421             * </p>
422             *
423             * @param  userId the primary key of the user
424             * @param  groupId the primary key of the group
425             * @param  privateLayout whether the layout is private to the group
426             * @param  parentLayoutId the primary key of the parent layout (optionally
427             *         {@link LayoutConstants#DEFAULT_PARENT_LAYOUT_ID}). The possible
428             *         values can be found in {@link LayoutConstants}.
429             * @param  name the layout's name (optionally {@link
430             *         PropsValues#DEFAULT_USER_PRIVATE_LAYOUT_NAME} or {@link
431             *         PropsValues#DEFAULT_USER_PUBLIC_LAYOUT_NAME}). The default values
432             *         can be overridden in <code>portal-ext.properties</code> by
433             *         specifying new values for the corresponding properties defined in
434             *         {@link PropsValues}
435             * @param  title the layout's title
436             * @param  description the layout's description
437             * @param  type the layout's type (optionally {@link
438             *         LayoutConstants#TYPE_PORTLET}). The possible types can be found
439             *         in {@link LayoutConstants}.
440             * @param  hidden whether the layout is hidden
441             * @param  friendlyURL the friendly URL of the layout (optionally {@link
442             *         PropsValues#DEFAULT_USER_PRIVATE_LAYOUT_FRIENDLY_URL} or {@link
443             *         PropsValues#DEFAULT_USER_PUBLIC_LAYOUT_FRIENDLY_URL}). The
444             *         default values can be overridden in
445             *         <code>portal-ext.properties</code> by specifying new values for
446             *         the corresponding properties defined in {@link PropsValues}. To
447             *         see how the URL is normalized when accessed, see {@link
448             *         com.liferay.portal.kernel.util.FriendlyURLNormalizerUtil#normalize(
449             *         String)}.
450             * @param  serviceContext the service context to be applied. Must set the
451             *         UUID for the layout. Can set the creation date and modification
452             *         date for the layout. For layouts that belong to a layout set
453             *         prototype, an attribute named <code>layoutUpdateable</code> can
454             *         be set to specify whether site administrators can modify this
455             *         page within their site.
456             * @return the layout
457             */
458            @Override
459            public Layout addLayout(
460                            long userId, long groupId, boolean privateLayout,
461                            long parentLayoutId, String name, String title, String description,
462                            String type, boolean hidden, String friendlyURL,
463                            ServiceContext serviceContext)
464                    throws PortalException {
465    
466                    Locale locale = LocaleUtil.getSiteDefault();
467    
468                    Map<Locale, String> nameMap = new HashMap<>();
469    
470                    nameMap.put(locale, name);
471    
472                    Map<Locale, String> titleMap = new HashMap<>();
473    
474                    titleMap.put(locale, title);
475    
476                    Map<Locale, String> descriptionMap = new HashMap<>();
477    
478                    descriptionMap.put(locale, description);
479    
480                    Map<Locale, String> friendlyURLMap = new HashMap<>();
481    
482                    friendlyURLMap.put(LocaleUtil.getSiteDefault(), friendlyURL);
483    
484                    return addLayout(
485                            userId, groupId, privateLayout, parentLayoutId, nameMap, titleMap,
486                            descriptionMap, new HashMap<Locale, String>(),
487                            new HashMap<Locale, String>(), type, StringPool.BLANK, hidden,
488                            friendlyURLMap, serviceContext);
489            }
490    
491            /**
492             * Deletes the layout, its child layouts, and its associated resources.
493             *
494             * @param layout the layout
495             * @param updateLayoutSet whether the layout set's page counter needs to be
496             *        updated
497             * @param serviceContext the service context to be applied
498             */
499            @Override
500            @SystemEvent(
501                    action = SystemEventConstants.ACTION_SKIP,
502                    type = SystemEventConstants.TYPE_DELETE
503            )
504            public void deleteLayout(
505                            Layout layout, boolean updateLayoutSet,
506                            ServiceContext serviceContext)
507                    throws PortalException {
508    
509                    // First layout validation
510    
511                    if (layout.getParentLayoutId() ==
512                                    LayoutConstants.DEFAULT_PARENT_LAYOUT_ID) {
513    
514                            List<Layout> rootLayouts = layoutPersistence.findByG_P_P(
515                                    layout.getGroupId(), layout.isPrivateLayout(),
516                                    LayoutConstants.DEFAULT_PARENT_LAYOUT_ID, 0, 2);
517    
518                            if (rootLayouts.size() > 1) {
519                                    Layout firstLayout = rootLayouts.get(0);
520    
521                                    if (firstLayout.getLayoutId() == layout.getLayoutId()) {
522                                            Layout secondLayout = rootLayouts.get(1);
523    
524                                            layoutLocalServiceHelper.validateFirstLayout(secondLayout);
525                                    }
526                            }
527                    }
528    
529                    // Child layouts
530    
531                    List<Layout> childLayouts = layoutPersistence.findByG_P_P(
532                            layout.getGroupId(), layout.isPrivateLayout(),
533                            layout.getLayoutId());
534    
535                    for (Layout childLayout : childLayouts) {
536                            layoutLocalService.deleteLayout(
537                                    childLayout, updateLayoutSet, serviceContext);
538                    }
539    
540                    // Layout friendly URLs
541    
542                    layoutFriendlyURLLocalService.deleteLayoutFriendlyURLs(
543                            layout.getPlid());
544    
545                    // Portlet preferences
546    
547                    portletPreferencesLocalService.deletePortletPreferencesByPlid(
548                            layout.getPlid());
549    
550                    // Subscriptions
551    
552                    subscriptionLocalService.deleteSubscriptions(
553                            layout.getCompanyId(), Layout.class.getName(), layout.getPlid());
554    
555                    // Asset
556    
557                    assetEntryLocalService.deleteEntry(
558                            Layout.class.getName(), layout.getPlid());
559    
560                    // Ratings
561    
562                    ratingsStatsLocalService.deleteStats(
563                            Layout.class.getName(), layout.getPlid());
564    
565                    // Expando
566    
567                    expandoRowLocalService.deleteRows(layout.getPlid());
568    
569                    // Icon
570    
571                    imageLocalService.deleteImage(layout.getIconImageId());
572    
573                    // Scope group
574    
575                    Group scopeGroup = layout.getScopeGroup();
576    
577                    if (scopeGroup != null) {
578                            groupLocalService.deleteGroup(scopeGroup.getGroupId());
579                    }
580    
581                    // Resources
582    
583                    String primKey =
584                            layout.getPlid() + PortletConstants.LAYOUT_SEPARATOR + "%";
585    
586                    List<ResourcePermission> resourcePermissions =
587                            resourcePermissionPersistence.findByC_LikeP(
588                                    layout.getCompanyId(), primKey);
589    
590                    for (ResourcePermission resourcePermission : resourcePermissions) {
591                            resourcePermissionLocalService.deleteResourcePermission(
592                                    resourcePermission);
593                    }
594    
595                    resourceLocalService.deleteResource(
596                            layout.getCompanyId(), Layout.class.getName(),
597                            ResourceConstants.SCOPE_INDIVIDUAL, layout.getPlid());
598    
599                    // Layout
600    
601                    layoutPersistence.remove(layout);
602    
603                    // Layout set
604    
605                    if (updateLayoutSet) {
606                            layoutSetLocalService.updatePageCount(
607                                    layout.getGroupId(), layout.isPrivateLayout());
608                    }
609    
610                    // System event
611    
612                    SystemEventHierarchyEntry systemEventHierarchyEntry =
613                            SystemEventHierarchyEntryThreadLocal.peek();
614    
615                    if ((systemEventHierarchyEntry != null) &&
616                            systemEventHierarchyEntry.hasTypedModel(
617                                    Layout.class.getName(), layout.getPlid())) {
618    
619                            systemEventHierarchyEntry.setExtraDataValue(
620                                    "privateLayout", StringUtil.valueOf(layout.isPrivateLayout()));
621                    }
622            }
623    
624            /**
625             * Deletes the layout with the primary key, also deleting the layout's child
626             * layouts, and associated resources.
627             *
628             * @param groupId the primary key of the group
629             * @param privateLayout whether the layout is private to the group
630             * @param layoutId the primary key of the layout
631             * @param serviceContext the service context to be applied
632             */
633            @Override
634            public void deleteLayout(
635                            long groupId, boolean privateLayout, long layoutId,
636                            ServiceContext serviceContext)
637                    throws PortalException {
638    
639                    Layout layout = layoutPersistence.findByG_P_L(
640                            groupId, privateLayout, layoutId);
641    
642                    layoutLocalService.deleteLayout(layout, true, serviceContext);
643            }
644    
645            /**
646             * Deletes the layout with the plid, also deleting the layout's child
647             * layouts, and associated resources.
648             *
649             * @param plid the primary key of the layout
650             * @param serviceContext the service context to be applied
651             */
652            @Override
653            public void deleteLayout(long plid, ServiceContext serviceContext)
654                    throws PortalException {
655    
656                    Layout layout = layoutPersistence.findByPrimaryKey(plid);
657    
658                    layoutLocalService.deleteLayout(layout, true, serviceContext);
659            }
660    
661            /**
662             * Deletes the group's private or non-private layouts, also deleting the
663             * layouts' child layouts, and associated resources.
664             *
665             * @param groupId the primary key of the group
666             * @param privateLayout whether the layout is private to the group
667             * @param serviceContext the service context to be applied. The parent
668             *        layout set's page count will be updated by default, unless an
669             *        attribute named <code>updatePageCount</code> is set to
670             *        <code>false</code>.
671             */
672            @Override
673            public void deleteLayouts(
674                            long groupId, boolean privateLayout, ServiceContext serviceContext)
675                    throws PortalException {
676    
677                    // Layouts
678    
679                    List<Layout> layouts = layoutPersistence.findByG_P_P(
680                            groupId, privateLayout, LayoutConstants.DEFAULT_PARENT_LAYOUT_ID,
681                            QueryUtil.ALL_POS, QueryUtil.ALL_POS,
682                            new LayoutPriorityComparator(false));
683    
684                    for (Layout layout : layouts) {
685                            try {
686                                    layoutLocalService.deleteLayout(layout, false, serviceContext);
687                            }
688                            catch (NoSuchLayoutException nsle) {
689                            }
690                    }
691    
692                    // Layout set
693    
694                    if (GetterUtil.getBoolean(
695                                    serviceContext.getAttribute("updatePageCount"), true)) {
696    
697                            layoutSetLocalService.updatePageCount(groupId, privateLayout);
698                    }
699    
700                    // Counter
701    
702                    counterLocalService.reset(getCounterName(groupId, privateLayout));
703            }
704    
705            /**
706             * Exports layouts with the primary keys and criteria as a byte array.
707             *
708             * @param      groupId the primary key of the group
709             * @param      privateLayout whether the layout is private to the group
710             * @param      layoutIds the primary keys of the layouts to be exported
711             * @param      parameterMap the mapping of parameters indicating which
712             *             information to export. For information on the keys used in
713             *             the map see {@link
714             *             com.liferay.portlet.exportimport.lar.PortletDataHandlerKeys}.
715             * @param      startDate the export's start date
716             * @param      endDate the export's end date
717             * @return     the layouts as a byte array
718             * @throws     PortalException
719             * @deprecated As of 7.0.0, with no direct replacement
720             */
721            @Deprecated
722            @Override
723            public byte[] exportLayouts(
724                            long groupId, boolean privateLayout, long[] layoutIds,
725                            Map<String, String[]> parameterMap, Date startDate, Date endDate)
726                    throws PortalException {
727    
728                    throw new UnsupportedOperationException();
729            }
730    
731            /**
732             * Exports all layouts that match the criteria as a byte array.
733             *
734             * @param      groupId the primary key of the group
735             * @param      privateLayout whether the layout is private to the group
736             * @param      parameterMap the mapping of parameters indicating which
737             *             information to export. For information on the keys used in
738             *             the map see {@link
739             *             com.liferay.portlet.exportimport.lar.PortletDataHandlerKeys}.
740             * @param      startDate the export's start date
741             * @param      endDate the export's end date
742             * @return     the layout as a byte array
743             * @throws     PortalException
744             * @deprecated As of 7.0.0, with no direct replacement
745             */
746            @Deprecated
747            @Override
748            public byte[] exportLayouts(
749                            long groupId, boolean privateLayout,
750                            Map<String, String[]> parameterMap, Date startDate, Date endDate)
751                    throws PortalException {
752    
753                    throw new UnsupportedOperationException();
754            }
755    
756            /**
757             * @throws     PortalException
758             * @deprecated As of 7.0.0, replaced by {@link
759             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#exportLayoutsAsFile(
760             *             ExportImportConfiguration)}
761             */
762            @Deprecated
763            @Override
764            public File exportLayoutsAsFile(
765                            ExportImportConfiguration exportImportConfiguration)
766                    throws PortalException {
767    
768                    throw new UnsupportedOperationException();
769            }
770    
771            /**
772             * Exports the layouts that match the primary keys and criteria as a file.
773             *
774             * @param      groupId the primary key of the group
775             * @param      privateLayout whether the layout is private to the group
776             * @param      layoutIds the primary keys of the layouts to be exported
777             *             (optionally <code>null</code>)
778             * @param      parameterMap the mapping of parameters indicating which
779             *             information to export. For information on the keys used in
780             *             the map see {@link
781             *             com.liferay.portlet.exportimport.lar.PortletDataHandlerKeys}.
782             * @param      startDate the export's start date
783             * @param      endDate the export's end date
784             * @return     the layouts as a File
785             * @throws     PortalException
786             * @deprecated As of 7.0.0, with no direct replacement
787             */
788            @Deprecated
789            @Override
790            public File exportLayoutsAsFile(
791                            long groupId, boolean privateLayout, long[] layoutIds,
792                            Map<String, String[]> parameterMap, Date startDate, Date endDate)
793                    throws PortalException {
794    
795                    throw new UnsupportedOperationException();
796            }
797    
798            /**
799             * @throws     PortalException
800             * @deprecated As of 7.0.0, replaced by {@link
801             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#exportLayoutsAsFileInBackground(
802             *             long, ExportImportConfiguration)}
803             */
804            @Deprecated
805            @Override
806            public long exportLayoutsAsFileInBackground(
807                            long userId, ExportImportConfiguration exportImportConfiguration)
808                    throws PortalException {
809    
810                    throw new UnsupportedOperationException();
811            }
812    
813            /**
814             * @throws     PortalException
815             * @deprecated As of 7.0.0, replaced by {@link
816             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#exportLayoutsAsFileInBackground(
817             *             long, long)}
818             */
819            @Deprecated
820            @Override
821            public long exportLayoutsAsFileInBackground(
822                            long userId, long exportImportConfigurationId)
823                    throws PortalException {
824    
825                    throw new UnsupportedOperationException();
826            }
827    
828            /**
829             * @throws     PortalException
830             * @deprecated As of 7.0.0, with no direct replacement
831             */
832            @Deprecated
833            @Override
834            public long exportLayoutsAsFileInBackground(
835                            long userId, String taskName, long groupId, boolean privateLayout,
836                            long[] layoutIds, Map<String, String[]> parameterMap,
837                            Date startDate, Date endDate)
838                    throws PortalException {
839    
840                    throw new UnsupportedOperationException();
841            }
842    
843            /**
844             * @throws     PortalException
845             * @deprecated As of 7.0.0, with no direct replacement
846             */
847            @Deprecated
848            @Override
849            public long exportLayoutsAsFileInBackground(
850                            long userId, String taskName, long groupId, boolean privateLayout,
851                            long[] layoutIds, Map<String, String[]> parameterMap,
852                            Date startDate, Date endDate, String fileName)
853                    throws PortalException {
854    
855                    throw new UnsupportedOperationException();
856            }
857    
858            /**
859             * Exports the portlet information (categories, permissions, ... etc.) as a
860             * byte array.
861             *
862             * @param      plid the primary key of the layout
863             * @param      groupId the primary key of the group
864             * @param      portletId the primary key of the portlet
865             * @param      parameterMap the mapping of parameters indicating which
866             *             information to export. For information on the keys used in
867             *             the map see {@link
868             *             com.liferay.portlet.exportimport.lar.PortletDataHandlerKeys}.
869             * @param      startDate the export's start date
870             * @param      endDate the export's end date
871             * @return     the portlet information as a byte array
872             * @throws     PortalException
873             * @deprecated As of 7.0.0, with no direct replacement
874             */
875            @Deprecated
876            @Override
877            public byte[] exportPortletInfo(
878                            long plid, long groupId, String portletId,
879                            Map<String, String[]> parameterMap, Date startDate, Date endDate)
880                    throws PortalException {
881    
882                    throw new UnsupportedOperationException();
883            }
884    
885            /**
886             * @throws     PortalException
887             * @deprecated As of 7.0.0, with no direct replacement
888             */
889            @Deprecated
890            @Override
891            public byte[] exportPortletInfo(
892                            long companyId, String portletId,
893                            Map<String, String[]> parameterMap, Date startDate, Date endDate)
894                    throws PortalException {
895    
896                    throw new UnsupportedOperationException();
897            }
898    
899            /**
900             * @throws     PortalException
901             * @deprecated As of 7.0.0, replaced by {@link
902             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#exportPortletInfoAsFile(
903             *             ExportImportConfiguration)}}
904             */
905            @Deprecated
906            @Override
907            public File exportPortletInfoAsFile(
908                            ExportImportConfiguration exportImportConfiguration)
909                    throws PortalException {
910    
911                    throw new UnsupportedOperationException();
912            }
913    
914            /**
915             * Exports the portlet information (categories, permissions, ... etc.) as a
916             * file.
917             *
918             * @param      plid the primary key of the layout
919             * @param      groupId the primary key of the group
920             * @param      portletId the primary key of the portlet
921             * @param      parameterMap the mapping of parameters indicating which
922             *             information to export. For information on the keys used in
923             *             the map see {@link
924             *             com.liferay.portlet.exportimport.lar.PortletDataHandlerKeys}.
925             * @param      startDate the export's start date
926             * @param      endDate the export's end date
927             * @return     the portlet information as a file
928             * @throws     PortalException
929             * @deprecated As of 7.0.0, with no direct replacement
930             */
931            @Deprecated
932            @Override
933            public File exportPortletInfoAsFile(
934                            long plid, long groupId, String portletId,
935                            Map<String, String[]> parameterMap, Date startDate, Date endDate)
936                    throws PortalException {
937    
938                    throw new UnsupportedOperationException();
939            }
940    
941            /**
942             * @throws     PortalException
943             * @deprecated As of 7.0.0, with no direct replacement
944             */
945            @Deprecated
946            @Override
947            public File exportPortletInfoAsFile(
948                            long companyId, String portletId,
949                            Map<String, String[]> parameterMap, Date startDate, Date endDate)
950                    throws PortalException {
951    
952                    throw new UnsupportedOperationException();
953            }
954    
955            /**
956             * @throws     PortalException
957             * @deprecated As of 7.0.0, replaced by {@link
958             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#exportPortletInfoAsFileInBackground(
959             *             long, ExportImportConfiguration)}}
960             */
961            @Deprecated
962            @Override
963            public long exportPortletInfoAsFileInBackground(
964                            long userId, ExportImportConfiguration exportImportConfiguration)
965                    throws PortalException {
966    
967                    throw new UnsupportedOperationException();
968            }
969    
970            /**
971             * @throws     PortalException
972             * @deprecated As of 7.0.0, replaced by {@link
973             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#exportPortletInfoAsFileInBackground(
974             *             long, long)}}
975             */
976            @Deprecated
977            @Override
978            public long exportPortletInfoAsFileInBackground(
979                            long userId, long exportImportConfigurationId)
980                    throws PortalException {
981    
982                    throw new UnsupportedOperationException();
983            }
984    
985            /**
986             * @throws     PortalException
987             * @deprecated As of 7.0.0, with no direct replacement
988             */
989            @Deprecated
990            @Override
991            public long exportPortletInfoAsFileInBackground(
992                            long userId, String taskName, long plid, long groupId,
993                            String portletId, Map<String, String[]> parameterMap,
994                            Date startDate, Date endDate, String fileName)
995                    throws PortalException {
996    
997                    throw new UnsupportedOperationException();
998            }
999    
1000            /**
1001             * @throws     PortalException
1002             * @deprecated As of 7.0.0, with no direct replacement
1003             */
1004            @Deprecated
1005            @Override
1006            public long exportPortletInfoAsFileInBackground(
1007                            long userId, String taskName, String portletId,
1008                            Map<String, String[]> parameterMap, Date startDate, Date endDate,
1009                            String fileName)
1010                    throws PortalException {
1011    
1012                    throw new UnsupportedOperationException();
1013            }
1014    
1015            @Override
1016            public Layout fetchFirstLayout(
1017                    long groupId, boolean privateLayout, long parentLayoutId) {
1018    
1019                    return layoutPersistence.fetchByG_P_P_First(
1020                            groupId, privateLayout, parentLayoutId,
1021                            new LayoutPriorityComparator());
1022            }
1023    
1024            @Override
1025            public Layout fetchLayout(
1026                    long groupId, boolean privateLayout, long layoutId) {
1027    
1028                    return layoutPersistence.fetchByG_P_L(groupId, privateLayout, layoutId);
1029            }
1030    
1031            @Override
1032            public Layout fetchLayoutByFriendlyURL(
1033                    long groupId, boolean privateLayout, String friendlyURL) {
1034    
1035                    return layoutPersistence.fetchByG_P_F(
1036                            groupId, privateLayout, friendlyURL);
1037            }
1038    
1039            /**
1040             * Returns the primary key of the default layout for the group
1041             *
1042             * @param  groupId the primary key of the group
1043             * @return the primary key of the default layout for the group (optionally
1044             *         {@link LayoutConstants#DEFAULT_PLID})
1045             */
1046            @Override
1047            public long getDefaultPlid(long groupId) {
1048                    if (groupId > 0) {
1049                            List<Layout> layouts = layoutPersistence.findByGroupId(
1050                                    groupId, 0, 1);
1051    
1052                            if (!layouts.isEmpty()) {
1053                                    Layout layout = layouts.get(0);
1054    
1055                                    return layout.getPlid();
1056                            }
1057                    }
1058    
1059                    return LayoutConstants.DEFAULT_PLID;
1060            }
1061    
1062            /**
1063             * Returns primary key of the matching default layout for the group
1064             *
1065             * @param  groupId the primary key of the group
1066             * @param  privateLayout whether the layout is private to the group
1067             * @return the primary key of the default layout for the group; {@link
1068             *         LayoutConstants#DEFAULT_PLID}) otherwise
1069             */
1070            @Override
1071            public long getDefaultPlid(long groupId, boolean privateLayout) {
1072                    if (groupId > 0) {
1073                            List<Layout> layouts = layoutPersistence.findByG_P(
1074                                    groupId, privateLayout, 0, 1);
1075    
1076                            if (!layouts.isEmpty()) {
1077                                    Layout layout = layouts.get(0);
1078    
1079                                    return layout.getPlid();
1080                            }
1081                    }
1082    
1083                    return LayoutConstants.DEFAULT_PLID;
1084            }
1085    
1086            /**
1087             * Returns primary key of the default portlet layout for the group
1088             *
1089             * @param  groupId the primary key of the group
1090             * @param  privateLayout whether the layout is private to the group
1091             * @param  portletId the primary key of the portlet
1092             * @return the primary key of the default portlet layout for the group;
1093             *         {@link LayoutConstants#DEFAULT_PLID} otherwise
1094             * @throws PortalException
1095             */
1096            @Override
1097            public long getDefaultPlid(
1098                            long groupId, boolean privateLayout, String portletId)
1099                    throws PortalException {
1100    
1101                    if (groupId > 0) {
1102                            List<Layout> layouts = layoutPersistence.findByG_P(
1103                                    groupId, privateLayout);
1104    
1105                            for (Layout layout : layouts) {
1106                                    if (layout.isTypePortlet()) {
1107                                            LayoutTypePortlet layoutTypePortlet =
1108                                                    (LayoutTypePortlet)layout.getLayoutType();
1109    
1110                                            if (layoutTypePortlet.hasPortletId(portletId)) {
1111                                                    return layout.getPlid();
1112                                            }
1113                                    }
1114                            }
1115                    }
1116    
1117                    return LayoutConstants.DEFAULT_PLID;
1118            }
1119    
1120            /**
1121             * Returns the layout for the friendly URL
1122             *
1123             * @param  groupId the primary key of the group
1124             * @param  privateLayout whether the layout is private to the group
1125             * @param  friendlyURL the friendly URL of the layout
1126             * @return the layout for the friendly URL
1127             */
1128            @Override
1129            public Layout getFriendlyURLLayout(
1130                            long groupId, boolean privateLayout, String friendlyURL)
1131                    throws PortalException {
1132    
1133                    if (Validator.isNull(friendlyURL)) {
1134                            StringBundler sb = new StringBundler(5);
1135    
1136                            sb.append("{groupId=");
1137                            sb.append(groupId);
1138                            sb.append(", privateLayout=");
1139                            sb.append(privateLayout);
1140                            sb.append("}");
1141    
1142                            throw new NoSuchLayoutException(sb.toString());
1143                    }
1144    
1145                    friendlyURL = layoutLocalServiceHelper.getFriendlyURL(friendlyURL);
1146    
1147                    Layout layout = null;
1148    
1149                    List<LayoutFriendlyURL> layoutFriendlyURLs =
1150                            layoutFriendlyURLPersistence.findByG_P_F(
1151                                    groupId, privateLayout, friendlyURL, 0, 1);
1152    
1153                    if (!layoutFriendlyURLs.isEmpty()) {
1154                            LayoutFriendlyURL layoutFriendlyURL = layoutFriendlyURLs.get(0);
1155    
1156                            layout = layoutPersistence.findByPrimaryKey(
1157                                    layoutFriendlyURL.getPlid());
1158                    }
1159    
1160                    if ((layout == null) && friendlyURL.startsWith(StringPool.SLASH) &&
1161                            Validator.isNumber(friendlyURL.substring(1))) {
1162    
1163                            long layoutId = GetterUtil.getLong(friendlyURL.substring(1));
1164    
1165                            layout = layoutPersistence.fetchByG_P_L(
1166                                    groupId, privateLayout, layoutId);
1167                    }
1168    
1169                    if (layout == null) {
1170                            StringBundler sb = new StringBundler(7);
1171    
1172                            sb.append("{groupId=");
1173                            sb.append(groupId);
1174                            sb.append(", privateLayout=");
1175                            sb.append(privateLayout);
1176                            sb.append(", friendlyURL=");
1177                            sb.append(friendlyURL);
1178                            sb.append("}");
1179    
1180                            throw new NoSuchLayoutException(sb.toString());
1181                    }
1182    
1183                    return layout;
1184            }
1185    
1186            /**
1187             * Returns the layout matching the primary key, group, and privacy; throws a
1188             * {@link NoSuchLayoutException} otherwise.
1189             *
1190             * @param  groupId the primary key of the group
1191             * @param  privateLayout whether the layout is private to the group
1192             * @param  layoutId the primary key of the layout
1193             * @return the matching layout
1194             */
1195            @Override
1196            public Layout getLayout(long groupId, boolean privateLayout, long layoutId)
1197                    throws PortalException {
1198    
1199                    return layoutPersistence.findByG_P_L(groupId, privateLayout, layoutId);
1200            }
1201    
1202            /**
1203             * Returns the layout for the icon image; throws a {@link
1204             * NoSuchLayoutException} otherwise.
1205             *
1206             * @param  iconImageId the primary key of the icon image
1207             * @return Returns the layout for the icon image
1208             */
1209            @Override
1210            public Layout getLayoutByIconImageId(long iconImageId)
1211                    throws PortalException {
1212    
1213                    return layoutPersistence.findByIconImageId(iconImageId);
1214            }
1215    
1216            /**
1217             * Returns all the layouts belonging to the group.
1218             *
1219             * @param  groupId the primary key of the group
1220             * @param  privateLayout whether the layout is private to the group
1221             * @return the matching layouts, or <code>null</code> if no matches were
1222             *         found
1223             */
1224            @Override
1225            public List<Layout> getLayouts(long groupId, boolean privateLayout) {
1226                    return layoutPersistence.findByG_P(groupId, privateLayout);
1227            }
1228    
1229            /**
1230             * Returns all the layouts belonging to the group that are children of the
1231             * parent layout.
1232             *
1233             * @param  groupId the primary key of the group
1234             * @param  privateLayout whether the layout is private to the group
1235             * @param  parentLayoutId the primary key of the parent layout
1236             * @return the matching layouts, or <code>null</code> if no matches were
1237             *         found
1238             */
1239            @Override
1240            public List<Layout> getLayouts(
1241                    long groupId, boolean privateLayout, long parentLayoutId) {
1242    
1243                    return layoutPersistence.findByG_P_P(
1244                            groupId, privateLayout, parentLayoutId);
1245            }
1246    
1247            /**
1248             * Returns a range of all the layouts belonging to the group that are
1249             * children of the parent layout.
1250             *
1251             * <p>
1252             * Useful when paginating results. Returns a maximum of <code>end -
1253             * start</code> instances. <code>start</code> and <code>end</code> are not
1254             * primary keys, they are indexes in the result set. Thus, <code>0</code>
1255             * refers to the first result in the set. Setting both <code>start</code>
1256             * and <code>end</code> to {@link QueryUtil#ALL_POS} will return the full
1257             * result set.
1258             * </p>
1259             *
1260             * @param  groupId the primary key of the group
1261             * @param  privateLayout whether the layout is private to the group
1262             * @param  parentLayoutId the primary key of the parent layout
1263             * @param  incomplete whether the layout is incomplete
1264             * @param  start the lower bound of the range of layouts
1265             * @param  end the upper bound of the range of layouts (not inclusive)
1266             * @return the matching layouts, or <code>null</code> if no matches were
1267             *         found
1268             */
1269            @Override
1270            public List<Layout> getLayouts(
1271                    long groupId, boolean privateLayout, long parentLayoutId,
1272                    boolean incomplete, int start, int end) {
1273    
1274                    return layoutPersistence.findByG_P_P(
1275                            groupId, privateLayout, parentLayoutId, start, end);
1276            }
1277    
1278            /**
1279             * Returns all the layouts that match the layout IDs and belong to the
1280             * group.
1281             *
1282             * @param  groupId the primary key of the group
1283             * @param  privateLayout whether the layout is private to the group
1284             * @param  layoutIds the primary keys of the layouts
1285             * @return the matching layouts, or an empty list if no matches were found
1286             */
1287            @Override
1288            public List<Layout> getLayouts(
1289                            long groupId, boolean privateLayout, long[] layoutIds)
1290                    throws PortalException {
1291    
1292                    List<Layout> layouts = new ArrayList<>();
1293    
1294                    for (long layoutId : layoutIds) {
1295                            Layout layout = getLayout(groupId, privateLayout, layoutId);
1296    
1297                            layouts.add(layout);
1298                    }
1299    
1300                    return layouts;
1301            }
1302    
1303            /**
1304             * Returns all the layouts that match the type and belong to the group.
1305             *
1306             * @param  groupId the primary key of the group
1307             * @param  privateLayout whether the layout is private to the group
1308             * @param  type the type of the layouts (optionally {@link
1309             *         LayoutConstants#TYPE_PORTLET})
1310             * @return the matching layouts, or <code>null</code> if no matches were
1311             *         found
1312             */
1313            @Override
1314            public List<Layout> getLayouts(
1315                    long groupId, boolean privateLayout, String type) {
1316    
1317                    return layoutPersistence.findByG_P_T(groupId, privateLayout, type);
1318            }
1319    
1320            /**
1321             * Returns the layout references for all the layouts that belong to the
1322             * company and belong to the portlet that matches the preferences.
1323             *
1324             * @param  companyId the primary key of the company
1325             * @param  portletId the primary key of the portlet
1326             * @param  preferencesKey the portlet's preference key
1327             * @param  preferencesValue the portlet's preference value
1328             * @return the layout references of the matching layouts
1329             */
1330            @Override
1331            public LayoutReference[] getLayouts(
1332                    long companyId, String portletId, String preferencesKey,
1333                    String preferencesValue) {
1334    
1335                    List<LayoutReference> layoutReferences = layoutFinder.findByC_P_P(
1336                            companyId, portletId, preferencesKey, preferencesValue);
1337    
1338                    return layoutReferences.toArray(
1339                            new LayoutReference[layoutReferences.size()]);
1340            }
1341    
1342            @Override
1343            public List<Layout> getLayoutsByLayoutPrototypeUuid(
1344                    String layoutPrototypeUuid) {
1345    
1346                    return layoutPersistence.findByLayoutPrototypeUuid(layoutPrototypeUuid);
1347            }
1348    
1349            @Override
1350            public int getLayoutsByLayoutPrototypeUuidCount(
1351                    String layoutPrototypeUuid) {
1352    
1353                    return layoutPersistence.countByLayoutPrototypeUuid(
1354                            layoutPrototypeUuid);
1355            }
1356    
1357            @Override
1358            public int getLayoutsCount(Group group, boolean privateLayout)
1359                    throws PortalException {
1360    
1361                    return getLayoutsCount(group, privateLayout, true);
1362            }
1363    
1364            @Override
1365            public int getLayoutsCount(
1366                            Group group, boolean privateLayout, boolean includeUserGroups)
1367                    throws PortalException {
1368    
1369                    LayoutSet layoutSet = layoutSetPersistence.findByG_P(
1370                            group.getGroupId(), privateLayout);
1371    
1372                    int count = layoutSet.getPageCount();
1373    
1374                    if (!group.isUser() || !includeUserGroups) {
1375                            return count;
1376                    }
1377    
1378                    long[] userGroupIds = userPersistence.getUserGroupPrimaryKeys(
1379                            group.getClassPK());
1380    
1381                    if (userGroupIds.length != 0) {
1382                            long userGroupClassNameId = classNameLocalService.getClassNameId(
1383                                    UserGroup.class);
1384    
1385                            for (long userGroupId : userGroupIds) {
1386                                    Group userGroupGroup = groupPersistence.findByC_C_C(
1387                                            group.getCompanyId(), userGroupClassNameId, userGroupId);
1388    
1389                                    layoutSet = layoutSetPersistence.findByG_P(
1390                                            userGroupGroup.getGroupId(), privateLayout);
1391    
1392                                    count += layoutSet.getPageCount();
1393                            }
1394                    }
1395    
1396                    return count;
1397            }
1398    
1399            @Override
1400            public int getLayoutsCount(
1401                    Group group, boolean privateLayout, long parentLayoutId) {
1402    
1403                    return layoutPersistence.countByG_P_P(
1404                            group.getGroupId(), privateLayout, parentLayoutId);
1405            }
1406    
1407            @Override
1408            public int getLayoutsCount(User user, boolean privateLayout)
1409                    throws PortalException {
1410    
1411                    return getLayoutsCount(user, privateLayout, true);
1412            }
1413    
1414            @Override
1415            public int getLayoutsCount(
1416                            User user, boolean privateLayout, boolean includeUserGroups)
1417                    throws PortalException {
1418    
1419                    long classNameId = classNameLocalService.getClassNameId(User.class);
1420    
1421                    Group group = groupPersistence.findByC_C_C(
1422                            user.getCompanyId(), classNameId, user.getUserId());
1423    
1424                    return getLayoutsCount(group, privateLayout, includeUserGroups);
1425            }
1426    
1427            /**
1428             * Returns the primary key to use for the next layout.
1429             *
1430             * @param  groupId the primary key of the group
1431             * @param  privateLayout whether the layout is private to the group
1432             * @return the primary key to use for the next layout
1433             */
1434            @Override
1435            public long getNextLayoutId(long groupId, boolean privateLayout) {
1436                    long nextLayoutId = counterLocalService.increment(
1437                            getCounterName(groupId, privateLayout));
1438    
1439                    if (nextLayoutId == 1) {
1440                            List<Layout> layouts = layoutPersistence.findByG_P(
1441                                    groupId, privateLayout, 0, 1, new LayoutComparator());
1442    
1443                            if (!layouts.isEmpty()) {
1444                                    Layout layout = layouts.get(0);
1445    
1446                                    nextLayoutId = layout.getLayoutId() + 1;
1447    
1448                                    counterLocalService.reset(
1449                                            getCounterName(groupId, privateLayout), nextLayoutId);
1450                            }
1451                    }
1452    
1453                    return nextLayoutId;
1454            }
1455    
1456            /**
1457             * Returns all the layouts without resource permissions
1458             *
1459             * @param  roleId the primary key of the role
1460             * @return all the layouts without resource permissions
1461             */
1462            @Override
1463            public List<Layout> getNoPermissionLayouts(long roleId) {
1464                    return layoutFinder.findByNoPermissions(roleId);
1465            }
1466    
1467            /**
1468             * Returns all the layouts whose friendly URLs are <code>null</code>
1469             *
1470             * @return all the layouts whose friendly URLs are <code>null</code>
1471             */
1472            @Override
1473            public List<Layout> getNullFriendlyURLLayouts() {
1474                    return layoutFinder.findByNullFriendlyURL();
1475            }
1476    
1477            @Override
1478            public Layout getParentLayout(Layout layout) throws PortalException {
1479                    Layout parentLayout = null;
1480    
1481                    if (layout instanceof VirtualLayout) {
1482                            VirtualLayout virtualLayout = (VirtualLayout)layout;
1483    
1484                            Layout sourceLayout = virtualLayout.getSourceLayout();
1485    
1486                            parentLayout = getLayout(
1487                                    sourceLayout.getGroupId(), sourceLayout.isPrivateLayout(),
1488                                    sourceLayout.getParentLayoutId());
1489    
1490                            parentLayout = new VirtualLayout(parentLayout, layout.getGroup());
1491                    }
1492                    else {
1493                            parentLayout = getLayout(
1494                                    layout.getGroupId(), layout.isPrivateLayout(),
1495                                    layout.getParentLayoutId());
1496                    }
1497    
1498                    return parentLayout;
1499            }
1500    
1501            /**
1502             * Returns all the layouts within scope of the group
1503             *
1504             * @param  groupId the primary key of the group
1505             * @param  privateLayout whether the layout is private to the group
1506             * @return the layouts within scope of the group
1507             */
1508            @Override
1509            public List<Layout> getScopeGroupLayouts(
1510                    long groupId, boolean privateLayout) {
1511    
1512                    return layoutFinder.findByScopeGroup(groupId, privateLayout);
1513            }
1514    
1515            @Override
1516            public boolean hasLayouts(Group group) throws PortalException {
1517                    List<LayoutSet> groupLayoutSets = layoutSetPersistence.findByGroupId(
1518                            group.getGroupId());
1519    
1520                    for (LayoutSet layoutSet : groupLayoutSets) {
1521                            if (layoutSet.getPageCount() > 0) {
1522                                    return true;
1523                            }
1524                    }
1525    
1526                    if (!group.isUser()) {
1527                            return false;
1528                    }
1529    
1530                    long[] userGroupIds = userPersistence.getUserGroupPrimaryKeys(
1531                            group.getClassPK());
1532    
1533                    if (userGroupIds.length != 0) {
1534                            long userGroupClassNameId = classNameLocalService.getClassNameId(
1535                                    UserGroup.class);
1536    
1537                            for (long userGroupId : userGroupIds) {
1538                                    Group userGroupGroup = groupPersistence.findByC_C_C(
1539                                            group.getCompanyId(), userGroupClassNameId, userGroupId);
1540    
1541                                    List<LayoutSet> userGroupGroupLayoutSets =
1542                                            layoutSetPersistence.findByGroupId(
1543                                                    userGroupGroup.getGroupId());
1544    
1545                                    for (LayoutSet layoutSet : userGroupGroupLayoutSets) {
1546                                            if (layoutSet.getPageCount() > 0) {
1547                                                    return true;
1548                                            }
1549                                    }
1550                            }
1551                    }
1552    
1553                    return false;
1554            }
1555    
1556            @Override
1557            public boolean hasLayouts(Group group, boolean privateLayout)
1558                    throws PortalException {
1559    
1560                    return hasLayouts(group, privateLayout, true);
1561            }
1562    
1563            @Override
1564            public boolean hasLayouts(
1565                            Group group, boolean privateLayout, boolean includeUserGroups)
1566                    throws PortalException {
1567    
1568                    LayoutSet layoutSet = layoutSetPersistence.findByG_P(
1569                            group.getGroupId(), privateLayout);
1570    
1571                    if (layoutSet.getPageCount() > 0) {
1572                            return true;
1573                    }
1574    
1575                    if (!group.isUser() || !includeUserGroups) {
1576                            return false;
1577                    }
1578    
1579                    long[] userGroupIds = userPersistence.getUserGroupPrimaryKeys(
1580                            group.getClassPK());
1581    
1582                    if (userGroupIds.length != 0) {
1583                            long userGroupClassNameId = classNameLocalService.getClassNameId(
1584                                    UserGroup.class);
1585    
1586                            for (long userGroupId : userGroupIds) {
1587                                    Group userGroupGroup = groupPersistence.findByC_C_C(
1588                                            group.getCompanyId(), userGroupClassNameId, userGroupId);
1589    
1590                                    layoutSet = layoutSetPersistence.findByG_P(
1591                                            userGroupGroup.getGroupId(), privateLayout);
1592    
1593                                    if (layoutSet.getPageCount() > 0) {
1594                                            return true;
1595                                    }
1596                            }
1597                    }
1598    
1599                    return false;
1600            }
1601    
1602            /**
1603             * Returns <code>true</code> if the group has any layouts;
1604             * <code>false</code> otherwise.
1605             *
1606             * @param  groupId the primary key of the group
1607             * @param  privateLayout whether the layout is private to the group
1608             * @param  parentLayoutId the primary key of the parent layout
1609             * @return <code>true</code> if the group has any layouts;
1610             *         <code>false</code> otherwise
1611             */
1612            @Override
1613            public boolean hasLayouts(
1614                    long groupId, boolean privateLayout, long parentLayoutId) {
1615    
1616                    return layoutPersistence.countByG_P_P(
1617                            groupId, privateLayout, parentLayoutId) > 0;
1618            }
1619    
1620            @Override
1621            public boolean hasLayouts(User user, boolean privateLayout)
1622                    throws PortalException {
1623    
1624                    return hasLayouts(user, privateLayout, true);
1625            }
1626    
1627            @Override
1628            public boolean hasLayouts(
1629                            User user, boolean privateLayout, boolean includeUserGroups)
1630                    throws PortalException {
1631    
1632                    long classNameId = classNameLocalService.getClassNameId(User.class);
1633    
1634                    Group group = groupPersistence.findByC_C_C(
1635                            user.getCompanyId(), classNameId, user.getUserId());
1636    
1637                    return hasLayouts(group, privateLayout, includeUserGroups);
1638            }
1639    
1640            @Override
1641            public boolean hasLayoutSetPrototypeLayout(
1642                            long layoutSetPrototypeId, String layoutUuid)
1643                    throws PortalException {
1644    
1645                    LayoutSetPrototype layoutSetPrototype =
1646                            layoutSetPrototypeLocalService.getLayoutSetPrototype(
1647                                    layoutSetPrototypeId);
1648    
1649                    return layoutLocalServiceHelper.hasLayoutSetPrototypeLayout(
1650                            layoutSetPrototype, layoutUuid);
1651            }
1652    
1653            @Override
1654            public boolean hasLayoutSetPrototypeLayout(
1655                            String layoutSetPrototypeUuid, long companyId, String layoutUuid)
1656                    throws PortalException {
1657    
1658                    LayoutSetPrototype layoutSetPrototype =
1659                            layoutSetPrototypeLocalService.
1660                                    getLayoutSetPrototypeByUuidAndCompanyId(
1661                                            layoutSetPrototypeUuid, companyId);
1662    
1663                    return layoutLocalServiceHelper.hasLayoutSetPrototypeLayout(
1664                            layoutSetPrototype, layoutUuid);
1665            }
1666    
1667            /**
1668             * @throws     PortalException
1669             * @deprecated As of 7.0.0, replaced by {@link
1670             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#importLayouts(
1671             *             ExportImportConfiguration, File)}}
1672             */
1673            @Deprecated
1674            @Override
1675            public void importLayouts(
1676                            ExportImportConfiguration exportImportConfiguration, File file)
1677                    throws PortalException {
1678    
1679                    throw new UnsupportedOperationException();
1680            }
1681    
1682            /**
1683             * @throws     PortalException
1684             * @deprecated As of 7.0.0, replaced by {@link
1685             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#importLayouts(
1686             *             ExportImportConfiguration, InputStream)}}
1687             */
1688            @Deprecated
1689            @Override
1690            public void importLayouts(
1691                            ExportImportConfiguration exportImportConfiguration, InputStream is)
1692                    throws PortalException {
1693    
1694                    throw new UnsupportedOperationException();
1695            }
1696    
1697            /**
1698             * Imports the layouts from the byte array.
1699             *
1700             * @param      userId the primary key of the user
1701             * @param      groupId the primary key of the group
1702             * @param      privateLayout whether the layout is private to the group
1703             * @param      parameterMap the mapping of parameters indicating which
1704             *             information will be imported. For information on the keys
1705             *             used in the map see {@link
1706             *             com.liferay.portlet.exportimport.lar.PortletDataHandlerKeys}.
1707             * @param      bytes the byte array with the data
1708             * @throws     PortalException
1709             * @see        com.liferay.portlet.exportimport.lar.LayoutImporter
1710             * @deprecated As of 7.0.0, with no direct replacement
1711             */
1712            @Deprecated
1713            @Override
1714            public void importLayouts(
1715                            long userId, long groupId, boolean privateLayout,
1716                            Map<String, String[]> parameterMap, byte[] bytes)
1717                    throws PortalException {
1718    
1719                    throw new UnsupportedOperationException();
1720            }
1721    
1722            /**
1723             * Imports the layouts from the file.
1724             *
1725             * @param      userId the primary key of the user
1726             * @param      groupId the primary key of the group
1727             * @param      privateLayout whether the layout is private to the group
1728             * @param      parameterMap the mapping of parameters indicating which
1729             *             information will be imported. For information on the keys
1730             *             used in the map see {@link
1731             *             com.liferay.portlet.exportimport.lar.PortletDataHandlerKeys}.
1732             * @param      file the LAR file with the data
1733             * @throws     PortalException
1734             * @see        com.liferay.portlet.exportimport.lar.LayoutImporter
1735             * @deprecated As of 7.0.0, with no direct replacement
1736             */
1737            @Deprecated
1738            @Override
1739            public void importLayouts(
1740                            long userId, long groupId, boolean privateLayout,
1741                            Map<String, String[]> parameterMap, File file)
1742                    throws PortalException {
1743    
1744                    throw new UnsupportedOperationException();
1745            }
1746    
1747            /**
1748             * Imports the layouts from the input stream.
1749             *
1750             * @param      userId the primary key of the user
1751             * @param      groupId the primary key of the group
1752             * @param      privateLayout whether the layout is private to the group
1753             * @param      parameterMap the mapping of parameters indicating which
1754             *             information will be imported. For information on the keys
1755             *             used in the map see {@link
1756             *             com.liferay.portlet.exportimport.lar.PortletDataHandlerKeys}.
1757             * @param      is the input stream
1758             * @throws     PortalException
1759             * @see        com.liferay.portlet.exportimport.lar.LayoutImporter
1760             * @deprecated As of 7.0.0, with no direct replacement
1761             */
1762            @Deprecated
1763            @Override
1764            public void importLayouts(
1765                            long userId, long groupId, boolean privateLayout,
1766                            Map<String, String[]> parameterMap, InputStream is)
1767                    throws PortalException {
1768    
1769                    throw new UnsupportedOperationException();
1770            }
1771    
1772            /**
1773             * @throws     PortalException
1774             * @deprecated As of 7.0.0, replaced by {@link
1775             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#importLayoutsDataDeletions(
1776             *             ExportImportConfiguration, File)}
1777             */
1778            @Deprecated
1779            @Override
1780            public void importLayoutsDataDeletions(
1781                            ExportImportConfiguration exportImportConfiguration, File file)
1782                    throws PortalException {
1783    
1784                    throw new UnsupportedOperationException();
1785            }
1786    
1787            /**
1788             * @throws     PortalException
1789             * @deprecated As of 7.0.0, replaced by {@link
1790             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#importLayoutsInBackground(
1791             *             long, ExportImportConfiguration, File)}
1792             */
1793            @Deprecated
1794            @Override
1795            public long importLayoutsInBackground(
1796                            long userId, ExportImportConfiguration exportImportConfiguration,
1797                            File file)
1798                    throws PortalException {
1799    
1800                    throw new UnsupportedOperationException();
1801            }
1802    
1803            /**
1804             * @throws     PortalException
1805             * @deprecated As of 7.0.0, replaced by {@link
1806             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#importLayoutsInBackground(
1807             *             long, long, File)}
1808             */
1809            @Deprecated
1810            @Override
1811            public long importLayoutsInBackground(
1812                            long userId, long exportImportConfigurationId, File file)
1813                    throws PortalException {
1814    
1815                    throw new UnsupportedOperationException();
1816            }
1817    
1818            /**
1819             * @throws     PortalException
1820             * @deprecated As of 7.0.0, with no direct replacement
1821             */
1822            @Deprecated
1823            @Override
1824            public long importLayoutsInBackground(
1825                            long userId, String taskName, long groupId, boolean privateLayout,
1826                            Map<String, String[]> parameterMap, File file)
1827                    throws PortalException {
1828    
1829                    throw new UnsupportedOperationException();
1830            }
1831    
1832            /**
1833             * @throws     PortalException
1834             * @deprecated As of 7.0.0, with no direct replacement
1835             */
1836            @Deprecated
1837            @Override
1838            public long importLayoutsInBackground(
1839                            long userId, String taskName, long groupId, boolean privateLayout,
1840                            Map<String, String[]> parameterMap, InputStream is)
1841                    throws PortalException {
1842    
1843                    throw new UnsupportedOperationException();
1844            }
1845    
1846            /**
1847             * @throws     PortalException
1848             * @deprecated As of 7.0.0, replaced by {@link
1849             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#importPortletDataDeletions(
1850             *             ExportImportConfiguration, File)}
1851             */
1852            @Deprecated
1853            @Override
1854            public void importPortletDataDeletions(
1855                            ExportImportConfiguration exportImportConfiguration, File file)
1856                    throws PortalException {
1857    
1858                    throw new UnsupportedOperationException();
1859            }
1860    
1861            /**
1862             * @throws     PortalException
1863             * @deprecated As of 7.0.0, replaced by {@link
1864             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#importPortletInfo(
1865             *             ExportImportConfiguration, File)}
1866             */
1867            @Deprecated
1868            @Override
1869            public void importPortletInfo(
1870                            ExportImportConfiguration exportImportConfiguration, File file)
1871                    throws PortalException {
1872    
1873                    throw new UnsupportedOperationException();
1874            }
1875    
1876            /**
1877             * @throws     PortalException
1878             * @deprecated As of 7.0.0, replaced by {@link
1879             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#importPortletInfo(
1880             *             ExportImportConfiguration, InputStream)}
1881             */
1882            @Deprecated
1883            @Override
1884            public void importPortletInfo(
1885                            ExportImportConfiguration exportImportConfiguration, InputStream is)
1886                    throws PortalException {
1887    
1888                    throw new UnsupportedOperationException();
1889            }
1890    
1891            /**
1892             * Imports the portlet information (categories, permissions, ... etc.) from
1893             * the file.
1894             *
1895             * @param      userId the primary key of the user
1896             * @param      plid the primary key of the target layout
1897             * @param      groupId the primary key of the target group
1898             * @param      portletId the primary key of the portlet
1899             * @param      parameterMap the mapping of parameters indicating which
1900             *             information will be imported. For information on the keys
1901             *             used in the map see {@link
1902             *             com.liferay.portlet.exportimport.lar.PortletDataHandlerKeys}.
1903             * @param      file the LAR file with the data
1904             * @throws     PortalException
1905             * @deprecated As of 7.0.0, with no direct replacement
1906             */
1907            @Deprecated
1908            @Override
1909            public void importPortletInfo(
1910                            long userId, long plid, long groupId, String portletId,
1911                            Map<String, String[]> parameterMap, File file)
1912                    throws PortalException {
1913    
1914                    throw new UnsupportedOperationException();
1915            }
1916    
1917            /**
1918             * Imports the portlet information (categories, permissions, ... etc.) from
1919             * the input stream.
1920             *
1921             * @param      userId the primary key of the user
1922             * @param      plid the primary key of the layout
1923             * @param      groupId the primary key of the group
1924             * @param      portletId the primary key of the portlet
1925             * @param      parameterMap the mapping of parameters indicating which
1926             *             information will be imported. For information on the keys
1927             *             used in the map see {@link
1928             *             com.liferay.portlet.exportimport.lar.PortletDataHandlerKeys}.
1929             * @param      is the input stream
1930             * @throws     PortalException
1931             * @deprecated As of 7.0.0, with no direct replacement
1932             */
1933            @Deprecated
1934            @Override
1935            public void importPortletInfo(
1936                            long userId, long plid, long groupId, String portletId,
1937                            Map<String, String[]> parameterMap, InputStream is)
1938                    throws PortalException {
1939    
1940                    throw new UnsupportedOperationException();
1941            }
1942    
1943            /**
1944             * @throws     PortalException
1945             * @deprecated As of 7.0.0, with no direct replacement
1946             */
1947            @Deprecated
1948            @Override
1949            public void importPortletInfo(
1950                            long userId, String portletId, Map<String, String[]> parameterMap,
1951                            File file)
1952                    throws PortalException {
1953    
1954                    throw new UnsupportedOperationException();
1955            }
1956    
1957            /**
1958             * @throws     PortalException
1959             * @deprecated As of 7.0.0, with no direct replacement
1960             */
1961            @Deprecated
1962            @Override
1963            public void importPortletInfo(
1964                            long userId, String portletId, Map<String, String[]> parameterMap,
1965                            InputStream is)
1966                    throws PortalException {
1967    
1968                    throw new UnsupportedOperationException();
1969            }
1970    
1971            /**
1972             * @throws     PortalException
1973             * @deprecated As of 7.0.0, replaced by {@link
1974             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#importPortletInfoInBackground(
1975             *             long, ExportImportConfiguration, File)}
1976             */
1977            @Deprecated
1978            @Override
1979            public long importPortletInfoInBackground(
1980                            long userId, ExportImportConfiguration exportImportConfiguration,
1981                            File file)
1982                    throws PortalException {
1983    
1984                    throw new UnsupportedOperationException();
1985            }
1986    
1987            /**
1988             * @throws     PortalException
1989             * @deprecated As of 7.0.0, replaced by {@link
1990             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#importPortletInfoInBackground(
1991             *             long, long, File)}
1992             */
1993            @Deprecated
1994            @Override
1995            public long importPortletInfoInBackground(
1996                            long userId, long exportImportConfigurationId, File file)
1997                    throws PortalException {
1998    
1999                    throw new UnsupportedOperationException();
2000            }
2001    
2002            /**
2003             * @throws     PortalException
2004             * @deprecated As of 7.0.0, with no direct replacement
2005             */
2006            @Deprecated
2007            @Override
2008            public long importPortletInfoInBackground(
2009                            long userId, String taskName, long plid, long groupId,
2010                            String portletId, Map<String, String[]> parameterMap, File file)
2011                    throws PortalException {
2012    
2013                    throw new UnsupportedOperationException();
2014            }
2015    
2016            /**
2017             * @throws     PortalException
2018             * @deprecated As of 7.0.0, with no direct replacement
2019             */
2020            @Deprecated
2021            @Override
2022            public long importPortletInfoInBackground(
2023                            long userId, String taskName, long plid, long groupId,
2024                            String portletId, Map<String, String[]> parameterMap,
2025                            InputStream is)
2026                    throws PortalException {
2027    
2028                    throw new UnsupportedOperationException();
2029            }
2030    
2031            /**
2032             * @throws     PortalException
2033             * @deprecated As of 7.0.0, with no direct replacement
2034             */
2035            @Deprecated
2036            @Override
2037            public long importPortletInfoInBackground(
2038                            long userId, String taskName, String portletId,
2039                            Map<String, String[]> parameterMap, File file)
2040                    throws PortalException {
2041    
2042                    throw new UnsupportedOperationException();
2043            }
2044    
2045            /**
2046             * @throws     PortalException
2047             * @deprecated As of 7.0.0, with no direct replacement
2048             */
2049            @Deprecated
2050            @Override
2051            public long importPortletInfoInBackground(
2052                            long userId, String taskName, String portletId,
2053                            Map<String, String[]> parameterMap, InputStream is)
2054                    throws PortalException {
2055    
2056                    throw new UnsupportedOperationException();
2057            }
2058    
2059            /**
2060             * Sets the layouts for the group, replacing and prioritizing all layouts of
2061             * the parent layout.
2062             *
2063             * @param groupId the primary key of the group
2064             * @param privateLayout whether the layout is private to the group
2065             * @param parentLayoutId the primary key of the parent layout
2066             * @param layoutIds the primary keys of the layouts
2067             * @param serviceContext the service context to be applied
2068             */
2069            @Override
2070            public void setLayouts(
2071                            long groupId, boolean privateLayout, long parentLayoutId,
2072                            long[] layoutIds, ServiceContext serviceContext)
2073                    throws PortalException {
2074    
2075                    if (layoutIds == null) {
2076                            return;
2077                    }
2078    
2079                    if (parentLayoutId == LayoutConstants.DEFAULT_PARENT_LAYOUT_ID) {
2080                            if (layoutIds.length < 1) {
2081                                    throw new RequiredLayoutException(
2082                                            RequiredLayoutException.AT_LEAST_ONE);
2083                            }
2084    
2085                            Layout layout = layoutPersistence.findByG_P_L(
2086                                    groupId, privateLayout, layoutIds[0]);
2087    
2088                            LayoutType layoutType = layout.getLayoutType();
2089    
2090                            if (!layoutType.isFirstPageable()) {
2091                                    throw new RequiredLayoutException(
2092                                            RequiredLayoutException.FIRST_LAYOUT_TYPE);
2093                            }
2094                    }
2095    
2096                    Set<Long> layoutIdsSet = new LinkedHashSet<>();
2097    
2098                    for (long layoutId : layoutIds) {
2099                            layoutIdsSet.add(layoutId);
2100                    }
2101    
2102                    Set<Long> newLayoutIdsSet = new HashSet<>();
2103    
2104                    List<Layout> layouts = layoutPersistence.findByG_P_P(
2105                            groupId, privateLayout, parentLayoutId);
2106    
2107                    for (Layout layout : layouts) {
2108                            if (!layoutIdsSet.contains(layout.getLayoutId())) {
2109                                    deleteLayout(layout, true, serviceContext);
2110                            }
2111                            else {
2112                                    newLayoutIdsSet.add(layout.getLayoutId());
2113                            }
2114                    }
2115    
2116                    int priority = 0;
2117    
2118                    for (long layoutId : layoutIdsSet) {
2119                            Layout layout = layoutPersistence.findByG_P_L(
2120                                    groupId, privateLayout, layoutId);
2121    
2122                            layout.setPriority(priority++);
2123    
2124                            layoutPersistence.update(layout);
2125                    }
2126    
2127                    layoutSetLocalService.updatePageCount(groupId, privateLayout);
2128            }
2129    
2130            @Override
2131            public void updateAsset(
2132                            long userId, Layout layout, long[] assetCategoryIds,
2133                            String[] assetTagNames)
2134                    throws PortalException {
2135    
2136                    assetEntryLocalService.updateEntry(
2137                            userId, layout.getGroupId(), layout.getCreateDate(),
2138                            layout.getModifiedDate(), Layout.class.getName(), layout.getPlid(),
2139                            layout.getUuid(), 0, assetCategoryIds, assetTagNames, false, null,
2140                            null, null, ContentTypes.TEXT_HTML,
2141                            layout.getName(LocaleUtil.getDefault()), null, null, null, null, 0,
2142                            0, null);
2143            }
2144    
2145            /**
2146             * Updates the friendly URL of the layout.
2147             *
2148             * @param  userId the primary key of the user
2149             * @param  plid the primary key of the layout
2150             * @param  friendlyURL the friendly URL to be assigned
2151             * @param  languageId the primary key of the language
2152             * @return the updated layout
2153             */
2154            @Override
2155            public Layout updateFriendlyURL(
2156                            long userId, long plid, String friendlyURL, String languageId)
2157                    throws PortalException {
2158    
2159                    Date now = new Date();
2160    
2161                    Layout layout = layoutPersistence.findByPrimaryKey(plid);
2162    
2163                    friendlyURL = layoutLocalServiceHelper.getFriendlyURL(
2164                            layout.getGroupId(), layout.isPrivateLayout(), layout.getLayoutId(),
2165                            StringPool.BLANK, friendlyURL);
2166    
2167                    layoutLocalServiceHelper.validateFriendlyURL(
2168                            layout.getGroupId(), layout.isPrivateLayout(), layout.getLayoutId(),
2169                            friendlyURL);
2170    
2171                    layoutFriendlyURLLocalService.updateLayoutFriendlyURL(
2172                            userId, layout.getCompanyId(), layout.getGroupId(),
2173                            layout.getPlid(), layout.isPrivateLayout(), friendlyURL, languageId,
2174                            new ServiceContext());
2175    
2176                    layout.setModifiedDate(now);
2177    
2178                    String defaultLanguageId = LocaleUtil.toLanguageId(
2179                            LocaleUtil.getSiteDefault());
2180    
2181                    if (languageId.equals(defaultLanguageId)) {
2182                            layout.setFriendlyURL(friendlyURL);
2183                    }
2184    
2185                    layoutPersistence.update(layout);
2186    
2187                    return layout;
2188            }
2189    
2190            /**
2191             * Updates the friendly URL of the layout.
2192             *
2193             * @param      plid the primary key of the layout
2194             * @param      friendlyURL the friendly URL to be assigned
2195             * @param      languageId the primary key of the language
2196             * @return     the updated layout
2197             * @deprecated As of 7.0.0, replaced by {@link #updateFriendlyURL(long,
2198             *             long, String, String)}
2199             */
2200            @Deprecated
2201            @Override
2202            public Layout updateFriendlyURL(
2203                            long plid, String friendlyURL, String languageId)
2204                    throws PortalException {
2205    
2206                    Layout layout = layoutPersistence.findByPrimaryKey(plid);
2207    
2208                    return updateFriendlyURL(
2209                            layout.getUserId(), plid, friendlyURL, languageId);
2210            }
2211    
2212            @Override
2213            public Layout updateIconImage(long plid, byte[] bytes)
2214                    throws PortalException {
2215    
2216                    Layout layout = layoutPersistence.fetchByPrimaryKey(plid);
2217    
2218                    if (layout == null) {
2219                            return null;
2220                    }
2221    
2222                    PortalUtil.updateImageId(layout, true, bytes, "iconImageId", 0, 0, 0);
2223    
2224                    layoutPersistence.update(layout);
2225    
2226                    return layout;
2227            }
2228    
2229            /**
2230             * Updates the layout.
2231             *
2232             * @param  groupId the primary key of the group
2233             * @param  privateLayout whether the layout is private to the group
2234             * @param  layoutId the primary key of the layout
2235             * @param  parentLayoutId the primary key of the layout's new parent layout
2236             * @param  nameMap the locales and localized names to merge (optionally
2237             *         <code>null</code>)
2238             * @param  titleMap the locales and localized titles to merge (optionally
2239             *         <code>null</code>)
2240             * @param  descriptionMap the locales and localized descriptions to merge
2241             *         (optionally <code>null</code>)
2242             * @param  keywordsMap the locales and localized keywords to merge
2243             *         (optionally <code>null</code>)
2244             * @param  robotsMap the locales and localized robots to merge (optionally
2245             *         <code>null</code>)
2246             * @param  type the layout's new type (optionally {@link
2247             *         LayoutConstants#TYPE_PORTLET})
2248             * @param  hidden whether the layout is hidden
2249             * @param  friendlyURLMap the layout's locales and localized friendly URLs.
2250             *         To see how the URL is normalized when accessed, see {@link
2251             *         com.liferay.portal.kernel.util.FriendlyURLNormalizerUtil#normalize(
2252             *         String)}.
2253             * @param  iconImage whether the icon image will be updated
2254             * @param  iconBytes the byte array of the layout's new icon image
2255             * @param  serviceContext the service context to be applied. Can set the
2256             *         modification date and expando bridge attributes for the layout.
2257             *         For layouts that are linked to a layout prototype, attributes
2258             *         named <code>layoutPrototypeUuid</code> and
2259             *         <code>layoutPrototypeLinkedEnabled</code> can be specified to
2260             *         provide the unique identifier of the source prototype and a
2261             *         boolean to determine whether a link to it should be enabled to
2262             *         activate propagation of changes made to the linked page in the
2263             *         prototype.
2264             * @return the updated layout
2265             */
2266            @Override
2267            public Layout updateLayout(
2268                            long groupId, boolean privateLayout, long layoutId,
2269                            long parentLayoutId, Map<Locale, String> nameMap,
2270                            Map<Locale, String> titleMap, Map<Locale, String> descriptionMap,
2271                            Map<Locale, String> keywordsMap, Map<Locale, String> robotsMap,
2272                            String type, boolean hidden, Map<Locale, String> friendlyURLMap,
2273                            boolean iconImage, byte[] iconBytes, ServiceContext serviceContext)
2274                    throws PortalException {
2275    
2276                    // Layout
2277    
2278                    parentLayoutId = layoutLocalServiceHelper.getParentLayoutId(
2279                            groupId, privateLayout, parentLayoutId);
2280                    String name = nameMap.get(LocaleUtil.getSiteDefault());
2281                    friendlyURLMap = layoutLocalServiceHelper.getFriendlyURLMap(
2282                            groupId, privateLayout, layoutId, name, friendlyURLMap);
2283    
2284                    String friendlyURL = friendlyURLMap.get(LocaleUtil.getSiteDefault());
2285    
2286                    layoutLocalServiceHelper.validate(
2287                            groupId, privateLayout, layoutId, parentLayoutId, name, type,
2288                            hidden, friendlyURLMap, serviceContext);
2289    
2290                    layoutLocalServiceHelper.validateParentLayoutId(
2291                            groupId, privateLayout, layoutId, parentLayoutId);
2292    
2293                    Date now = new Date();
2294    
2295                    Layout layout = layoutPersistence.findByG_P_L(
2296                            groupId, privateLayout, layoutId);
2297    
2298                    if (parentLayoutId != layout.getParentLayoutId()) {
2299                            int priority = layoutLocalServiceHelper.getNextPriority(
2300                                    groupId, privateLayout, parentLayoutId,
2301                                    layout.getSourcePrototypeLayoutUuid(), -1);
2302    
2303                            layout.setPriority(priority);
2304                    }
2305    
2306                    layout.setModifiedDate(serviceContext.getModifiedDate(now));
2307                    layout.setParentLayoutId(parentLayoutId);
2308                    layout.setNameMap(nameMap);
2309                    layout.setTitleMap(titleMap);
2310                    layout.setDescriptionMap(descriptionMap);
2311                    layout.setKeywordsMap(keywordsMap);
2312                    layout.setRobotsMap(robotsMap);
2313                    layout.setType(type);
2314                    layout.setHidden(hidden);
2315                    layout.setFriendlyURL(friendlyURL);
2316    
2317                    PortalUtil.updateImageId(
2318                            layout, iconImage, iconBytes, "iconImageId", 0, 0, 0);
2319    
2320                    boolean layoutUpdateable = ParamUtil.getBoolean(
2321                            serviceContext, Sites.LAYOUT_UPDATEABLE, true);
2322    
2323                    UnicodeProperties typeSettingsProperties =
2324                            layout.getTypeSettingsProperties();
2325    
2326                    typeSettingsProperties.put(
2327                            Sites.LAYOUT_UPDATEABLE, String.valueOf(layoutUpdateable));
2328    
2329                    if (privateLayout) {
2330                            typeSettingsProperties.put(
2331                                    "privateLayout", String.valueOf(privateLayout));
2332                    }
2333    
2334                    layout.setTypeSettingsProperties(typeSettingsProperties);
2335    
2336                    String layoutPrototypeUuid = ParamUtil.getString(
2337                            serviceContext, "layoutPrototypeUuid");
2338                    boolean layoutPrototypeLinkEnabled = ParamUtil.getBoolean(
2339                            serviceContext, "layoutPrototypeLinkEnabled");
2340    
2341                    if (Validator.isNotNull(layoutPrototypeUuid)) {
2342                            layout.setLayoutPrototypeUuid(layoutPrototypeUuid);
2343                            layout.setLayoutPrototypeLinkEnabled(layoutPrototypeLinkEnabled);
2344                    }
2345    
2346                    layout.setExpandoBridgeAttributes(serviceContext);
2347    
2348                    layoutPersistence.update(layout);
2349    
2350                    // Layout friendly URLs
2351    
2352                    layoutFriendlyURLLocalService.updateLayoutFriendlyURLs(
2353                            serviceContext.getUserId(), layout.getCompanyId(),
2354                            layout.getGroupId(), layout.getPlid(), layout.isPrivateLayout(),
2355                            friendlyURLMap, serviceContext);
2356    
2357                    // Asset
2358    
2359                    updateAsset(
2360                            serviceContext.getUserId(), layout,
2361                            serviceContext.getAssetCategoryIds(),
2362                            serviceContext.getAssetTagNames());
2363    
2364                    return layout;
2365            }
2366    
2367            /**
2368             * Updates the layout.
2369             *
2370             * @param      groupId the primary key of the group
2371             * @param      privateLayout whether the layout is private to the group
2372             * @param      layoutId the primary key of the layout
2373             * @param      parentLayoutId the primary key of the layout's new parent
2374             *             layout
2375             * @param      nameMap the locales and localized names to merge (optionally
2376             *             <code>null</code>)
2377             * @param      titleMap the locales and localized titles to merge
2378             *             (optionally <code>null</code>)
2379             * @param      descriptionMap the locales and localized descriptions to
2380             *             merge (optionally <code>null</code>)
2381             * @param      keywordsMap the locales and localized keywords to merge
2382             *             (optionally <code>null</code>)
2383             * @param      robotsMap the locales and localized robots to merge
2384             *             (optionally <code>null</code>)
2385             * @param      type the layout's new type (optionally {@link
2386             *             LayoutConstants#TYPE_PORTLET})
2387             * @param      hidden whether the layout is hidden
2388             * @param      friendlyURL the layout's new friendly URL (optionally {@link
2389             *             PropsValues#DEFAULT_USER_PRIVATE_LAYOUT_FRIENDLY_URL} or
2390             *             {@link
2391             *             PropsValues#DEFAULT_USER_PRIVATE_LAYOUT_FRIENDLY_URL}). The
2392             *             default values can be overridden in
2393             *             <code>portal-ext.properties</code> by specifying new values
2394             *             for the corresponding properties defined in {@link
2395             *             PropsValues}. To see how the URL is normalized when accessed,
2396             *             see {@link
2397             *             com.liferay.portal.kernel.util.FriendlyURLNormalizerUtil#normalize(
2398             *             String)}.
2399             * @param      iconImage whether the icon image will be updated
2400             * @param      iconBytes the byte array of the layout's new icon image
2401             * @param      serviceContext the service context to be applied. Can set the
2402             *             modification date and expando bridge attributes for the
2403             *             layout. For layouts that are linked to a layout prototype,
2404             *             attributes named <code>layoutPrototypeUuid</code> and
2405             *             <code>layoutPrototypeLinkedEnabled</code> can be specified to
2406             *             provide the unique identifier of the source prototype and a
2407             *             boolean to determine whether a link to it should be enabled
2408             *             to activate propagation of changes made to the linked page in
2409             *             the prototype.
2410             * @return     the updated layout
2411             * @deprecated As of 6.2.0, replaced by {@link #updateLayout(long, boolean,
2412             *             long, long, Map, Map, Map, Map, Map, String, boolean, Map,
2413             *             boolean, byte[], ServiceContext)}
2414             */
2415            @Deprecated
2416            @Override
2417            public Layout updateLayout(
2418                            long groupId, boolean privateLayout, long layoutId,
2419                            long parentLayoutId, Map<Locale, String> nameMap,
2420                            Map<Locale, String> titleMap, Map<Locale, String> descriptionMap,
2421                            Map<Locale, String> keywordsMap, Map<Locale, String> robotsMap,
2422                            String type, boolean hidden, String friendlyURL, Boolean iconImage,
2423                            byte[] iconBytes, ServiceContext serviceContext)
2424                    throws PortalException {
2425    
2426                    Map<Locale, String> friendlyURLMap = new HashMap<>();
2427    
2428                    friendlyURLMap.put(LocaleUtil.getSiteDefault(), friendlyURL);
2429    
2430                    return updateLayout(
2431                            groupId, privateLayout, layoutId, parentLayoutId, nameMap, titleMap,
2432                            descriptionMap, keywordsMap, robotsMap, type, hidden,
2433                            friendlyURLMap, iconImage, iconBytes, serviceContext);
2434            }
2435    
2436            /**
2437             * Updates the layout replacing its type settings.
2438             *
2439             * @param  groupId the primary key of the group
2440             * @param  privateLayout whether the layout is private to the group
2441             * @param  layoutId the primary key of the layout
2442             * @param  typeSettings the settings to load the unicode properties object.
2443             *         See {@link UnicodeProperties #fastLoad(String)}.
2444             * @return the updated layout
2445             */
2446            @Override
2447            public Layout updateLayout(
2448                            long groupId, boolean privateLayout, long layoutId,
2449                            String typeSettings)
2450                    throws PortalException {
2451    
2452                    Date now = new Date();
2453    
2454                    UnicodeProperties typeSettingsProperties = new UnicodeProperties();
2455    
2456                    typeSettingsProperties.fastLoad(typeSettings);
2457    
2458                    validateTypeSettingsProperties(typeSettingsProperties);
2459    
2460                    Layout layout = layoutPersistence.findByG_P_L(
2461                            groupId, privateLayout, layoutId);
2462    
2463                    layout.setModifiedDate(now);
2464                    layout.setTypeSettings(typeSettingsProperties.toString());
2465    
2466                    layoutPersistence.update(layout);
2467    
2468                    return layout;
2469            }
2470    
2471            /**
2472             * Updates the look and feel of the layout.
2473             *
2474             * @param  groupId the primary key of the group
2475             * @param  privateLayout whether the layout is private to the group
2476             * @param  layoutId the primary key of the layout
2477             * @param  themeId the primary key of the layout's new theme
2478             * @param  colorSchemeId the primary key of the layout's new color scheme
2479             * @param  css the layout's new CSS
2480             * @param  wapTheme whether the theme is for WAP browsers
2481             * @return the updated layout
2482             */
2483            @Override
2484            public Layout updateLookAndFeel(
2485                            long groupId, boolean privateLayout, long layoutId, String themeId,
2486                            String colorSchemeId, String css, boolean wapTheme)
2487                    throws PortalException {
2488    
2489                    Date now = new Date();
2490    
2491                    Layout layout = layoutPersistence.findByG_P_L(
2492                            groupId, privateLayout, layoutId);
2493    
2494                    layout.setModifiedDate(now);
2495    
2496                    if (wapTheme) {
2497                            layout.setWapThemeId(themeId);
2498                            layout.setWapColorSchemeId(colorSchemeId);
2499                    }
2500                    else {
2501                            layout.setThemeId(themeId);
2502                            layout.setColorSchemeId(colorSchemeId);
2503                            layout.setCss(css);
2504                    }
2505    
2506                    layoutPersistence.update(layout);
2507    
2508                    return layout;
2509            }
2510    
2511            /**
2512             * Updates the name of the layout.
2513             *
2514             * @param  layout the layout to be updated
2515             * @param  name the layout's new name
2516             * @param  languageId the primary key of the language. For more information
2517             *         see {@link Locale}.
2518             * @return the updated layout
2519             */
2520            @Override
2521            public Layout updateName(Layout layout, String name, String languageId)
2522                    throws PortalException {
2523    
2524                    Date now = new Date();
2525    
2526                    layoutLocalServiceHelper.validateName(name, languageId);
2527    
2528                    layout.setModifiedDate(now);
2529                    layout.setName(name, LocaleUtil.fromLanguageId(languageId));
2530    
2531                    layoutPersistence.update(layout);
2532    
2533                    Group group = layout.getGroup();
2534    
2535                    if (group.isLayoutPrototype()) {
2536                            LayoutPrototype layoutPrototype =
2537                                    layoutPrototypeLocalService.getLayoutPrototype(
2538                                            group.getClassPK());
2539    
2540                            layoutPrototype.setModifiedDate(now);
2541                            layoutPrototype.setName(
2542                                    name, LocaleUtil.fromLanguageId(languageId));
2543    
2544                            layoutPrototypePersistence.update(layoutPrototype);
2545                    }
2546    
2547                    return layout;
2548            }
2549    
2550            /**
2551             * Updates the name of the layout matching the group, layout ID, and
2552             * privacy.
2553             *
2554             * @param  groupId the primary key of the group
2555             * @param  privateLayout whether the layout is private to the group
2556             * @param  layoutId the primary key of the layout
2557             * @param  name the layout's new name
2558             * @param  languageId the primary key of the language. For more information
2559             *         see {@link Locale}.
2560             * @return the updated layout
2561             */
2562            @Override
2563            public Layout updateName(
2564                            long groupId, boolean privateLayout, long layoutId, String name,
2565                            String languageId)
2566                    throws PortalException {
2567    
2568                    Layout layout = layoutPersistence.findByG_P_L(
2569                            groupId, privateLayout, layoutId);
2570    
2571                    return updateName(layout, name, languageId);
2572            }
2573    
2574            /**
2575             * Updates the name of the layout matching the primary key.
2576             *
2577             * @param  plid the primary key of the layout
2578             * @param  name the name to be assigned
2579             * @param  languageId the primary key of the language. For more information
2580             *         see {@link Locale}.
2581             * @return the updated layout
2582             */
2583            @Override
2584            public Layout updateName(long plid, String name, String languageId)
2585                    throws PortalException {
2586    
2587                    Layout layout = layoutPersistence.findByPrimaryKey(plid);
2588    
2589                    return updateName(layout, name, languageId);
2590            }
2591    
2592            /**
2593             * Updates the parent layout ID of the layout matching the group, layout ID,
2594             * and privacy.
2595             *
2596             * @param  groupId the primary key of the group
2597             * @param  privateLayout whether the layout is private to the group
2598             * @param  layoutId the primary key of the layout
2599             * @param  parentLayoutId the primary key to be assigned to the parent
2600             *         layout
2601             * @return the matching layout
2602             */
2603            @Override
2604            public Layout updateParentLayoutId(
2605                            long groupId, boolean privateLayout, long layoutId,
2606                            long parentLayoutId)
2607                    throws PortalException {
2608    
2609                    parentLayoutId = layoutLocalServiceHelper.getParentLayoutId(
2610                            groupId, privateLayout, parentLayoutId);
2611    
2612                    layoutLocalServiceHelper.validateParentLayoutId(
2613                            groupId, privateLayout, layoutId, parentLayoutId);
2614    
2615                    Date now = new Date();
2616    
2617                    Layout layout = layoutPersistence.findByG_P_L(
2618                            groupId, privateLayout, layoutId);
2619    
2620                    if (parentLayoutId != layout.getParentLayoutId()) {
2621                            int priority = layoutLocalServiceHelper.getNextPriority(
2622                                    groupId, privateLayout, parentLayoutId,
2623                                    layout.getSourcePrototypeLayoutUuid(), -1);
2624    
2625                            layout.setPriority(priority);
2626                    }
2627    
2628                    layout.setModifiedDate(now);
2629                    layout.setParentLayoutId(parentLayoutId);
2630    
2631                    layoutPersistence.update(layout);
2632    
2633                    return layout;
2634            }
2635    
2636            /**
2637             * Updates the parent layout ID of the layout matching the primary key. If a
2638             * layout matching the parent primary key is found, the layout ID of that
2639             * layout is assigned, otherwise {@link
2640             * LayoutConstants#DEFAULT_PARENT_LAYOUT_ID} is assigned.
2641             *
2642             * @param  plid the primary key of the layout
2643             * @param  parentPlid the primary key of the parent layout
2644             * @return the layout matching the primary key
2645             */
2646            @Override
2647            public Layout updateParentLayoutId(long plid, long parentPlid)
2648                    throws PortalException {
2649    
2650                    Date now = new Date();
2651    
2652                    Layout layout = layoutPersistence.findByPrimaryKey(plid);
2653    
2654                    long parentLayoutId = LayoutConstants.DEFAULT_PARENT_LAYOUT_ID;
2655    
2656                    if (parentPlid > 0) {
2657                            Layout parentLayout = layoutPersistence.fetchByPrimaryKey(
2658                                    parentPlid);
2659    
2660                            if (parentLayout != null) {
2661                                    parentLayoutId = parentLayout.getLayoutId();
2662                            }
2663                    }
2664    
2665                    parentLayoutId = layoutLocalServiceHelper.getParentLayoutId(
2666                            layout.getGroupId(), layout.isPrivateLayout(), parentLayoutId);
2667    
2668                    layoutLocalServiceHelper.validateParentLayoutId(
2669                            layout.getGroupId(), layout.isPrivateLayout(), layout.getLayoutId(),
2670                            parentLayoutId);
2671    
2672                    if (parentLayoutId != layout.getParentLayoutId()) {
2673                            int priority = layoutLocalServiceHelper.getNextPriority(
2674                                    layout.getGroupId(), layout.isPrivateLayout(), parentLayoutId,
2675                                    layout.getSourcePrototypeLayoutUuid(), -1);
2676    
2677                            layout.setPriority(priority);
2678                    }
2679    
2680                    layout.setModifiedDate(now);
2681                    layout.setParentLayoutId(parentLayoutId);
2682    
2683                    layoutPersistence.update(layout);
2684    
2685                    return layout;
2686            }
2687    
2688            /**
2689             * Updates the parent layout ID and priority of the layout.
2690             *
2691             * @param  plid the primary key of the layout
2692             * @param  parentPlid the primary key of the parent layout
2693             * @param  priority the layout's new priority
2694             * @return the layout matching the primary key
2695             */
2696            @Override
2697            public Layout updateParentLayoutIdAndPriority(
2698                            long plid, long parentPlid, int priority)
2699                    throws PortalException {
2700    
2701                    Layout layout = updateParentLayoutId(plid, parentPlid);
2702    
2703                    return updatePriority(layout, priority);
2704            }
2705    
2706            /**
2707             * Updates the priorities of the layouts.
2708             *
2709             * @param  groupId the primary key of the group
2710             * @param  privateLayout whether the layout is private to the group
2711             * @throws PortalException
2712             */
2713            @Override
2714            public void updatePriorities(long groupId, boolean privateLayout)
2715                    throws PortalException {
2716    
2717                    List<Layout> layouts = layoutPersistence.findByG_P(
2718                            groupId, privateLayout);
2719    
2720                    for (Layout layout : layouts) {
2721                            int nextPriority = layoutLocalServiceHelper.getNextPriority(
2722                                    layout.getGroupId(), layout.isPrivateLayout(),
2723                                    layout.getParentLayoutId(),
2724                                    layout.getSourcePrototypeLayoutUuid(), layout.getPriority());
2725    
2726                            layout.setPriority(nextPriority);
2727    
2728                            layoutPersistence.update(layout);
2729                    }
2730            }
2731    
2732            /**
2733             * Updates the priority of the layout.
2734             *
2735             * @param  layout the layout to be updated
2736             * @param  priority the layout's new priority
2737             * @return the updated layout
2738             */
2739            @Override
2740            public Layout updatePriority(Layout layout, int priority)
2741                    throws PortalException {
2742    
2743                    if (layout.getPriority() == priority) {
2744                            return layout;
2745                    }
2746    
2747                    int oldPriority = layout.getPriority();
2748    
2749                    int nextPriority = layoutLocalServiceHelper.getNextPriority(
2750                            layout.getGroupId(), layout.isPrivateLayout(),
2751                            layout.getParentLayoutId(), layout.getSourcePrototypeLayoutUuid(),
2752                            priority);
2753    
2754                    if (oldPriority == nextPriority) {
2755                            return layout;
2756                    }
2757    
2758                    layout.setModifiedDate(new Date());
2759                    layout.setPriority(nextPriority);
2760    
2761                    layoutPersistence.update(layout);
2762    
2763                    List<Layout> layouts = layoutPersistence.findByG_P_P(
2764                            layout.getGroupId(), layout.isPrivateLayout(),
2765                            layout.getParentLayoutId());
2766    
2767                    boolean lessThan = false;
2768    
2769                    if (oldPriority < nextPriority) {
2770                            lessThan = true;
2771                    }
2772    
2773                    layouts = ListUtil.sort(
2774                            layouts, new LayoutPriorityComparator(layout, lessThan));
2775    
2776                    if (layout.getParentLayoutId() ==
2777                                    LayoutConstants.DEFAULT_PARENT_LAYOUT_ID) {
2778    
2779                            Layout firstLayout = layouts.get(0);
2780    
2781                            layoutLocalServiceHelper.validateFirstLayout(firstLayout);
2782                    }
2783    
2784                    int newPriority = LayoutConstants.FIRST_PRIORITY;
2785    
2786                    for (Layout curLayout : layouts) {
2787                            int curNextPriority = layoutLocalServiceHelper.getNextPriority(
2788                                    layout.getGroupId(), layout.isPrivateLayout(),
2789                                    layout.getParentLayoutId(),
2790                                    curLayout.getSourcePrototypeLayoutUuid(), newPriority++);
2791    
2792                            if (curLayout.getPriority() == curNextPriority) {
2793                                    continue;
2794                            }
2795    
2796                            curLayout.setModifiedDate(layout.getModifiedDate());
2797                            curLayout.setPriority(curNextPriority);
2798    
2799                            layoutPersistence.update(curLayout);
2800    
2801                            if (curLayout.equals(layout)) {
2802                                    layout = curLayout;
2803                            }
2804                    }
2805    
2806                    return layout;
2807            }
2808    
2809            /**
2810             * Updates the priority of the layout matching the group, layout ID, and
2811             * privacy.
2812             *
2813             * @param  groupId the primary key of the group
2814             * @param  privateLayout whether the layout is private to the group
2815             * @param  layoutId the primary key of the layout
2816             * @param  priority the layout's new priority
2817             * @return the updated layout
2818             */
2819            @Override
2820            public Layout updatePriority(
2821                            long groupId, boolean privateLayout, long layoutId, int priority)
2822                    throws PortalException {
2823    
2824                    Layout layout = layoutPersistence.findByG_P_L(
2825                            groupId, privateLayout, layoutId);
2826    
2827                    return updatePriority(layout, priority);
2828            }
2829    
2830            /**
2831             * Updates the priority of the layout matching the group, layout ID, and
2832             * privacy, setting the layout's priority based on the priorities of the
2833             * next and previous layouts.
2834             *
2835             * @param  groupId the primary key of the group
2836             * @param  privateLayout whether the layout is private to the group
2837             * @param  layoutId the primary key of the layout
2838             * @param  nextLayoutId the primary key of the next layout
2839             * @param  previousLayoutId the primary key of the previous layout
2840             * @return the updated layout
2841             */
2842            @Override
2843            public Layout updatePriority(
2844                            long groupId, boolean privateLayout, long layoutId,
2845                            long nextLayoutId, long previousLayoutId)
2846                    throws PortalException {
2847    
2848                    Layout layout = getLayout(groupId, privateLayout, layoutId);
2849    
2850                    int priority = layout.getPriority();
2851    
2852                    Layout nextLayout = null;
2853    
2854                    if (nextLayoutId > 0) {
2855                            nextLayout = getLayout(groupId, privateLayout, nextLayoutId);
2856                    }
2857    
2858                    Layout previousLayout = null;
2859    
2860                    if (previousLayoutId > 0) {
2861                            previousLayout = getLayout(
2862                                    groupId, privateLayout, previousLayoutId);
2863                    }
2864    
2865                    if ((nextLayout != null) && (priority > nextLayout.getPriority())) {
2866                            priority = nextLayout.getPriority();
2867                    }
2868                    else if ((previousLayout != null) &&
2869                                     (priority < previousLayout.getPriority())) {
2870    
2871                            priority = previousLayout.getPriority();
2872                    }
2873    
2874                    return updatePriority(layout, priority);
2875            }
2876    
2877            /**
2878             * Updates the priority of the layout matching the primary key.
2879             *
2880             * @param  plid the primary key of the layout
2881             * @param  priority the layout's new priority
2882             * @return the updated layout
2883             */
2884            @Override
2885            public Layout updatePriority(long plid, int priority)
2886                    throws PortalException {
2887    
2888                    Layout layout = layoutPersistence.findByPrimaryKey(plid);
2889    
2890                    return updatePriority(layout, priority);
2891            }
2892    
2893            /**
2894             * @deprecated As of 6.2.0, with no direct replacement
2895             */
2896            @Deprecated
2897            @Override
2898            @SuppressWarnings("unused")
2899            public void updateScopedPortletNames(
2900                            long groupId, boolean privateLayout, long layoutId,
2901                            Map<Locale, String> nameMap, List<Locale> nameMapModifiedLocales)
2902                    throws PortalException {
2903            }
2904    
2905            /**
2906             * Updates the names of the portlets within scope of the group, the scope of
2907             * the layout's UUID, and the privacy.
2908             *
2909             * @param      groupId the primary key of the group
2910             * @param      privateLayout whether the layout is private to the group
2911             * @param      layoutId the primary key of the layout whose UUID to match
2912             * @param      name the new name for the portlets
2913             * @param      languageId the primary key of the language
2914             * @throws     PortalException
2915             * @see        com.liferay.portlet.portletconfiguration.action.EditScopeAction
2916             * @deprecated As of 6.2.0, with no direct replacement
2917             */
2918            @Deprecated
2919            @Override
2920            public void updateScopedPortletNames(
2921                            long groupId, boolean privateLayout, long layoutId, String name,
2922                            String languageId)
2923                    throws PortalException {
2924            }
2925    
2926            /**
2927             * @throws     PortalException
2928             * @deprecated As of 7.0.0, replaced by {@link
2929             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#validateImportLayoutsFile(
2930             *             ExportImportConfiguration, File)}
2931             */
2932            @Deprecated
2933            @Override
2934            public MissingReferences validateImportLayoutsFile(
2935                            ExportImportConfiguration exportImportConfiguration, File file)
2936                    throws PortalException {
2937    
2938                    throw new UnsupportedOperationException();
2939            }
2940    
2941            /**
2942             * @throws     PortalException
2943             * @deprecated As of 7.0.0, replaced by {@link
2944             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#validateImportLayoutsFile(
2945             *             ExportImportConfiguration, InputStream)}
2946             */
2947            @Deprecated
2948            @Override
2949            public MissingReferences validateImportLayoutsFile(
2950                            ExportImportConfiguration exportImportConfiguration,
2951                            InputStream inputStream)
2952                    throws PortalException {
2953    
2954                    throw new UnsupportedOperationException();
2955            }
2956    
2957            /**
2958             * @throws     PortalException
2959             * @deprecated As of 7.0.0, with no direct replacement
2960             */
2961            @Deprecated
2962            @Override
2963            public MissingReferences validateImportLayoutsFile(
2964                            long userId, long groupId, boolean privateLayout,
2965                            Map<String, String[]> parameterMap, File file)
2966                    throws PortalException {
2967    
2968                    throw new UnsupportedOperationException();
2969            }
2970    
2971            /**
2972             * @throws     PortalException
2973             * @deprecated As of 7.0.0, with no direct replacement
2974             */
2975            @Deprecated
2976            @Override
2977            public MissingReferences validateImportLayoutsFile(
2978                            long userId, long groupId, boolean privateLayout,
2979                            Map<String, String[]> parameterMap, InputStream inputStream)
2980                    throws PortalException {
2981    
2982                    throw new UnsupportedOperationException();
2983            }
2984    
2985            /**
2986             * @throws     PortalException
2987             * @deprecated As of 7.0.0, replaced by {@link
2988             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#validateImportPortletInfo(
2989             *             ExportImportConfiguration, File)}
2990             */
2991            @Deprecated
2992            @Override
2993            public MissingReferences validateImportPortletInfo(
2994                            ExportImportConfiguration exportImportConfiguration, File file)
2995                    throws PortalException {
2996    
2997                    throw new UnsupportedOperationException();
2998            }
2999    
3000            /**
3001             * @throws     PortalException
3002             * @deprecated As of 7.0.0, replaced by {@link
3003             *             com.liferay.portlet.exportimport.service.ExportImportLocalService#validateImportPortletInfo(
3004             *             ExportImportConfiguration, InputStream)}
3005             */
3006            @Deprecated
3007            @Override
3008            public MissingReferences validateImportPortletInfo(
3009                            ExportImportConfiguration exportImportConfiguration,
3010                            InputStream inputStream)
3011                    throws PortalException {
3012    
3013                    throw new UnsupportedOperationException();
3014            }
3015    
3016            /**
3017             * @throws     PortalException
3018             * @deprecated As of 7.0.0, with no direct replacement
3019             */
3020            @Deprecated
3021            @Override
3022            public MissingReferences validateImportPortletInfo(
3023                            long userId, long plid, long groupId, String portletId,
3024                            Map<String, String[]> parameterMap, File file)
3025                    throws PortalException {
3026    
3027                    throw new UnsupportedOperationException();
3028            }
3029    
3030            /**
3031             * @throws     PortalException
3032             * @deprecated As of 7.0.0, with no direct replacement
3033             */
3034            @Deprecated
3035            @Override
3036            public MissingReferences validateImportPortletInfo(
3037                            long userId, long plid, long groupId, String portletId,
3038                            Map<String, String[]> parameterMap, InputStream inputStream)
3039                    throws PortalException {
3040    
3041                    throw new UnsupportedOperationException();
3042            }
3043    
3044            protected void validateTypeSettingsProperties(
3045                            UnicodeProperties typeSettingsProperties)
3046                    throws PortalException {
3047    
3048                    String sitemapChangeFrequency = typeSettingsProperties.getProperty(
3049                            "sitemap-changefreq");
3050    
3051                    if (Validator.isNotNull(sitemapChangeFrequency) &&
3052                            !sitemapChangeFrequency.equals("always") &&
3053                            !sitemapChangeFrequency.equals("hourly") &&
3054                            !sitemapChangeFrequency.equals("daily") &&
3055                            !sitemapChangeFrequency.equals("weekly") &&
3056                            !sitemapChangeFrequency.equals("monthly") &&
3057                            !sitemapChangeFrequency.equals("yearly") &&
3058                            !sitemapChangeFrequency.equals("never")) {
3059    
3060                            throw new SitemapChangeFrequencyException();
3061                    }
3062    
3063                    String sitemapInclude = typeSettingsProperties.getProperty(
3064                            "sitemap-include");
3065    
3066                    if (Validator.isNotNull(sitemapInclude) &&
3067                            !sitemapInclude.equals("0") && !sitemapInclude.equals("1")) {
3068    
3069                            throw new SitemapIncludeException();
3070                    }
3071    
3072                    String sitemapPriority = typeSettingsProperties.getProperty(
3073                            "sitemap-priority");
3074    
3075                    if (Validator.isNotNull(sitemapPriority)) {
3076                            try {
3077                                    double priority = Double.parseDouble(sitemapPriority);
3078    
3079                                    if ((priority < 0) || (priority > 1)) {
3080                                            throw new SitemapPagePriorityException();
3081                                    }
3082                            }
3083                            catch (NumberFormatException nfe) {
3084                                    throw new SitemapPagePriorityException();
3085                            }
3086                    }
3087            }
3088    
3089            @BeanReference(type = LayoutLocalServiceHelper.class)
3090            protected LayoutLocalServiceHelper layoutLocalServiceHelper;
3091    
3092    }