001    /**
002     * Copyright (c) 2000-2013 Liferay, Inc. All rights reserved.
003     *
004     * The contents of this file are subject to the terms of the Liferay Enterprise
005     * Subscription License ("License"). You may not use this file except in
006     * compliance with the License. You can obtain a copy of the License by
007     * contacting Liferay, Inc. See the License for the specific language governing
008     * permissions and limitations under the License, including but not limited to
009     * distribution rights of the Software.
010     *
011     *
012     *
013     */
014    
015    package com.liferay.portlet;
016    
017    import com.liferay.portal.kernel.cache.PortalCache;
018    import com.liferay.portal.kernel.cache.SingleVMPoolUtil;
019    import com.liferay.portal.kernel.cache.key.CacheKeyGenerator;
020    import com.liferay.portal.kernel.cache.key.CacheKeyGeneratorUtil;
021    import com.liferay.portal.kernel.exception.PortalException;
022    import com.liferay.portal.kernel.exception.SystemException;
023    import com.liferay.portal.kernel.io.unsync.UnsyncStringReader;
024    import com.liferay.portal.kernel.log.Log;
025    import com.liferay.portal.kernel.log.LogFactoryUtil;
026    import com.liferay.portal.kernel.portlet.LiferayPortletMode;
027    import com.liferay.portal.kernel.security.pacl.DoPrivileged;
028    import com.liferay.portal.kernel.util.GetterUtil;
029    import com.liferay.portal.kernel.util.JavaConstants;
030    import com.liferay.portal.kernel.util.ParamUtil;
031    import com.liferay.portal.kernel.util.StringPool;
032    import com.liferay.portal.kernel.util.Validator;
033    import com.liferay.portal.model.Group;
034    import com.liferay.portal.model.Layout;
035    import com.liferay.portal.model.LayoutConstants;
036    import com.liferay.portal.model.LayoutTypePortlet;
037    import com.liferay.portal.model.Portlet;
038    import com.liferay.portal.model.PortletConstants;
039    import com.liferay.portal.model.PortletPreferencesIds;
040    import com.liferay.portal.security.auth.PrincipalException;
041    import com.liferay.portal.security.permission.ActionKeys;
042    import com.liferay.portal.security.permission.PermissionChecker;
043    import com.liferay.portal.security.permission.PermissionThreadLocal;
044    import com.liferay.portal.service.GroupLocalServiceUtil;
045    import com.liferay.portal.service.PortalPreferencesLocalServiceUtil;
046    import com.liferay.portal.service.PortletLocalServiceUtil;
047    import com.liferay.portal.service.PortletPreferencesLocalServiceUtil;
048    import com.liferay.portal.service.UserLocalServiceUtil;
049    import com.liferay.portal.service.permission.LayoutPermissionUtil;
050    import com.liferay.portal.service.permission.PortletPermissionUtil;
051    import com.liferay.portal.theme.ThemeDisplay;
052    import com.liferay.portal.util.PortalUtil;
053    import com.liferay.portal.util.PortletKeys;
054    import com.liferay.portal.util.PropsValues;
055    import com.liferay.portal.util.WebKeys;
056    import com.liferay.portal.xml.StAXReaderUtil;
057    import com.liferay.portlet.portletconfiguration.util.ConfigurationPortletRequest;
058    
059    import java.util.ArrayList;
060    import java.util.Collections;
061    import java.util.HashMap;
062    import java.util.List;
063    import java.util.Map;
064    
065    import javax.portlet.PortletPreferences;
066    import javax.portlet.PortletRequest;
067    import javax.portlet.PreferencesValidator;
068    import javax.portlet.filter.PortletRequestWrapper;
069    import javax.servlet.http.HttpServletRequest;
070    import javax.servlet.http.HttpSession;
071    import javax.xml.stream.XMLEventReader;
072    import javax.xml.stream.XMLInputFactory;
073    import javax.xml.stream.XMLStreamException;
074    import javax.xml.stream.events.EndElement;
075    import javax.xml.stream.events.StartElement;
076    import javax.xml.stream.events.XMLEvent;
077    
078    /**
079     * @author Brian Wing Shun Chan
080     * @author Alexander Chow
081     * @author Minhchau Dang
082     * @author Raymond Aug??
083     */
084    @DoPrivileged
085    public class PortletPreferencesFactoryImpl
086            implements PortletPreferencesFactory {
087    
088            @Override
089            public void checkControlPanelPortletPreferences(
090                            ThemeDisplay themeDisplay, Portlet portlet)
091                    throws PortalException, SystemException {
092    
093                    Layout layout = themeDisplay.getLayout();
094    
095                    Group group = layout.getGroup();
096    
097                    if (!group.isControlPanel()) {
098                            return;
099                    }
100    
101                    String portletId = portlet.getPortletId();
102    
103                    boolean hasControlPanelAccessPermission =
104                            PortletPermissionUtil.hasControlPanelAccessPermission(
105                                    themeDisplay.getPermissionChecker(),
106                                    themeDisplay.getScopeGroupId(), portletId);
107    
108                    if (!hasControlPanelAccessPermission) {
109                            return;
110                    }
111    
112                    PortletPreferences portletSetup = getStrictLayoutPortletSetup(
113                            layout, portletId);
114    
115                    if (portletSetup instanceof StrictPortletPreferencesImpl) {
116                            getLayoutPortletSetup(layout, portletId);
117                    }
118    
119                    if (portlet.isInstanceable()) {
120                            return;
121                    }
122    
123                    PortletPreferencesIds portletPreferencesIds = getPortletPreferencesIds(
124                            themeDisplay.getScopeGroupId(), themeDisplay.getUserId(), layout,
125                            portletId, false);
126    
127                    PortletPreferences portletPreferences =
128                            PortletPreferencesLocalServiceUtil.fetchPreferences(
129                                    portletPreferencesIds);
130    
131                    if (portletPreferences != null) {
132                            return;
133                    }
134    
135                    PortletPreferencesLocalServiceUtil.getPreferences(
136                            portletPreferencesIds);
137            }
138    
139            @Override
140            public PortletPreferences fromDefaultXML(String xml)
141                    throws SystemException {
142    
143                    Map<String, Preference> preferencesMap = toPreferencesMap(xml);
144    
145                    return new PortletPreferencesImpl(xml, preferencesMap);
146            }
147    
148            @Override
149            public PortalPreferencesImpl fromXML(
150                            long ownerId, int ownerType, String xml)
151                    throws SystemException {
152    
153                    Map<String, Preference> preferencesMap = toPreferencesMap(xml);
154    
155                    return new PortalPreferencesImpl(
156                            ownerId, ownerType, xml, preferencesMap, false);
157            }
158    
159            @Override
160            public PortletPreferencesImpl fromXML(
161                            long companyId, long ownerId, int ownerType, long plid,
162                            String portletId, String xml)
163                    throws SystemException {
164    
165                    Map<String, Preference> preferencesMap = toPreferencesMap(xml);
166    
167                    return new PortletPreferencesImpl(
168                            companyId, ownerId, ownerType, plid, portletId, xml,
169                            preferencesMap);
170            }
171    
172            /**
173             * @deprecated As of 6.2.0, replaced by {@link #fromXML(long, int, String)}
174             */
175            @Override
176            public PortalPreferences fromXML(
177                            long companyId, long ownerId, int ownerType, String xml)
178                    throws SystemException {
179    
180                    return fromXML(ownerId, ownerType, xml);
181            }
182    
183            @Override
184            public PortletPreferences getLayoutPortletSetup(
185                            Layout layout, String portletId)
186                    throws SystemException {
187    
188                    return getLayoutPortletSetup(layout, portletId, null);
189            }
190    
191            @Override
192            public PortletPreferences getLayoutPortletSetup(
193                            Layout layout, String portletId, String defaultPreferences)
194                    throws SystemException {
195    
196                    long ownerId = PortletKeys.PREFS_OWNER_ID_DEFAULT;
197                    int ownerType = PortletKeys.PREFS_OWNER_TYPE_LAYOUT;
198    
199                    if (PortletConstants.hasUserId(portletId)) {
200                            ownerId = PortletConstants.getUserId(portletId);
201                            ownerType = PortletKeys.PREFS_OWNER_TYPE_USER;
202                    }
203    
204                    return PortletPreferencesLocalServiceUtil.getPreferences(
205                            layout.getCompanyId(), ownerId, ownerType, layout.getPlid(),
206                            portletId, defaultPreferences);
207            }
208    
209            @Override
210            public PortalPreferences getPortalPreferences(HttpServletRequest request)
211                    throws SystemException {
212    
213                    ThemeDisplay themeDisplay = (ThemeDisplay)request.getAttribute(
214                            WebKeys.THEME_DISPLAY);
215    
216                    return getPortalPreferences(
217                            request.getSession(), themeDisplay.getUserId(),
218                            themeDisplay.isSignedIn());
219            }
220    
221            @Override
222            public PortalPreferences getPortalPreferences(
223                            HttpSession session, long userId, boolean signedIn)
224                    throws SystemException {
225    
226                    long ownerId = userId;
227                    int ownerType = PortletKeys.PREFS_OWNER_TYPE_USER;
228    
229                    PortalPreferences portalPreferences = null;
230    
231                    if (signedIn) {
232                            PortalPreferencesWrapper portalPreferencesWrapper =
233                                    PortalPreferencesWrapperCacheUtil.get(ownerId, ownerType);
234    
235                            if (portalPreferencesWrapper == null) {
236                                    portalPreferencesWrapper =
237                                            (PortalPreferencesWrapper)
238                                                    PortalPreferencesLocalServiceUtil.getPreferences(
239                                                            ownerId, ownerType);
240    
241                                    portalPreferences =
242                                            portalPreferencesWrapper.getPortalPreferencesImpl();
243                            }
244                            else {
245                                    PortalPreferencesImpl portalPreferencesImpl =
246                                            portalPreferencesWrapper.getPortalPreferencesImpl();
247    
248                                    portalPreferences = portalPreferencesImpl.clone();
249                            }
250                    }
251                    else {
252                            if (session != null) {
253                                    portalPreferences = (PortalPreferences)session.getAttribute(
254                                            WebKeys.PORTAL_PREFERENCES);
255                            }
256    
257                            if (portalPreferences == null) {
258                                    PortalPreferencesWrapper portalPreferencesWrapper =
259                                            PortalPreferencesWrapperCacheUtil.get(ownerId, ownerType);
260    
261                                    if (portalPreferencesWrapper == null) {
262                                            portalPreferencesWrapper =
263                                                    (PortalPreferencesWrapper)
264                                                            PortalPreferencesLocalServiceUtil.getPreferences(
265                                                                    ownerId, ownerType);
266    
267                                            portalPreferences =
268                                                    portalPreferencesWrapper.getPortalPreferencesImpl();
269                                    }
270                                    else {
271                                            PortalPreferencesImpl portalPreferencesImpl =
272                                                    portalPreferencesWrapper.getPortalPreferencesImpl();
273    
274                                            portalPreferences = portalPreferencesImpl.clone();
275                                    }
276    
277                                    if (session != null) {
278                                            session.setAttribute(
279                                                    WebKeys.PORTAL_PREFERENCES, portalPreferences);
280                                    }
281                            }
282                    }
283    
284                    portalPreferences.setSignedIn(signedIn);
285                    portalPreferences.setUserId(userId);
286    
287                    return portalPreferences;
288            }
289    
290            /**
291             * @deprecated As of 6.2.0, replaced by {@link
292             *             #getPortalPreferences(HttpSession, long, boolean)}
293             */
294            @Override
295            public PortalPreferences getPortalPreferences(
296                            HttpSession session, long companyId, long userId, boolean signedIn)
297                    throws SystemException {
298    
299                    return getPortalPreferences(session, userId, signedIn);
300            }
301    
302            @Override
303            public PortalPreferences getPortalPreferences(long userId, boolean signedIn)
304                    throws SystemException {
305    
306                    return getPortalPreferences(null, userId, signedIn);
307            }
308    
309            /**
310             * @deprecated As of 6.2.0, replaced by {@link #getPortalPreferences(long,
311             *             boolean)}
312             */
313            @Override
314            public PortalPreferences getPortalPreferences(
315                            long companyId, long userId, boolean signedIn)
316                    throws SystemException {
317    
318                    return getPortalPreferences(userId, signedIn);
319            }
320    
321            @Override
322            public PortalPreferences getPortalPreferences(PortletRequest portletRequest)
323                    throws SystemException {
324    
325                    HttpServletRequest request = PortalUtil.getHttpServletRequest(
326                            portletRequest);
327    
328                    return getPortalPreferences(request);
329            }
330    
331            @Override
332            public PortletPreferences getPortletPreferences(
333                            HttpServletRequest request, String portletId)
334                    throws PortalException, SystemException {
335    
336                    PortletPreferencesIds portletPreferencesIds = getPortletPreferencesIds(
337                            request, portletId);
338    
339                    return PortletPreferencesLocalServiceUtil.getPreferences(
340                            portletPreferencesIds);
341            }
342    
343            @Override
344            public PortletPreferencesIds getPortletPreferencesIds(
345                            HttpServletRequest request, Layout layout, String portletId)
346                    throws PortalException, SystemException {
347    
348                    ThemeDisplay themeDisplay = (ThemeDisplay)request.getAttribute(
349                            WebKeys.THEME_DISPLAY);
350    
351                    long scopeGroupId = PortalUtil.getScopeGroupId(
352                            request, portletId, true);
353                    long userId = PortalUtil.getUserId(request);
354                    LayoutTypePortlet layoutTypePortlet =
355                            themeDisplay.getLayoutTypePortlet();
356    
357                    boolean modeEditGuest = false;
358    
359                    String portletMode = ParamUtil.getString(request, "p_p_mode");
360    
361                    if (portletMode.equals(LiferayPortletMode.EDIT_GUEST.toString()) ||
362                            ((layoutTypePortlet != null) &&
363                             layoutTypePortlet.hasModeEditGuestPortletId(portletId))) {
364    
365                            modeEditGuest = true;
366                    }
367    
368                    return getPortletPreferencesIds(
369                            scopeGroupId, userId, layout, portletId, modeEditGuest);
370            }
371    
372            @Override
373            public PortletPreferencesIds getPortletPreferencesIds(
374                            HttpServletRequest request, String portletId)
375                    throws PortalException, SystemException {
376    
377                    Layout layout = (Layout)request.getAttribute(WebKeys.LAYOUT);
378    
379                    return getPortletPreferencesIds(request, layout, portletId);
380            }
381    
382            @Override
383            public PortletPreferencesIds getPortletPreferencesIds(
384                            long scopeGroupId, long userId, Layout layout, String portletId,
385                            boolean modeEditGuest)
386                    throws PortalException, SystemException {
387    
388                    PermissionChecker permissionChecker =
389                            PermissionThreadLocal.getPermissionChecker();
390    
391                    String originalPortletId = portletId;
392    
393                    Portlet portlet = PortletLocalServiceUtil.getPortletById(
394                            layout.getCompanyId(), portletId);
395    
396                    long ownerId = 0;
397                    int ownerType = 0;
398                    long plid = 0;
399    
400                    if (modeEditGuest) {
401                            boolean hasUpdateLayoutPermission = LayoutPermissionUtil.contains(
402                                    permissionChecker, layout, ActionKeys.UPDATE);
403    
404                            if (!layout.isPrivateLayout() && hasUpdateLayoutPermission) {
405                            }
406                            else {
407    
408                                    // Only users with the correct permissions can update guest
409                                    // preferences
410    
411                                    throw new PrincipalException();
412                            }
413                    }
414    
415                    if (PortletConstants.hasUserId(originalPortletId) &&
416                            (PortletConstants.getUserId(originalPortletId) == userId)) {
417    
418                            ownerId = userId;
419                            ownerType = PortletKeys.PREFS_OWNER_TYPE_USER;
420                            plid = layout.getPlid();
421                    }
422                    else if (portlet.isPreferencesCompanyWide()) {
423                            ownerId = layout.getCompanyId();
424                            ownerType = PortletKeys.PREFS_OWNER_TYPE_COMPANY;
425                            plid = PortletKeys.PREFS_PLID_SHARED;
426                            portletId = PortletConstants.getRootPortletId(portletId);
427                    }
428                    else {
429                            if (portlet.isPreferencesUniquePerLayout()) {
430                                    ownerId = PortletKeys.PREFS_OWNER_ID_DEFAULT;
431                                    ownerType = PortletKeys.PREFS_OWNER_TYPE_LAYOUT;
432                                    plid = layout.getPlid();
433    
434                                    if (portlet.isPreferencesOwnedByGroup()) {
435                                    }
436                                    else {
437                                            if ((userId <= 0) || modeEditGuest) {
438                                                    userId = UserLocalServiceUtil.getDefaultUserId(
439                                                            layout.getCompanyId());
440                                            }
441    
442                                            ownerId = userId;
443                                            ownerType = PortletKeys.PREFS_OWNER_TYPE_USER;
444                                    }
445                            }
446                            else {
447                                    plid = PortletKeys.PREFS_PLID_SHARED;
448    
449                                    if (portlet.isPreferencesOwnedByGroup()) {
450                                            ownerId = scopeGroupId;
451                                            ownerType = PortletKeys.PREFS_OWNER_TYPE_GROUP;
452                                            portletId = PortletConstants.getRootPortletId(portletId);
453                                    }
454                                    else {
455                                            if ((userId <= 0) || modeEditGuest) {
456                                                    userId = UserLocalServiceUtil.getDefaultUserId(
457                                                            layout.getCompanyId());
458                                            }
459    
460                                            ownerId = userId;
461                                            ownerType = PortletKeys.PREFS_OWNER_TYPE_USER;
462                                    }
463                            }
464                    }
465    
466                    return new PortletPreferencesIds(
467                            layout.getCompanyId(), ownerId, ownerType, plid, portletId);
468            }
469    
470            @Override
471            public PortletPreferences getPortletSetup(
472                            HttpServletRequest request, String portletId)
473                    throws SystemException {
474    
475                    return getPortletSetup(request, portletId, null);
476            }
477    
478            @Override
479            public PortletPreferences getPortletSetup(
480                            HttpServletRequest request, String portletId,
481                            String defaultPreferences)
482                    throws SystemException {
483    
484                    PortletRequest portletRequest = (PortletRequest)request.getAttribute(
485                            JavaConstants.JAVAX_PORTLET_REQUEST);
486    
487                    if (portletRequest instanceof ConfigurationPortletRequest) {
488                            PortletRequestWrapper portletRequestWrapper =
489                                    (PortletRequestWrapper)portletRequest;
490    
491                            return portletRequestWrapper.getPreferences();
492                    }
493    
494                    ThemeDisplay themeDisplay = (ThemeDisplay)request.getAttribute(
495                            WebKeys.THEME_DISPLAY);
496    
497                    return getPortletSetup(
498                            themeDisplay.getScopeGroupId(), themeDisplay.getLayout(), portletId,
499                            defaultPreferences);
500            }
501    
502            @Override
503            public PortletPreferences getPortletSetup(
504                            Layout layout, String portletId, String defaultPreferences)
505                    throws SystemException {
506    
507                    return getPortletSetup(
508                            LayoutConstants.DEFAULT_PLID, layout, portletId,
509                            defaultPreferences);
510            }
511    
512            @Override
513            public PortletPreferences getPortletSetup(
514                            long scopeGroupId, Layout layout, String portletId,
515                            String defaultPreferences)
516                    throws SystemException {
517    
518                    return getPortletSetup(
519                            scopeGroupId, layout, portletId, defaultPreferences, false);
520            }
521    
522            @Override
523            public PortletPreferences getPortletSetup(PortletRequest portletRequest)
524                    throws SystemException {
525    
526                    String portletId = PortalUtil.getPortletId(portletRequest);
527    
528                    return getPortletSetup(portletRequest, portletId);
529            }
530    
531            @Override
532            public PortletPreferences getPortletSetup(
533                            PortletRequest portletRequest, String portletId)
534                    throws SystemException {
535    
536                    if (portletRequest instanceof ConfigurationPortletRequest) {
537                            PortletRequestWrapper portletRequestWrapper =
538                                    (PortletRequestWrapper)portletRequest;
539    
540                            return portletRequestWrapper.getPreferences();
541                    }
542    
543                    HttpServletRequest request = PortalUtil.getHttpServletRequest(
544                            portletRequest);
545    
546                    return getPortletSetup(request, portletId);
547            }
548    
549            @Override
550            public Map<Long, PortletPreferences> getPortletSetupMap(
551                            long companyId, long groupId, long ownerId, int ownerType,
552                            String portletId, boolean privateLayout)
553                    throws SystemException {
554    
555                    Map<Long, PortletPreferences> portletSetupMap =
556                            new HashMap<Long, PortletPreferences>();
557    
558                    List<com.liferay.portal.model.PortletPreferences>
559                            portletPreferencesList =
560                                    PortletPreferencesLocalServiceUtil.getPortletPreferences(
561                                            companyId, groupId, ownerId, ownerType, portletId,
562                                            privateLayout);
563    
564                    for (com.liferay.portal.model.PortletPreferences portletPreferences :
565                                    portletPreferencesList) {
566    
567                            PortletPreferences portletSetup =
568                                    PortletPreferencesLocalServiceUtil.getPreferences(
569                                            companyId, ownerId, ownerType, portletPreferences.getPlid(),
570                                            portletId);
571    
572                            portletSetupMap.put(portletPreferences.getPlid(), portletSetup);
573                    }
574    
575                    return portletSetupMap;
576            }
577    
578            @Override
579            public PortletPreferences getPreferences(HttpServletRequest request) {
580                    PortletRequest portletRequest = (PortletRequest)request.getAttribute(
581                            JavaConstants.JAVAX_PORTLET_REQUEST);
582    
583                    PortletPreferences portletPreferences = null;
584    
585                    if (portletRequest != null) {
586                            PortletPreferencesWrapper portletPreferencesWrapper =
587                                    (PortletPreferencesWrapper)portletRequest.getPreferences();
588    
589                            portletPreferences =
590                                    portletPreferencesWrapper.getPortletPreferencesImpl();
591                    }
592    
593                    return portletPreferences;
594            }
595    
596            @Override
597            public PreferencesValidator getPreferencesValidator(Portlet portlet) {
598                    return PortalUtil.getPreferencesValidator(portlet);
599            }
600    
601            @Override
602            public PortletPreferences getStrictLayoutPortletSetup(
603                            Layout layout, String portletId)
604                    throws SystemException {
605    
606                    long ownerId = PortletKeys.PREFS_OWNER_ID_DEFAULT;
607                    int ownerType = PortletKeys.PREFS_OWNER_TYPE_LAYOUT;
608    
609                    if (PortletConstants.hasUserId(portletId)) {
610                            ownerId = PortletConstants.getUserId(portletId);
611                            ownerType = PortletKeys.PREFS_OWNER_TYPE_USER;
612                    }
613    
614                    return PortletPreferencesLocalServiceUtil.getStrictPreferences(
615                            layout.getCompanyId(), ownerId, ownerType, layout.getPlid(),
616                            portletId);
617            }
618    
619            @Override
620            public PortletPreferences getStrictPortletSetup(
621                            Layout layout, String portletId)
622                    throws SystemException {
623    
624                    return getPortletSetup(
625                            LayoutConstants.DEFAULT_PLID, layout, portletId, StringPool.BLANK,
626                            true);
627            }
628    
629            @Override
630            public StrictPortletPreferencesImpl strictFromXML(
631                            long companyId, long ownerId, int ownerType, long plid,
632                            String portletId, String xml)
633                    throws SystemException {
634    
635                    Map<String, Preference> preferencesMap = toPreferencesMap(xml);
636    
637                    return new StrictPortletPreferencesImpl(
638                            companyId, ownerId, ownerType, plid, portletId, xml,
639                            preferencesMap);
640            }
641    
642            @Override
643            public String toXML(PortalPreferences portalPreferences) {
644                    PortalPreferencesImpl portalPreferencesImpl =
645                            (PortalPreferencesImpl)portalPreferences;
646    
647                    return portalPreferencesImpl.toXML();
648            }
649    
650            @Override
651            public String toXML(PortletPreferences portletPreferences) {
652                    PortletPreferencesImpl portletPreferencesImpl =
653                            (PortletPreferencesImpl)portletPreferences;
654    
655                    return portletPreferencesImpl.toXML();
656            }
657    
658            protected PortletPreferences getPortletSetup(
659                            long scopeGroupId, Layout layout, String portletId,
660                            String defaultPreferences, boolean strictMode)
661                    throws SystemException {
662    
663                    String originalPortletId = portletId;
664    
665                    Portlet portlet = PortletLocalServiceUtil.getPortletById(
666                            layout.getCompanyId(), portletId);
667    
668                    boolean uniquePerLayout = false;
669                    boolean uniquePerGroup = false;
670    
671                    if (portlet.isPreferencesCompanyWide()) {
672                            portletId = PortletConstants.getRootPortletId(portletId);
673                    }
674                    else {
675                            if (portlet.isPreferencesUniquePerLayout()) {
676                                    uniquePerLayout = true;
677    
678                                    if (portlet.isPreferencesOwnedByGroup()) {
679                                            uniquePerGroup = true;
680                                    }
681                            }
682                            else {
683                                    if (portlet.isPreferencesOwnedByGroup()) {
684                                            uniquePerGroup = true;
685                                            portletId = PortletConstants.getRootPortletId(portletId);
686                                    }
687                            }
688                    }
689    
690                    long ownerId = PortletKeys.PREFS_OWNER_ID_DEFAULT;
691                    int ownerType = PortletKeys.PREFS_OWNER_TYPE_LAYOUT;
692                    long plid = layout.getPlid();
693    
694                    Group group = GroupLocalServiceUtil.fetchGroup(scopeGroupId);
695    
696                    if ((group != null) && group.isLayout()) {
697                            plid = group.getClassPK();
698                    }
699    
700                    if (PortletConstants.hasUserId(originalPortletId)) {
701                            ownerId = PortletConstants.getUserId(originalPortletId);
702                            ownerType = PortletKeys.PREFS_OWNER_TYPE_USER;
703                    }
704                    else if (!uniquePerLayout) {
705                            plid = PortletKeys.PREFS_PLID_SHARED;
706    
707                            if (uniquePerGroup) {
708                                    if (scopeGroupId > LayoutConstants.DEFAULT_PLID) {
709                                            ownerId = scopeGroupId;
710                                    }
711                                    else {
712                                            ownerId = layout.getGroupId();
713                                    }
714    
715                                    ownerType = PortletKeys.PREFS_OWNER_TYPE_GROUP;
716                            }
717                            else {
718                                    ownerId = layout.getCompanyId();
719                                    ownerType = PortletKeys.PREFS_OWNER_TYPE_COMPANY;
720                            }
721                    }
722    
723                    if (strictMode) {
724                            return PortletPreferencesLocalServiceUtil.getStrictPreferences(
725                                    layout.getCompanyId(), ownerId, ownerType, plid, portletId);
726                    }
727    
728                    return PortletPreferencesLocalServiceUtil.getPreferences(
729                            layout.getCompanyId(), ownerId, ownerType, plid, portletId,
730                            defaultPreferences);
731            }
732    
733            protected Preference readPreference(XMLEventReader xmlEventReader)
734                    throws XMLStreamException {
735    
736                    String name = null;
737                    List<String> values = new ArrayList<String>();
738                    boolean readOnly = false;
739    
740                    while (xmlEventReader.hasNext()) {
741                            XMLEvent xmlEvent = xmlEventReader.nextEvent();
742    
743                            if (xmlEvent.isStartElement()) {
744                                    StartElement startElement = xmlEvent.asStartElement();
745    
746                                    String elementName = startElement.getName().getLocalPart();
747    
748                                    if (elementName.equals("name")) {
749                                            name = StAXReaderUtil.read(xmlEventReader);
750                                    }
751                                    else if (elementName.equals("value")) {
752                                            String value = StAXReaderUtil.read(xmlEventReader);
753    
754                                            values.add(value);
755                                    }
756                                    else if (elementName.equals("read-only")) {
757                                            String value = StAXReaderUtil.read(xmlEventReader);
758    
759                                            readOnly = GetterUtil.getBoolean(value);
760                                    }
761                            }
762                            else if (xmlEvent.isEndElement()) {
763                                    EndElement endElement = xmlEvent.asEndElement();
764    
765                                    String elementName = endElement.getName().getLocalPart();
766    
767                                    if (elementName.equals("preference")) {
768                                            break;
769                                    }
770                            }
771                    }
772    
773                    return new Preference(
774                            name, values.toArray(new String[values.size()]), readOnly);
775            }
776    
777            protected Map<String, Preference> toPreferencesMap(String xml)
778                    throws SystemException {
779    
780                    if (Validator.isNull(xml)) {
781                            return Collections.emptyMap();
782                    }
783    
784                    String cacheKey = _encodeCacheKey(xml);
785    
786                    Map<String, Preference> preferencesMap = _preferencesMapPortalCache.get(
787                            cacheKey);
788    
789                    if (preferencesMap != null) {
790                            return preferencesMap;
791                    }
792    
793                    XMLEventReader xmlEventReader = null;
794    
795                    try {
796                            XMLInputFactory xmlInputFactory =
797                                    StAXReaderUtil.getXMLInputFactory();
798    
799                            xmlEventReader = xmlInputFactory.createXMLEventReader(
800                                    new UnsyncStringReader(xml));
801    
802                            while (xmlEventReader.hasNext()) {
803                                    XMLEvent xmlEvent = xmlEventReader.nextEvent();
804    
805                                    if (xmlEvent.isStartElement()) {
806                                            StartElement startElement = xmlEvent.asStartElement();
807    
808                                            String elementName = startElement.getName().getLocalPart();
809    
810                                            if (elementName.equals("preference")) {
811                                                    Preference preference = readPreference(xmlEventReader);
812    
813                                                    if (preferencesMap == null) {
814                                                            preferencesMap = new HashMap<String, Preference>();
815                                                    }
816    
817                                                    preferencesMap.put(preference.getName(), preference);
818                                            }
819                                    }
820                            }
821                    }
822                    catch (XMLStreamException xse) {
823                            throw new SystemException(xse);
824                    }
825                    finally {
826                            if (xmlEventReader != null) {
827                                    try {
828                                            xmlEventReader.close();
829                                    }
830                                    catch (XMLStreamException xse) {
831                                            if (_log.isDebugEnabled()) {
832                                                    _log.debug(xse, xse);
833                                            }
834                                    }
835                            }
836                    }
837    
838                    if (preferencesMap == null) {
839                            preferencesMap = Collections.emptyMap();
840                    }
841    
842                    _preferencesMapPortalCache.put(cacheKey, preferencesMap);
843    
844                    return preferencesMap;
845            }
846    
847            private String _encodeCacheKey(String xml) {
848                    if (xml.length() <=
849                                    PropsValues.PORTLET_PREFERENCES_CACHE_KEY_THRESHOLD_SIZE) {
850    
851                            return xml;
852                    }
853    
854                    CacheKeyGenerator cacheKeyGenerator =
855                            CacheKeyGeneratorUtil.getCacheKeyGenerator(
856                                    PortletPreferencesFactoryImpl.class.getName());
857    
858                    if (_log.isDebugEnabled()) {
859                            _log.debug("Cache key generator " + cacheKeyGenerator.getClass());
860                    }
861    
862                    return String.valueOf(cacheKeyGenerator.getCacheKey(xml));
863            }
864    
865            private static Log _log = LogFactoryUtil.getLog(
866                    PortletPreferencesFactoryImpl.class);
867            private PortalCache<String, Map<String, Preference>>
868                    _preferencesMapPortalCache = SingleVMPoolUtil.getCache(
869                            PortletPreferencesFactoryImpl.class.getName());
870    
871    }