001/*
002 * This library is part of OpenCms -
003 * the Open Source Content Management System
004 *
005 * Copyright (c) Alkacon Software GmbH & Co. KG (https://www.alkacon.com)
006 *
007 * This library is free software; you can redistribute it and/or
008 * modify it under the terms of the GNU Lesser General Public
009 * License as published by the Free Software Foundation; either
010 * version 2.1 of the License, or (at your option) any later version.
011 *
012 * This library is distributed in the hope that it will be useful,
013 * but WITHOUT ANY WARRANTY; without even the implied warranty of
014 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
015 * Lesser General Public License for more details.
016 *
017 * For further information about Alkacon Software GmbH & Co. KG, please see the
018 * company website: https://www.alkacon.com
019 *
020 * For further information about OpenCms, please see the
021 * project website: https://www.opencms.org
022 *
023 * You should have received a copy of the GNU Lesser General Public
024 * License along with this library; if not, write to the Free Software
025 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
026 */
027
028package org.opencms.workplace.commons;
029
030import org.opencms.db.CmsDbEntryNotFoundException;
031import org.opencms.file.CmsGroup;
032import org.opencms.file.CmsObject;
033import org.opencms.file.CmsResource;
034import org.opencms.file.CmsResourceFilter;
035import org.opencms.file.CmsUser;
036import org.opencms.file.history.CmsHistoryPrincipal;
037import org.opencms.jsp.CmsJspActionElement;
038import org.opencms.lock.CmsLockFilter;
039import org.opencms.main.CmsException;
040import org.opencms.main.CmsLog;
041import org.opencms.main.OpenCms;
042import org.opencms.security.CmsAccessControlEntry;
043import org.opencms.security.CmsAccessControlList;
044import org.opencms.security.CmsOrganizationalUnit;
045import org.opencms.security.CmsPermissionSet;
046import org.opencms.security.CmsPrincipal;
047import org.opencms.security.CmsRole;
048import org.opencms.security.I_CmsPrincipal;
049import org.opencms.util.CmsStringUtil;
050import org.opencms.util.CmsUUID;
051import org.opencms.widgets.CmsPrincipalWidget;
052import org.opencms.workplace.CmsDialog;
053import org.opencms.workplace.CmsWorkplace;
054import org.opencms.workplace.CmsWorkplaceSettings;
055import org.opencms.workplace.explorer.CmsResourceUtil;
056
057import java.util.ArrayList;
058import java.util.Arrays;
059import java.util.HashMap;
060import java.util.Iterator;
061import java.util.List;
062import java.util.Map;
063import java.util.Set;
064
065import org.apache.commons.logging.Log;
066
067import jakarta.servlet.http.HttpServletRequest;
068import jakarta.servlet.http.HttpServletResponse;
069import jakarta.servlet.jsp.PageContext;
070
071/**
072 * Provides methods for building the permission settings dialog.<p>
073 *
074 * The following files use this class:
075 * <ul>
076 * <li>/commons/chacc.jsp
077 * </ul>
078 * <p>
079 *
080 * @since 6.0.0
081 */
082public class CmsChacc extends CmsDialog {
083
084    /** Value for the action: add an access control entry. */
085    public static final int ACTION_ADDACE = 300;
086
087    /** Value for the action: delete the permissions. */
088    public static final int ACTION_DELETE = 200;
089
090    /** Value for the action: set the internal use flag. */
091    public static final int ACTION_INTERNALUSE = 400;
092
093    /** Request parameter value for the action: add an access control entry. */
094    public static final String DIALOG_ADDACE = "addace";
095
096    /** Request parameter value for the action: delete the permissions. */
097    public static final String DIALOG_DELETE = "delete";
098
099    /** Request parameter value for the action: set the internal use flag. */
100    public static final String DIALOG_INTERNALUSE = "internaluse";
101
102    /** The dialog type. */
103    public static final String DIALOG_TYPE = "chacc";
104
105    /** Request parameter name for the inherit permissions parameter. */
106    public static final String PARAM_INHERIT = "inherit";
107
108    /** Request parameter name for the internal use only flag. */
109    public static final String PARAM_INTERNAL = "internal";
110
111    /** Request parameter name for the name parameter. */
112    public static final String PARAM_NAME = "name";
113
114    /** Request parameter name for the overwrite inherited permissions parameter. */
115    public static final String PARAM_OVERWRITEINHERITED = "overwriteinherited";
116
117    /** Request parameter name for the responsible parameter. */
118    public static final String PARAM_RESPONSIBLE = "responsible";
119
120    /** Request parameter name for the type parameter. */
121    public static final String PARAM_TYPE = "type";
122
123    /** Request parameter name for the view parameter. */
124    public static final String PARAM_VIEW = "view";
125
126    /** Constant for the request parameters suffix: allow. */
127    public static final String PERMISSION_ALLOW = "allow";
128
129    /** Constant for the request parameters suffix: deny. */
130    public static final String PERMISSION_DENY = "deny";
131
132    /** The log object for this class. */
133    private static final Log LOG = CmsLog.getLog(CmsChacc.class);
134
135    /** Constant for unknown type. */
136    private static final String UNKNOWN_TYPE = "Unknown";
137
138    /** PermissionSet of the current user for the resource. */
139    private CmsPermissionSet m_curPermissions;
140
141    /** Indicates if forms are editable by current user. */
142    private boolean m_editable;
143
144    /** Stores eventual error message Strings. */
145    private List<String> m_errorMessages = new ArrayList<String>();
146
147    /** Indicates if inheritance flags are set as hidden fields for resource folders. */
148    private boolean m_inherit;
149
150    /** The name parameter. */
151    private String m_paramName;
152
153    /** The type parameter. */
154    private String m_paramType;
155
156    /** UUID paramter as String. */
157    private String m_paramUuid;
158
159    /** Stores all possible permission keys of a permission set. */
160    private Set<String> m_permissionKeys = CmsPermissionSet.getPermissionKeys();
161
162    /** Marks if the inherited permissions information should be displayed. */
163    private boolean m_showInheritedPermissions;
164
165    /** The possible types of new access control entries. */
166    private String[] m_types = {
167        I_CmsPrincipal.PRINCIPAL_GROUP,
168        I_CmsPrincipal.PRINCIPAL_USER,
169        CmsRole.PRINCIPAL_ROLE,
170        CmsAccessControlEntry.PRINCIPAL_ALL_OTHERS_NAME,
171        CmsAccessControlEntry.PRINCIPAL_OVERWRITE_ALL_NAME};
172
173    /** The possible type values of access control entries. */
174    private int[] m_typesInt = {
175        CmsAccessControlEntry.ACCESS_FLAGS_GROUP,
176        CmsAccessControlEntry.ACCESS_FLAGS_USER,
177        CmsAccessControlEntry.ACCESS_FLAGS_ROLE,
178        CmsAccessControlEntry.ACCESS_FLAGS_ALLOTHERS,
179        CmsAccessControlEntry.ACCESS_FLAGS_OVERWRITE_ALL};
180
181    /** The possible localized types of new access control entries. */
182    private String[] m_typesLocalized = new String[5];
183
184    /**
185     * Public constructor.<p>
186     *
187     * @param jsp an initialized JSP action element
188     */
189    public CmsChacc(CmsJspActionElement jsp) {
190
191        super(jsp);
192        m_errorMessages.clear();
193    }
194
195    /**
196     * Public constructor with JSP variables.<p>
197     *
198     * @param context the JSP page context
199     * @param req the JSP request
200     * @param res the JSP response
201     */
202    public CmsChacc(PageContext context, HttpServletRequest req, HttpServletResponse res) {
203
204        this(new CmsJspActionElement(context, req, res));
205    }
206
207    /**
208     * Builds a detail view selector.<p>
209     *
210     * @param wp the dialog object
211     * @return the HTML code for the detail view selector
212     */
213    public static String buildSummaryDetailsButtons(CmsDialog wp) {
214
215        StringBuffer result = new StringBuffer(512);
216        // create detail view selector
217        result.append("<table border=\"0\">\n<tr>\n\t<td>");
218        result.append(wp.key(Messages.GUI_PERMISSION_SELECT_VIEW_0));
219        result.append("</td>\n");
220        String selectedView = wp.getSettings().getPermissionDetailView();
221        result.append("\t<form action=\"").append(wp.getDialogUri()).append(
222            "\" method=\"post\" name=\"selectshortview\">\n");
223        result.append("\t<td>\n");
224        result.append("\t<input type=\"hidden\" name=\"");
225        result.append(PARAM_VIEW);
226        result.append("\" value=\"short\">\n");
227        // set parameters to show correct hidden input fields
228        wp.setParamAction(null);
229        result.append(wp.paramsAsHidden());
230        result.append("\t<input  type=\"submit\" class=\"dialogbutton\" value=\"").append(
231            wp.key(Messages.GUI_LABEL_SUMMARY_0)).append("\"");
232        if (!"long".equals(selectedView)) {
233            result.append(" disabled=\"disabled\"");
234        }
235        result.append(">\n");
236        result.append("\t</td>\n");
237        result.append("\t</form>\n\t<form action=\"").append(wp.getDialogUri()).append(
238            "\" method=\"post\" name=\"selectlongview\">\n");
239        result.append("\t<td>\n");
240        result.append("\t<input type=\"hidden\" name=\"");
241        result.append(PARAM_VIEW);
242        result.append("\" value=\"long\">\n");
243        result.append(wp.paramsAsHidden());
244        result.append("\t<input type=\"submit\" class=\"dialogbutton\" value=\"").append(
245            wp.key(Messages.GUI_LABEL_DETAILS_0)).append("\"");
246        if ("long".equals(selectedView)) {
247            result.append(" disabled=\"disabled\"");
248        }
249        result.append(">\n");
250        result.append("\t</td>\n\t</form>\n");
251        result.append("</tr>\n</table>\n");
252        return result.toString();
253    }
254
255    /**
256     * Adds a new access control entry to the resource.<p>
257     *
258     * @return true if a new ace was created, otherwise false
259     */
260    public boolean actionAddAce() {
261
262        String file = getParamResource();
263        String name = getParamName();
264        String type = getParamType();
265        int arrayPosition = -1;
266        try {
267            arrayPosition = Integer.parseInt(type);
268        } catch (Exception e) {
269            // can usually be ignored
270            if (LOG.isInfoEnabled()) {
271                LOG.info(e.getLocalizedMessage());
272            }
273        }
274
275        if (checkNewEntry(name, arrayPosition)) {
276            String permissionString = "";
277            if (getInheritOption() && getSettings().getUserSettings().getDialogPermissionsInheritOnFolder()) {
278                // inherit permissions on folders if setting is enabled
279                permissionString = "+i";
280            }
281            try {
282                // lock resource if autolock is enabled
283                checkLock(getParamResource());
284                if (name.equals(key(Messages.GUI_LABEL_ALLOTHERS_0))) {
285                    getCms().chacc(
286                        file,
287                        getTypes(false)[arrayPosition],
288                        CmsAccessControlEntry.PRINCIPAL_ALL_OTHERS_NAME,
289                        permissionString);
290                } else if (name.equals(key(Messages.GUI_LABEL_OVERWRITEALL_0))) {
291                    getCms().chacc(
292                        file,
293                        getTypes(false)[arrayPosition],
294                        CmsAccessControlEntry.PRINCIPAL_OVERWRITE_ALL_NAME,
295                        permissionString);
296                } else {
297                    if (getTypes(false)[arrayPosition].equalsIgnoreCase(CmsRole.PRINCIPAL_ROLE)) {
298                        // if role, first check if we have to translate the role name
299                        CmsRole role = CmsRole.valueOfRoleName(name);
300                        if (role == null) {
301                            // we need translation
302                            Iterator<CmsRole> it = CmsRole.getSystemRoles().iterator();
303                            while (it.hasNext()) {
304                                role = it.next();
305                                if (role.getName(getLocale()).equalsIgnoreCase(name)) {
306                                    name = role.getRoleName();
307                                    break;
308                                }
309                            }
310                        }
311                    }
312                    getCms().chacc(file, getTypes(false)[arrayPosition], name, permissionString);
313                }
314                return true;
315            } catch (CmsException e) {
316                m_errorMessages.add(e.getMessage());
317                if (LOG.isErrorEnabled()) {
318                    LOG.error(e.getLocalizedMessage(), e);
319                }
320            }
321        }
322        return false;
323    }
324
325    /**
326     * Modifies the Internal Use flag of a resource.<p>
327     * @param request the Http servlet request
328     *
329     * @return true if the operation was was successfully removed, otherwise false
330     */
331    public boolean actionInternalUse(HttpServletRequest request) {
332
333        String internal = request.getParameter(PARAM_INTERNAL);
334
335        CmsResource resource;
336        boolean internalValue = false;
337        if (internal != null) {
338            internalValue = true;
339        }
340        try {
341            resource = getCms().readResource(getParamResource(), CmsResourceFilter.ALL);
342
343            int flags = resource.getFlags();
344
345            if (internalValue) {
346                flags |= CmsResource.FLAG_INTERNAL;
347            } else {
348                flags &= ~CmsResource.FLAG_INTERNAL;
349            }
350
351            getCms().lockResource(getParamResource());
352            getCms().chflags(getParamResource(), flags);
353
354        } catch (CmsException e) {
355            m_errorMessages.add(key(Messages.ERR_MODIFY_INTERNAL_FLAG_0));
356            if (LOG.isErrorEnabled()) {
357                LOG.error(e.getLocalizedMessage(), e);
358            }
359            return false;
360        }
361        return true;
362    }
363
364    /**
365     * Modifies a present access control entry for a resource.<p>
366     *
367     * @param request the Http servlet request
368     * @return true if the modification worked, otherwise false
369     */
370    public boolean actionModifyAce(HttpServletRequest request) {
371
372        String file = getParamResource();
373
374        // get request parameters
375        String name = getParamName();
376        String type = getParamType();
377        String inherit = request.getParameter(PARAM_INHERIT);
378        String overWriteInherited = request.getParameter(PARAM_OVERWRITEINHERITED);
379        String responsible = request.getParameter(PARAM_RESPONSIBLE);
380
381        // get the new permissions
382        Set<String> permissionKeys = CmsPermissionSet.getPermissionKeys();
383        int allowValue = 0;
384        int denyValue = 0;
385        String key, param;
386        int value, paramInt;
387
388        Iterator<String> i = permissionKeys.iterator();
389        // loop through all possible permissions
390        while (i.hasNext()) {
391            key = i.next();
392            value = CmsPermissionSet.getPermissionValue(key);
393            // set the right allowed and denied permissions from request parameters
394            try {
395                param = request.getParameter(value + PERMISSION_ALLOW);
396                paramInt = Integer.parseInt(param);
397                allowValue |= paramInt;
398            } catch (Exception e) {
399                // can usually be ignored
400                if (LOG.isInfoEnabled()) {
401                    LOG.info(e.getLocalizedMessage());
402                }
403            }
404            try {
405                param = request.getParameter(value + PERMISSION_DENY);
406                paramInt = Integer.parseInt(param);
407                denyValue |= paramInt;
408            } catch (Exception e) {
409                // can usually be ignored
410                if (LOG.isInfoEnabled()) {
411                    LOG.info(e.getLocalizedMessage());
412                }
413            }
414        }
415
416        // get the current Ace to get the current ace flags
417        try {
418            List<CmsAccessControlEntry> allEntries = getCms().getAccessControlEntries(file, false);
419            int flags = 0;
420            for (int k = 0; k < allEntries.size(); k++) {
421                CmsAccessControlEntry curEntry = allEntries.get(k);
422                String curType = getEntryType(curEntry.getFlags(), false);
423                I_CmsPrincipal p;
424                try {
425                    p = CmsPrincipal.readPrincipalIncludingHistory(getCms(), curEntry.getPrincipal());
426                } catch (CmsException e) {
427                    p = null;
428                }
429                if (((p != null) && p.getName().equals(name) && curType.equals(type))) {
430                    flags = curEntry.getFlags();
431                    break;
432                } else if (p == null) {
433                    // check if it is the case of a role
434                    CmsRole role = CmsRole.valueOfId(curEntry.getPrincipal());
435                    if ((role != null) && name.equals(role.getRoleName())) {
436                        flags = curEntry.getFlags();
437                        break;
438                    } else if ((curEntry.getPrincipal().equals(CmsAccessControlEntry.PRINCIPAL_ALL_OTHERS_ID)
439                        && name.equals(CmsAccessControlEntry.PRINCIPAL_ALL_OTHERS_NAME))
440                        || (curEntry.getPrincipal().equals(CmsAccessControlEntry.PRINCIPAL_OVERWRITE_ALL_ID)
441                            && name.equals(CmsAccessControlEntry.PRINCIPAL_OVERWRITE_ALL_NAME))) {
442                        flags = curEntry.getFlags();
443                        break;
444                    }
445                }
446            }
447
448            // modify the ace flags to determine inheritance of the current ace
449            if (Boolean.valueOf(inherit).booleanValue()) {
450                flags |= CmsAccessControlEntry.ACCESS_FLAGS_INHERIT;
451            } else {
452                flags &= ~CmsAccessControlEntry.ACCESS_FLAGS_INHERIT;
453            }
454
455            // modify the ace flags to determine overwriting of inherited ace
456            if (Boolean.valueOf(overWriteInherited).booleanValue()) {
457                flags |= CmsAccessControlEntry.ACCESS_FLAGS_OVERWRITE;
458            } else {
459                flags &= ~CmsAccessControlEntry.ACCESS_FLAGS_OVERWRITE;
460            }
461
462            if (Boolean.valueOf(responsible).booleanValue()) {
463                flags |= CmsAccessControlEntry.ACCESS_FLAGS_RESPONSIBLE;
464            } else {
465                flags &= ~CmsAccessControlEntry.ACCESS_FLAGS_RESPONSIBLE;
466            }
467
468            // lock resource if autolock is enabled
469            checkLock(getParamResource());
470            // try to change the access entry
471            if (name.equals(CmsAccessControlEntry.PRINCIPAL_ALL_OTHERS_ID.toString())) {
472                getCms().chacc(
473                    file,
474                    type,
475                    CmsAccessControlEntry.PRINCIPAL_ALL_OTHERS_NAME,
476                    allowValue,
477                    denyValue,
478                    flags);
479            } else if (name.equals(CmsAccessControlEntry.PRINCIPAL_OVERWRITE_ALL_ID.toString())) {
480                getCms().chacc(
481                    file,
482                    type,
483                    CmsAccessControlEntry.PRINCIPAL_OVERWRITE_ALL_NAME,
484                    allowValue,
485                    denyValue,
486                    flags);
487            } else {
488                getCms().chacc(file, type, name, allowValue, denyValue, flags);
489            }
490            return true;
491        } catch (CmsException e) {
492            m_errorMessages.add(key(Messages.ERR_CHACC_MODIFY_ENTRY_0));
493            if (LOG.isErrorEnabled()) {
494                LOG.error(e.getLocalizedMessage(), e);
495            }
496            return false;
497        }
498    }
499
500    /**
501     * Removes a present access control entry from the resource.<p>
502     *
503     * @return true if the ace was successfully removed, otherwise false
504     */
505    public boolean actionRemoveAce() {
506
507        String file = getParamResource();
508        String name = getParamName();
509        String type = getParamType();
510        String uuid = getParamUuid();
511        try {
512            // lock resource if autolock is enabled
513            checkLock(getParamResource());
514            // check if it is the case of a role
515            CmsRole role = CmsRole.valueOfGroupName(name);
516            if (role != null) {
517                // translate the internal group name to a role name
518                name = role.getFqn();
519            }
520            try {
521                getCms().rmacc(file, type, uuid);
522            } catch (CmsException e) {
523                LOG.warn(e.getLocalizedMessage(), e);
524                getCms().rmacc(file, type, name);
525            }
526            return true;
527        } catch (CmsException e) {
528            m_errorMessages.add(key(Messages.ERR_CHACC_DELETE_ENTRY_0));
529            if (LOG.isErrorEnabled()) {
530                LOG.error(e.getLocalizedMessage(), e);
531            }
532            return false;
533        }
534    }
535
536    /**
537     * Builds a String with HTML code to display the users access rights for the current resource.<p>
538     *
539     * @return HTML String with the access rights of the current user
540     */
541    public String buildCurrentPermissions() {
542
543        StringBuffer result = new StringBuffer(
544            dialogToggleStart(
545                key(Messages.GUI_PERMISSION_USER_0),
546                "userpermissions",
547                getSettings().getUserSettings().getDialogExpandUserPermissions()));
548        result.append(dialogWhiteBoxStart());
549        try {
550            result.append(
551                buildPermissionEntryForm(
552                    getSettings().getUser().getId(),
553                    buildPermissionsForCurrentUser(),
554                    false,
555                    false));
556        } catch (CmsException e) {
557            // should never happen
558            if (LOG.isErrorEnabled()) {
559                LOG.error(e.getLocalizedMessage(), e);
560            }
561        }
562        result.append(dialogWhiteBoxEnd());
563        result.append("</div>\n");
564        return result.toString();
565    }
566
567    /**
568     * Returns the error messages if something went wrong.<p>
569     *
570     * @return all error messages
571     */
572    public String buildErrorMessages() {
573
574        StringBuffer result = new StringBuffer(8);
575        String errorMessages = getErrorMessagesString();
576        if (!"".equals(errorMessages)) {
577            result.append(dialogBlock(HTML_START, key(Messages.GUI_PERMISSION_ERROR_0), true));
578            result.append("<font color='red'>").append(errorMessages).append("</font>");
579            result.append(dialogBlockEnd());
580        }
581        return result.toString();
582    }
583
584    /**
585     * Builds a String with HTML code to display the responsible users of a resource.<p>
586     *
587     * @param show true the responsible list is open
588     * @return HTML code for the responsible users of the current resource
589     */
590    public String buildResponsibleList(boolean show) {
591
592        List<CmsResource> parentResources = new ArrayList<CmsResource>();
593        Map<Object, String> responsibles = new HashMap<Object, String>();
594        CmsObject cms = getCms();
595        try {
596            // get all parent folders of the current file
597            parentResources = cms.readPath(getParamResource(), CmsResourceFilter.IGNORE_EXPIRATION);
598        } catch (CmsException e) {
599            // can usually be ignored
600            if (LOG.isInfoEnabled()) {
601                LOG.info(e.getLocalizedMessage());
602            }
603        }
604
605        String resourceRootPath = cms.getRequestContext().addSiteRoot(getParamResource());
606        String site = cms.getRequestContext().getSiteRoot();
607        try {
608            cms.getRequestContext().setSiteRoot("");
609            Iterator<CmsResource> i = parentResources.iterator();
610            while (i.hasNext()) {
611                CmsResource resource = i.next();
612                try {
613                    String rootPath = resource.getRootPath();
614                    Iterator<CmsAccessControlEntry> entries = cms.getAccessControlEntries(rootPath, false).iterator();
615                    while (entries.hasNext()) {
616                        CmsAccessControlEntry ace = entries.next();
617                        if (ace.isResponsible()) {
618                            try {
619                                responsibles.put(
620                                    CmsPrincipal.readPrincipalIncludingHistory(cms, ace.getPrincipal()),
621                                    rootPath);
622                            } catch (CmsDbEntryNotFoundException e) {
623                                responsibles.put(ace.getPrincipal(), rootPath);
624                            }
625                        }
626                    }
627                } catch (CmsException e) {
628                    // can usually be ignored
629                    if (LOG.isInfoEnabled()) {
630                        LOG.info(e.getLocalizedMessage());
631                    }
632                }
633            }
634            if (responsibles.size() == 0) {
635                return key(Messages.GUI_AVAILABILITY_NO_RESPONSIBLES_0);
636            }
637            StringBuffer result = new StringBuffer(512);
638            result.append(dialogToggleStart(key(Messages.GUI_AVAILABILITY_RESPONSIBLES_0), "responsibles", show));
639
640            result.append(dialogWhiteBoxStart());
641            Iterator<Map.Entry<Object, String>> it = responsibles.entrySet().iterator();
642            while (i.hasNext()) {
643                Map.Entry<Object, String> entry = it.next();
644                String name;
645                String ou = null;
646                String image;
647                if (entry.getKey() instanceof I_CmsPrincipal) {
648                    I_CmsPrincipal principal = (I_CmsPrincipal)entry.getKey();
649                    if (principal instanceof CmsHistoryPrincipal) {
650                        if (principal.isGroup()) {
651                            name = ((CmsHistoryPrincipal)principal).getDescription()
652                                + " ("
653                                + principal.getSimpleName()
654                                + ")";
655                            image = "commons/group.png";
656                        } else {
657                            name = ((CmsHistoryPrincipal)principal).getName();
658                            image = "commons/user.png";
659                        }
660                    } else if (principal instanceof CmsGroup) {
661                        name = ((CmsGroup)principal).getDescription(getLocale())
662                            + " ("
663                            + principal.getSimpleName()
664                            + ")";
665                        image = "commons/group.png";
666                    } else {
667                        name = ((CmsUser)principal).getFullName();
668                        image = "commons/user.png";
669                    }
670                    ou = principal.getOuFqn();
671                } else {
672                    // check if it is the case of a role
673                    CmsRole role = CmsRole.valueOfId((CmsUUID)entry.getKey());
674                    if (role != null) {
675                        name = role.getName(getLocale());
676                        image = "commons/role.png";
677                    } else {
678                        name = entry.getKey().toString();
679                        image = "explorer/project_none.gif";
680                    }
681                }
682                result.append("<div class=\"dialogrow\"><img src=\"");
683                result.append(getSkinUri());
684                result.append(image);
685                result.append(
686                    "\" class='noborder' width='16' height='16' alt='Principal' title='Principal'>&nbsp;<span class=\"textbold\">");
687                result.append(name);
688                result.append("</span>");
689                if ("long".equals(getSettings().getPermissionDetailView())) {
690                    String resourceName = entry.getValue();
691                    if (!resourceRootPath.equals(resourceName)) {
692                        result.append("<div class=\"dialogpermissioninherit\">");
693                        result.append(key(Messages.GUI_PERMISSION_INHERITED_FROM_1, new Object[] {resourceName}));
694                        result.append("</div>");
695                    }
696                }
697                try {
698                    if ((ou != null)
699                        && (OpenCms.getOrgUnitManager().getOrganizationalUnits(getCms(), "", true).size() > 1)) {
700                        result.append("<br>");
701                        result.append("<img src='").append(getSkinUri()).append(
702                            "explorer/project_none.gif' class='noborder' width='16' height='16' >");
703                        result.append("<img src='").append(getSkinUri()).append(
704                            "explorer/project_none.gif' class='noborder' width='16' height='16' >");
705                        result.append("&nbsp;");
706                        try {
707                            result.append(
708                                OpenCms.getOrgUnitManager().readOrganizationalUnit(getCms(), ou).getDisplayName(
709                                    getLocale()));
710                        } catch (CmsException e) {
711                            result.append(ou);
712                        }
713                    }
714                } catch (CmsException e) {
715                    // should never happen
716                    if (LOG.isErrorEnabled()) {
717                        LOG.error(e.getLocalizedMessage(), e);
718                    }
719                }
720                result.append("</div>\n");
721            }
722            result.append(dialogWhiteBoxEnd());
723            result.append("</div>\n");
724            return result.toString();
725        } finally {
726            cms.getRequestContext().setSiteRoot(site);
727        }
728    }
729
730    /**
731     * Builds a String with HTML code to display the inherited and own access control entries of a resource.<p>
732     *
733     * @return HTML code for inherited and own entries of the current resource
734     */
735    public String buildRightsList() {
736
737        StringBuffer result = new StringBuffer(
738            dialogToggleStart(
739                key(Messages.GUI_PERMISSION_BEQUEATH_SUBFOLDER_0),
740                "inheritedpermissions",
741                getSettings().getUserSettings().getDialogExpandInheritedPermissions()
742                    || getShowInheritedPermissions()));
743
744        // store all parent folder ids together with path in a map
745        Map<CmsUUID, String> parents = new HashMap<CmsUUID, String>();
746        String path = CmsResource.getParentFolder(getParamResource());
747        List<CmsResource> parentResources = new ArrayList<CmsResource>();
748        try {
749            // get all parent folders of the current file
750            parentResources = getCms().readPath(path, CmsResourceFilter.IGNORE_EXPIRATION);
751        } catch (CmsException e) {
752            // can usually be ignored
753            if (LOG.isInfoEnabled()) {
754                LOG.info(e.getLocalizedMessage());
755            }
756        }
757        Iterator<CmsResource> k = parentResources.iterator();
758        while (k.hasNext()) {
759            // add the current folder to the map
760            CmsResource curRes = k.next();
761            parents.put(curRes.getResourceId(), curRes.getRootPath());
762        }
763
764        // create new ArrayLists in which inherited and non inherited entries are stored
765        ArrayList<CmsAccessControlEntry> ownEntries = new ArrayList<CmsAccessControlEntry>();
766        try {
767            Iterator<CmsAccessControlEntry> itAces = getCms().getAccessControlEntries(
768                getParamResource(),
769                false).iterator();
770            while (itAces.hasNext()) {
771                CmsAccessControlEntry curEntry = itAces.next();
772                if (!curEntry.isInherited()) {
773                    // add the entry to the own rights list
774                    ownEntries.add(curEntry);
775                }
776            }
777        } catch (CmsException e) {
778            // can usually be ignored
779            if (LOG.isInfoEnabled()) {
780                LOG.info(e.getLocalizedMessage());
781            }
782        }
783
784        ArrayList<CmsAccessControlEntry> inheritedEntries = new ArrayList<CmsAccessControlEntry>();
785        try {
786            Iterator<CmsAccessControlEntry> itAces = getCms().getAccessControlEntries(path, true).iterator();
787            while (itAces.hasNext()) {
788                CmsAccessControlEntry curEntry = itAces.next();
789                // add the entry to the inherited rights list for the "long" view
790                if ("long".equals(getSettings().getPermissionDetailView())) {
791                    inheritedEntries.add(curEntry);
792                }
793            }
794        } catch (CmsException e) {
795            // can usually be ignored
796            if (LOG.isInfoEnabled()) {
797                LOG.info(e.getLocalizedMessage());
798            }
799        }
800
801        // now create the inherited entries box
802        result.append(dialogWhiteBox(HTML_START));
803        result.append(buildInheritedList(inheritedEntries, parents));
804        result.append(dialogWhiteBox(HTML_END));
805
806        // close div that toggles visibility of inherited permissions
807        result.append("</div>");
808
809        // create the add user/group form
810        result.append(buildAddForm());
811
812        // create the resource entries box
813        result.append(buildResourceList(ownEntries));
814
815        return result.toString();
816    }
817
818    /**
819     * Returns the current users permission set on the resource.<p>
820     *
821     * @return the users permission set
822     */
823    public CmsPermissionSet getCurPermissions() {
824
825        return m_curPermissions;
826    }
827
828    /**
829     * Returns a list with all error messages which occurred when trying to add a new access control entry.<p>
830     *
831     * @return List of error message Strings
832     */
833    public List<String> getErrorMessages() {
834
835        return m_errorMessages;
836    }
837
838    /**
839     * Returns a String with all error messages occuring when trying to add a new access control entry.<p>
840     *
841     * @return String with error messages, separated by &lt;br&gt;
842     */
843    public String getErrorMessagesString() {
844
845        StringBuffer errors = new StringBuffer(8);
846        Iterator<String> i = getErrorMessages().iterator();
847        while (i.hasNext()) {
848            errors.append(i.next());
849            if (i.hasNext()) {
850                errors.append("<br>");
851            }
852        }
853        return errors.toString();
854    }
855
856    /**
857     * Returns the value of the name parameter,
858     * or null if this parameter was not provided.<p>
859     *
860     * The name parameter stores the name of the group or user.<p>
861     *
862     * @return the value of the name parameter
863     */
864    public String getParamName() {
865
866        return m_paramName;
867    }
868
869    /**
870     * Returns the value of the type parameter,
871     * or null if this parameter was not provided.<p>
872     *
873     * The type parameter stores the type of an ace (group or user).<p>
874     *
875     * @return the value of the type parameter
876     */
877    public String getParamType() {
878
879        return m_paramType;
880    }
881
882    /**
883     * Returns the UUID parameter.<p>
884     *
885     * @return the UUID parameter
886     */
887    public String getParamUuid() {
888
889        return m_paramUuid;
890    }
891
892    /**
893     * Returns if the inherited permissions information should be displayed.<p>
894     *
895     * @return true if the inherited permissions information should be displayed, otherwise false
896     */
897    public boolean getShowInheritedPermissions() {
898
899        return m_showInheritedPermissions;
900    }
901
902    /**
903     * @see org.opencms.workplace.CmsDialog#htmlStart()
904     */
905    @Override
906    public String htmlStart() {
907
908        StringBuffer result = new StringBuffer(256);
909        result.append(super.htmlStart());
910        result.append((new CmsPrincipalWidget().getDialogIncludes(getCms(), null)));
911        result.append("<script  >");
912        result.append("typeField = '").append(PARAM_TYPE).append("';");
913        result.append("</script>");
914        return result.toString();
915    }
916
917    /**
918     * Initializes some member variables to display the form with the right options for the current user.<p>
919     *
920     * This method must be called after initWorkplaceRequestValues().<p>
921     */
922    public void init() {
923
924        // the current user name
925        String userName = getSettings().getUser().getName();
926
927        if (m_typesLocalized[0] == null) {
928            m_typesLocalized[0] = key(Messages.GUI_LABEL_GROUP_0);
929            m_typesLocalized[1] = key(Messages.GUI_LABEL_USER_0);
930            m_typesLocalized[2] = key(Messages.GUI_LABEL_ROLE_0);
931            m_typesLocalized[3] = key(Messages.GUI_LABEL_ALLOTHERS_0);
932            m_typesLocalized[4] = key(Messages.GUI_LABEL_OVERWRITEALL_0);
933        }
934
935        // set flags to show editable or non editable entries
936        setEditable(false);
937        setInheritOption(false);
938        String resName = getParamResource();
939
940        try {
941            // get the current users' permissions
942            setCurPermissions(getCms().getPermissions(getParamResource(), userName));
943
944            // check if the current resource is a folder
945            CmsResource resource = getCms().readResource(getParamResource(), CmsResourceFilter.ALL);
946            if (resource.isFolder()) {
947                // only folders have the inherit option activated
948                setInheritOption(true);
949                if (!resName.endsWith("/")) {
950                    // append manually a "/" to folder name to avoid issues with check if resource is in project
951                    resName += "/";
952                }
953            }
954        } catch (CmsException e) {
955            // can usually be ignored
956            if (LOG.isInfoEnabled()) {
957                LOG.info(e.getLocalizedMessage());
958            }
959        }
960
961        // check the current users permission to change access control entries
962        if ((!getCms().getRequestContext().getCurrentProject().isOnlineProject()
963            && getCms().isInsideCurrentProject(resName))
964            && (OpenCms.getRoleManager().hasRole(getCms(), CmsRole.VFS_MANAGER)
965                || (((m_curPermissions.getAllowedPermissions() & CmsPermissionSet.PERMISSION_CONTROL) > 0)
966                    && !((m_curPermissions.getDeniedPermissions() & CmsPermissionSet.PERMISSION_CONTROL) > 0)))) {
967            if (isBlockingLocked()) {
968                m_errorMessages.add(key(Messages.ERR_PERMISSION_BLOCKING_LOCKS_0));
969            } else {
970                setEditable(true);
971            }
972        }
973    }
974
975    /**
976     * Sets the value of the name parameter.<p>
977     *
978     * @param value the value to set
979     */
980    public void setParamName(String value) {
981
982        m_paramName = value;
983    }
984
985    /**
986     * Sets the value of the type parameter.<p>
987     *
988     * @param value the value to set
989     */
990    public void setParamType(String value) {
991
992        m_paramType = value;
993    }
994
995    /**
996     * Sets the UUID parameter.<p>
997     *
998     * @param uuid the UUID to set
999     */
1000    public void setParamUuid(String uuid) {
1001
1002        m_paramUuid = uuid;
1003    }
1004
1005    /**
1006     * Validates the user input when creating a new access control entry.<p>
1007     *
1008     * @param name the name of the new user/group
1009     * @param arrayPosition the position in the types array
1010     *
1011     * @return true if everything is ok, otherwise false
1012     */
1013    protected boolean checkNewEntry(String name, int arrayPosition) {
1014
1015        m_errorMessages.clear();
1016        boolean inArray = false;
1017        if (getTypes(false)[arrayPosition] != null) {
1018            inArray = true;
1019        }
1020        if (!inArray) {
1021            m_errorMessages.add(key(Messages.ERR_PERMISSION_SELECT_TYPE_0));
1022        }
1023        if (CmsStringUtil.isEmptyOrWhitespaceOnly(name)) {
1024            m_errorMessages.add(key(Messages.ERR_MISSING_GROUP_OR_USER_NAME_0));
1025        }
1026        if (m_errorMessages.size() > 0) {
1027            return false;
1028        }
1029        return true;
1030    }
1031
1032    /**
1033     * Returns the resource on which the specified access control entry was set.<p>
1034     *
1035     * @param entry the current access control entry
1036     * @param parents the parent resources to determine the connected resource
1037     * @return the resource name of the corresponding resource
1038     */
1039    protected String getConnectedResource(CmsAccessControlEntry entry, Map<CmsUUID, String> parents) {
1040
1041        CmsUUID resId = entry.getResource();
1042        String resName = parents.get(resId);
1043        if (CmsStringUtil.isNotEmptyOrWhitespaceOnly(resName)) {
1044            return resName;
1045        }
1046        return resId.toString();
1047    }
1048
1049    /**
1050     * Returns the current editable flag for the user to change ACEs.<p>
1051     *
1052     * @return true if user can edit the permissions, otherwise false
1053     */
1054    protected boolean getEditable() {
1055
1056        return m_editable;
1057    }
1058
1059    /**
1060     * Determines the type of the current access control entry.<p>
1061     *
1062     * @param flags the value of the current flags
1063     * @param all to include all types, or just user and groups
1064     *
1065     * @return String representation of the ace type
1066     */
1067    protected String getEntryType(int flags, boolean all) {
1068
1069        for (int i = 0; i < getTypes(all).length; i++) {
1070            if ((flags & getTypesInt()[i]) > 0) {
1071                return getTypes(all)[i];
1072            }
1073        }
1074        return UNKNOWN_TYPE;
1075    }
1076
1077    /**
1078     * Determines the int type of the current access control entry.<p>
1079     *
1080     * @param flags the value of the current flags
1081     * @return int representation of the ace type as int
1082     */
1083    protected int getEntryTypeInt(int flags) {
1084
1085        for (int i = 0; i < getTypesInt().length; i++) {
1086            if ((flags & getTypesInt()[i]) > 0) {
1087                return i;
1088            }
1089        }
1090        return -1;
1091    }
1092
1093    /**
1094     * Returns if the access control entry can be inherited to subfolders and can overwrite inherited permissions.<p>
1095     *
1096     * @return true to show the checkbox, otherwise false
1097     */
1098    protected boolean getInheritOption() {
1099
1100        return m_inherit;
1101    }
1102
1103    /**
1104     * Returns a String array with the possible entry types.<p>
1105     *
1106     * @param all to include all types, or just user, groups and roles
1107     *
1108     * @return the possible types
1109     */
1110    protected String[] getTypes(boolean all) {
1111
1112        if (!all) {
1113            String[] array = new String[3];
1114            return Arrays.asList(m_types).subList(0, 3).toArray(array);
1115        }
1116        return m_types;
1117    }
1118
1119    /**
1120     * Returns an int array with possible entry types.<p>
1121     *
1122     * @return the possible types as int array
1123     */
1124    protected int[] getTypesInt() {
1125
1126        return m_typesInt;
1127    }
1128
1129    /**
1130     * Returns a String array with the possible localized entry types.<p>
1131     *
1132     * @return the possible localized types
1133     */
1134    protected String[] getTypesLocalized() {
1135
1136        return m_typesLocalized;
1137    }
1138
1139    /**
1140     * @see org.opencms.workplace.CmsWorkplace#initWorkplaceRequestValues(org.opencms.workplace.CmsWorkplaceSettings, jakarta.servlet.http.HttpServletRequest)
1141     */
1142    @Override
1143    protected void initWorkplaceRequestValues(CmsWorkplaceSettings settings, HttpServletRequest request) {
1144
1145        // fill the parameter values in the get/set methods
1146        fillParamValues(request);
1147
1148        // set the detail mode of the "inherited" list view
1149        String detail = request.getParameter(PARAM_VIEW);
1150        if (detail != null) {
1151            settings.setPermissionDetailView(detail);
1152            setShowInheritedPermissions(true);
1153        }
1154
1155        // determine which action has to be performed
1156        if (DIALOG_TYPE.equals(getParamAction())) {
1157            setAction(ACTION_DEFAULT);
1158        } else if (DIALOG_SET.equals(getParamAction())) {
1159            setAction(ACTION_SET);
1160        } else if (DIALOG_DELETE.equals(getParamAction())) {
1161            setAction(ACTION_DELETE);
1162        } else if (DIALOG_ADDACE.equals(getParamAction())) {
1163            setAction(ACTION_ADDACE);
1164        } else if (DIALOG_LOCKS_CONFIRMED.equals(getParamAction())) {
1165            setAction(ACTION_LOCKS_CONFIRMED);
1166        } else if (DIALOG_CANCEL.equals(getParamAction())) {
1167            setAction(ACTION_CANCEL);
1168        } else if (DIALOG_INTERNALUSE.equals(getParamAction())) {
1169            setAction(ACTION_INTERNALUSE);
1170        } else {
1171            setAction(ACTION_DEFAULT);
1172            // build the title for chacc dialog
1173            setParamTitle(
1174                key(Messages.GUI_PERMISSION_CHANGE_1, new Object[] {CmsResource.getName(getParamResource())}));
1175        }
1176
1177    }
1178
1179    /**
1180     * Checks if a certain permission of a permission set is allowed.<p>
1181     *
1182     * @param p the current CmsPermissionSet
1183     * @param value the int value of the permission to check
1184     * @return true if the permission is allowed, otherwise false
1185     */
1186    protected boolean isAllowed(CmsPermissionSet p, int value) {
1187
1188        if ((p.getAllowedPermissions() & value) > 0) {
1189            return true;
1190        }
1191        return false;
1192    }
1193
1194    /**
1195     * Checks if a certain permission of a permission set is denied.<p>
1196     *
1197     * @param p the current CmsPermissionSet
1198     * @param value the int value of the permission to check
1199     * @return true if the permission is denied, otherwise false
1200     */
1201    protected boolean isDenied(CmsPermissionSet p, int value) {
1202
1203        if ((p.getDeniedPermissions() & value) > 0) {
1204            return true;
1205        }
1206        return false;
1207    }
1208
1209    /**
1210     * Check if the current permissions are overwriting the inherited ones.<p>
1211     *
1212     * @param flags value of all flags of the current entry
1213     * @return true if permissions are overwriting the inherited ones, otherwise false
1214     */
1215    protected boolean isOverWritingInherited(int flags) {
1216
1217        if ((flags & CmsAccessControlEntry.ACCESS_FLAGS_OVERWRITE) > 0) {
1218            return true;
1219        }
1220        return false;
1221    }
1222
1223    /**
1224     * Check if the user is a responsible for the resource.<p>
1225     *
1226     * @param flags value of all flags of the current entry
1227     * @return true if user is responsible for the resource, otherwise false
1228     */
1229    protected boolean isResponsible(int flags) {
1230
1231        if ((flags & CmsAccessControlEntry.ACCESS_FLAGS_RESPONSIBLE) > 0) {
1232            return true;
1233        }
1234        return false;
1235    }
1236
1237    /**
1238     * Sets the current users permissions on the resource.
1239     * This is set in the init() method.<p>
1240     *
1241     * @param value the CmsPermissionSet
1242     */
1243    protected void setCurPermissions(CmsPermissionSet value) {
1244
1245        m_curPermissions = value;
1246    }
1247
1248    /**
1249     * Sets the editable flag for the forms.
1250     * This is set in the init() method.<p>
1251     *
1252     * @param value true if user can edit the permissions, otherwise false
1253     */
1254    protected void setEditable(boolean value) {
1255
1256        m_editable = value;
1257    }
1258
1259    /**
1260     * Sets if the access control entry can be inherited to subfolders and can overwrite inherited permissions.<p>
1261     *
1262     * This is set in the init() method.<p>
1263     *
1264     * @param value set to true for folders, otherwise false
1265     */
1266    protected void setInheritOption(boolean value) {
1267
1268        m_inherit = value;
1269    }
1270
1271    /**
1272     * Sets if the inherited permissions information should be displayed.<p>
1273     *
1274     * @param showInheritedPermissions true if the inherited permissions information should be displayed, otherwise false
1275     */
1276    protected void setShowInheritedPermissions(boolean showInheritedPermissions) {
1277
1278        m_showInheritedPermissions = showInheritedPermissions;
1279    }
1280
1281    /**
1282     * Builds a String with HTML code to display the form to add a new access control entry for the current resource.<p>
1283     *
1284     * @return HTML String with the form
1285     */
1286    private String buildAddForm() {
1287
1288        StringBuffer result = new StringBuffer(256);
1289
1290        // only display form if the current user has the "control" right
1291        if (getEditable()) {
1292            result.append(dialogSpacer());
1293            result.append(dialogBlockStart(key(Messages.GUI_PERMISSION_ADD_ACE_0)));
1294
1295            // get all possible entry types
1296            ArrayList<String> options = new ArrayList<String>();
1297            ArrayList<String> optionValues = new ArrayList<String>();
1298            for (int i = 0; i < (getTypes(false).length - (1 * (isRoleEditable() ? 0 : 1))); i++) {
1299                options.add(getTypesLocalized()[i]);
1300                optionValues.add(Integer.toString(i));
1301            }
1302
1303            // create the input form for adding an ace
1304            result.append("<form action=\"").append(getDialogUri()).append(
1305                "\" method=\"post\" name=\"add\" class=\"nomargin\">\n");
1306            // set parameters to show correct hidden input fields
1307            setParamAction(DIALOG_ADDACE);
1308            setParamType(null);
1309            setParamName(null);
1310            result.append(paramsAsHidden());
1311            result.append("<table border=\"0\" width=\"100%\">\n");
1312            result.append("<tr>\n");
1313            result.append("\t<td>").append(
1314                buildSelect("name=\"" + PARAM_TYPE + "\"", options, optionValues, -1)).append("</td>\n");
1315            result.append("\t<td class=\"maxwidth\"><input type=\"text\" class=\"maxwidth\" name=\"");
1316            result.append(PARAM_NAME);
1317            result.append("\" value=\"\"></td>\n");
1318
1319            result.append("<td><span style='display: block; height: 1px; width: 10px;'/></td>");
1320
1321            result.append(
1322                button(
1323                    new CmsPrincipalWidget().getButtonJs(PARAM_NAME, "add"),
1324                    null,
1325                    "principal",
1326                    org.opencms.workplace.Messages.GUI_DIALOG_BUTTON_SEARCH_0,
1327                    getSettings().getUserSettings().getEditorButtonStyle()));
1328
1329            result.append(
1330                button(
1331                    "javascript:document.forms['add'].submit();",
1332                    null,
1333                    "new",
1334                    Messages.GUI_LABEL_ADD_0,
1335                    getSettings().getUserSettings().getEditorButtonStyle()));
1336
1337            result.append("</tr>\n");
1338            result.append("</form>\n");
1339            result.append("</table>\n");
1340
1341            result.append(dialogBlockEnd());
1342        }
1343        return result.toString();
1344    }
1345
1346    /**
1347     * Builds a StringBuffer with HTML code to show a list of all inherited access control entries.<p>
1348     *
1349     * @param entries ArrayList with all entries to show for the long view
1350     * @param parents Map of parent resources needed to get the connected resources for the detailed view
1351     * @return StringBuffer with HTML code for all entries
1352     */
1353    private StringBuffer buildInheritedList(ArrayList<CmsAccessControlEntry> entries, Map<CmsUUID, String> parents) {
1354
1355        StringBuffer result = new StringBuffer(32);
1356        String view = getSettings().getPermissionDetailView();
1357
1358        // display the long view
1359        if ("long".equals(view)) {
1360            Iterator<CmsAccessControlEntry> i = entries.iterator();
1361            while (i.hasNext()) {
1362                CmsAccessControlEntry curEntry = i.next();
1363                // build the list with enabled extended view and resource name
1364                result.append(buildPermissionEntryForm(curEntry, false, true, getConnectedResource(curEntry, parents)));
1365            }
1366        } else {
1367            // show the short view, use an ACL to build the list
1368            try {
1369                // get the inherited ACL of the parent folder
1370                CmsAccessControlList acList = getCms().getAccessControlList(
1371                    CmsResource.getParentFolder(getParamResource()),
1372                    false);
1373                Iterator<CmsUUID> i = acList.getPrincipals().iterator();
1374                while (i.hasNext()) {
1375                    CmsUUID principalId = i.next();
1376                    if (!principalId.equals(CmsAccessControlEntry.PRINCIPAL_OVERWRITE_ALL_ID)) {
1377                        CmsPermissionSet permissions = acList.getPermissions(principalId);
1378                        // build the list with enabled extended view only
1379                        result.append(buildPermissionEntryForm(principalId, permissions, false, true));
1380                    }
1381                }
1382            } catch (CmsException e) {
1383                // can usually be ignored
1384                if (LOG.isInfoEnabled()) {
1385                    LOG.info(e.getLocalizedMessage());
1386                }
1387            }
1388        }
1389        return result;
1390    }
1391
1392    /**
1393     * Builds a String with HTML code to display the form to add a new access control entry for the current resource.<p>
1394     *
1395     * @return HTML String with the form
1396     */
1397    private String buildInternalForm() {
1398
1399        StringBuffer result = new StringBuffer(128);
1400
1401        CmsResource resource = null;
1402        boolean internal = false;
1403
1404        // try to read the internal flag from the resource
1405        try {
1406            resource = getCms().readResource(getParamResource(), CmsResourceFilter.ALL);
1407            internal = resource.isInternal();
1408        } catch (CmsException e) {
1409            // an error occurred reading the resource
1410            LOG.error(e.getLocalizedMessage());
1411        }
1412
1413        if ((resource != null) && (resource.isFile())) {
1414            // only show internal check box on files
1415            result.append("<form action=\"").append(getDialogUri()).append(
1416                "\" method=\"post\" name=\"internal\" class=\"nomargin\">\n");
1417            result.append("<table border=\"0\" width=\"100%\">\n");
1418            result.append("<tr>\n");
1419            result.append("\t<td class=\"dialogpermissioncell\">").append(key(Messages.GUI_PERMISSION_INTERNAL_0));
1420            result.append(" <input type=\"checkbox\" name=\"");
1421            result.append(PARAM_INTERNAL);
1422            result.append("\" value=\"true\"");
1423            if (internal) {
1424                result.append(" checked=\"checked\"");
1425            }
1426            if (!getEditable()) {
1427                result.append(" disabled=\"disabled\"");
1428            }
1429            result.append(" ></td>\n");
1430            if (getEditable()) {
1431                result.append("<td><input  type=\"submit\" class=\"dialogbutton\" value=\"").append(
1432                    key(Messages.GUI_LABEL_SET_0)).append("\">");
1433            }
1434            result.append("</td>\n");
1435            result.append("</tr>\n");
1436            result.append("</table>\n");
1437            setParamAction(DIALOG_INTERNALUSE);
1438            setParamType(null);
1439            setParamName(null);
1440            result.append(paramsAsHidden());
1441            result.append("</form>\n");
1442        }
1443        return result.toString();
1444
1445    }
1446
1447    /**
1448     * Creates an HTML input form for the current access control entry.<p>
1449     *
1450     * @param entry the current access control entry
1451     * @param editable boolean to determine if the form is editable
1452     * @param extendedView boolean to determine if the view is selectable with DHTML
1453     * @param inheritRes the resource name from which the ace is inherited
1454     * @return StringBuffer with HTML code of the form
1455     */
1456    private StringBuffer buildPermissionEntryForm(
1457        CmsAccessControlEntry entry,
1458        boolean editable,
1459        boolean extendedView,
1460        String inheritRes) {
1461
1462        StringBuffer result = new StringBuffer(512);
1463
1464        // get name and type of the current entry
1465        I_CmsPrincipal principal;
1466        try {
1467            principal = CmsPrincipal.readPrincipalIncludingHistory(getCms(), entry.getPrincipal());
1468        } catch (CmsException e) {
1469            principal = null;
1470        }
1471
1472        String id = (principal != null) ? principal.getName() : entry.getPrincipal().toString();
1473        String name;
1474        String ou = null;
1475        int flags = 0;
1476        if ((principal != null) && (principal instanceof CmsHistoryPrincipal)) {
1477            // there is a history principal entry, handle it
1478            if (principal.isGroup()) {
1479                String niceName = OpenCms.getWorkplaceManager().translateGroupName(principal.getName(), false);
1480                name = key(
1481                    org.opencms.security.Messages.GUI_ORGUNIT_DISPLAY_NAME_2,
1482                    new Object[] {((CmsHistoryPrincipal)principal).getDescription(), niceName});
1483                ou = CmsOrganizationalUnit.getParentFqn(id);
1484                flags = CmsAccessControlEntry.ACCESS_FLAGS_GROUP;
1485            } else {
1486                name = ((CmsHistoryPrincipal)principal).getName();
1487                ou = CmsOrganizationalUnit.getParentFqn(id);
1488                flags = CmsAccessControlEntry.ACCESS_FLAGS_USER;
1489            }
1490        } else if ((principal != null) && principal.isGroup()) {
1491            String niceName = OpenCms.getWorkplaceManager().translateGroupName(principal.getName(), false);
1492            name = key(
1493                org.opencms.security.Messages.GUI_ORGUNIT_DISPLAY_NAME_2,
1494                new Object[] {((CmsGroup)principal).getDescription(getLocale()), niceName});
1495            ou = CmsOrganizationalUnit.getParentFqn(id);
1496            flags = CmsAccessControlEntry.ACCESS_FLAGS_GROUP;
1497        } else if ((principal != null) && principal.isUser()) {
1498            name = ((CmsUser)principal).getFullName();
1499            ou = CmsOrganizationalUnit.getParentFqn(id);
1500            flags = CmsAccessControlEntry.ACCESS_FLAGS_USER;
1501        } else if ((id != null) && id.equals(CmsAccessControlEntry.PRINCIPAL_ALL_OTHERS_ID.toString())) {
1502            name = key(Messages.GUI_LABEL_ALLOTHERS_0);
1503            flags = CmsAccessControlEntry.ACCESS_FLAGS_ALLOTHERS;
1504        } else if ((id != null) && id.equals(CmsAccessControlEntry.PRINCIPAL_OVERWRITE_ALL_ID.toString())) {
1505            name = key(Messages.GUI_LABEL_OVERWRITEALL_0);
1506            flags = CmsAccessControlEntry.ACCESS_FLAGS_OVERWRITE_ALL;
1507        } else {
1508            // check if it is the case of a role
1509            CmsRole role = CmsRole.valueOfId(entry.getPrincipal());
1510            if (role != null) {
1511                name = role.getName(getLocale());
1512                id = role.getRoleName();
1513                flags = CmsAccessControlEntry.ACCESS_FLAGS_ROLE;
1514            } else {
1515                name = entry.getPrincipal().toString();
1516            }
1517        }
1518
1519        if ((flags > 0) && ((entry.getFlags() & flags) == 0)) {
1520            // the flag is set to the wrong principal type
1521            if (LOG.isErrorEnabled()) {
1522                LOG.error(Messages.get().getBundle(getLocale()).key(Messages.ERR_INVALID_ACE_1, entry.toString()));
1523            }
1524            entry = new CmsAccessControlEntry(
1525                entry.getResource(),
1526                entry.getPrincipal(),
1527                entry.getAllowedPermissions(),
1528                entry.getDeniedPermissions(),
1529                (entry.getFlags() | flags));
1530        } else if (entry.getFlags() < CmsAccessControlEntry.ACCESS_FLAGS_USER) {
1531            // the flag is set to NO principal type
1532            if (LOG.isErrorEnabled()) {
1533                LOG.error(Messages.get().getBundle(getLocale()).key(Messages.ERR_INVALID_ACE_1, entry.toString()));
1534            }
1535            entry = new CmsAccessControlEntry(
1536                entry.getResource(),
1537                entry.getPrincipal(),
1538                entry.getAllowedPermissions(),
1539                entry.getDeniedPermissions(),
1540                (entry.getFlags() | CmsAccessControlEntry.ACCESS_FLAGS_GROUP));
1541        }
1542
1543        String type = getEntryType(entry.getFlags(), false);
1544
1545        if (id == null) {
1546            id = "";
1547        }
1548
1549        // set the parameters for the hidden fields
1550        setParamType(type);
1551        setParamName(id);
1552        setParamUuid(entry.getPrincipal().toString());
1553
1554        // set id value for html attributes
1555        String idValue = type + id + entry.getResource();
1556
1557        // get the localized type label
1558        int typeInt = getEntryTypeInt(entry.getFlags());
1559        String typeLocalized = UNKNOWN_TYPE;
1560        if (typeInt >= 0) {
1561            typeLocalized = getTypesLocalized()[typeInt];
1562        }
1563
1564        // determine the right image to display
1565        String typeImg = getTypes(true)[0];
1566        if (typeInt >= 0) {
1567            typeImg = getEntryType(entry.getFlags(), true).toLowerCase();
1568        }
1569
1570        // get all permissions of the current entry
1571        CmsPermissionSet permissions = entry.getPermissions();
1572
1573        // build String for disabled check boxes
1574        String disabled = "";
1575        if (!editable || (typeInt < 0)) {
1576            disabled = " disabled=\"disabled\"";
1577        }
1578
1579        // build the heading
1580        if (!id.equals(CmsAccessControlEntry.PRINCIPAL_OVERWRITE_ALL_ID.toString())) {
1581            result.append(dialogRow(HTML_START));
1582            if (extendedView) {
1583                // for extended view, add toggle symbol and link to output
1584                result.append("<a href=\"javascript:toggleDetail('").append(idValue).append("');\">");
1585                result.append("<img src=\"").append(getSkinUri()).append(
1586                    "commons/plus.png\" class=\"noborder\" id=\"ic-").append(idValue).append("\"></a>");
1587            } else {
1588                result.append("<img src='").append(getSkinUri()).append(
1589                    "explorer/project_none.gif' class='noborder' width='16' height='16' >");
1590            }
1591            result.append("<img src=\"").append(getSkinUri()).append("commons/");
1592            result.append(typeImg);
1593            result.append(".png\" class=\"noborder\" width=\"16\" height=\"16\" alt=\"");
1594            result.append(typeLocalized);
1595            result.append("\" title=\"");
1596            result.append(typeLocalized);
1597            result.append("\">&nbsp;<span class=\"textbold\">");
1598            result.append(name);
1599            result.append("</span>");
1600            if (extendedView) {
1601                // for extended view, add short permissions
1602                result.append("&nbsp;(").append(entry.getPermissions().getPermissionString()).append(")");
1603            }
1604            try {
1605                if ((ou != null)
1606                    && (OpenCms.getOrgUnitManager().getOrganizationalUnits(getCms(), "", true).size() > 1)) {
1607                    result.append("<br>");
1608                    result.append("<img src='").append(getSkinUri()).append(
1609                        "explorer/project_none.gif' class='noborder' width='16' height='16' >");
1610                    result.append("<img src='").append(getSkinUri()).append(
1611                        "explorer/project_none.gif' class='noborder' width='16' height='16' >");
1612                    result.append("&nbsp;");
1613                    try {
1614                        result.append(
1615                            OpenCms.getOrgUnitManager().readOrganizationalUnit(getCms(), ou).getDisplayName(
1616                                getLocale()));
1617                    } catch (CmsException e) {
1618                        result.append(ou);
1619                    }
1620                }
1621            } catch (CmsException e) {
1622                // should never happen
1623                if (LOG.isInfoEnabled()) {
1624                    LOG.info(e.getLocalizedMessage());
1625                }
1626            }
1627            result.append(dialogRow(HTML_END));
1628            if (extendedView) {
1629                // show the resource from which the ace is inherited if present
1630                if (CmsStringUtil.isNotEmptyOrWhitespaceOnly(inheritRes)) {
1631                    result.append("<div class=\"dialogpermissioninherit\">");
1632                    result.append("<img src='").append(getSkinUri()).append(
1633                        "explorer/project_none.gif' class='noborder' width='16' height='16' >");
1634                    result.append("&nbsp;");
1635                    result.append(key(Messages.GUI_PERMISSION_INHERITED_FROM_1, new Object[] {inheritRes}));
1636                    result.append("</div>\n");
1637                }
1638                result.append("<div id =\"").append(idValue).append("\" class=\"hide\">");
1639            }
1640            result.append("<table class=\"dialogpermissiondetails\">\n");
1641
1642            // build the form depending on the editable flag
1643            if (editable) {
1644                result.append("<form action=\"").append(getDialogUri()).append(
1645                    "\" method=\"post\" class=\"nomargin\" name=\"set").append(idValue).append("\">\n");
1646                // set parameters to show correct hidden input fields
1647                setParamAction(DIALOG_SET);
1648                result.append(paramsAsHidden());
1649            } else {
1650                result.append("<form class=\"nomargin\">\n");
1651            }
1652
1653            // build headings for permission descriptions
1654            result.append("<tr>\n");
1655            result.append("\t<td class=\"dialogpermissioncell\"><span class=\"textbold\" unselectable=\"on\">");
1656            result.append(key(Messages.GUI_PERMISSION_0)).append("</span></td>\n");
1657            result.append(
1658                "\t<td class=\"dialogpermissioncell textcenter\"><span class=\"textbold\" unselectable=\"on\">");
1659            result.append(key(Messages.GUI_PERMISSION_ALLOWED_0)).append("</span></td>\n");
1660            result.append(
1661                "\t<td class=\"dialogpermissioncell textcenter\"><span class=\"textbold\" unselectable=\"on\">");
1662            result.append(key(Messages.GUI_PERMISSION_DENIED_0)).append("</span></td>\n");
1663            result.append("</tr>");
1664
1665            Iterator<String> i = m_permissionKeys.iterator();
1666
1667            // show all possible permissions in the form
1668            while (i.hasNext()) {
1669                String key = i.next();
1670                int value = CmsPermissionSet.getPermissionValue(key);
1671                String keyMessage = key(key);
1672                result.append("<tr>\n");
1673                result.append("\t<td class=\"dialogpermissioncell\">").append(keyMessage).append("</td>\n");
1674                result.append("\t<td class=\"dialogpermissioncell textcenter\"><input type=\"checkbox\" name=\"");
1675                result.append(value).append(PERMISSION_ALLOW).append("\" value=\"").append(value).append("\"").append(
1676                    disabled);
1677                if (isAllowed(permissions, value)) {
1678                    result.append(" checked=\"checked\"");
1679                }
1680                result.append("></td>\n");
1681                result.append("\t<td class=\"dialogpermissioncell textcenter\"><input type=\"checkbox\" name=\"");
1682                result.append(value).append(PERMISSION_DENY).append("\" value=\"").append(value).append("\"").append(
1683                    disabled);
1684                if (isDenied(permissions, value)) {
1685                    result.append(" checked=\"checked\"");
1686                }
1687                result.append("></td>\n");
1688                result.append("</tr>\n");
1689            }
1690
1691            // show overwrite check box and buttons only for editable entries
1692            if (editable) {
1693                // do not show the responsible option for the 'all others' ace
1694                if (!id.equals(CmsAccessControlEntry.PRINCIPAL_ALL_OTHERS_ID.toString())) {
1695                    // show owner check box
1696                    result.append("<tr>\n");
1697                    result.append("\t<td class=\"dialogpermissioncell\">").append(
1698                        key(Messages.GUI_LABEL_RESPONSIBLE_0)).append("</td>\n");
1699                    result.append("\t<td class=\"dialogpermissioncell textcenter\">");
1700                    result.append("<input type=\"checkbox\" name=\"").append(PARAM_RESPONSIBLE).append(
1701                        "\" value=\"true\"").append(disabled);
1702                    if (isResponsible(entry.getFlags())) {
1703                        result.append(" checked=\"checked\"");
1704                    }
1705                    result.append("></td>\n");
1706                    result.append("\t<td class=\"dialogpermissioncell\">&nbsp;</td>\n");
1707                    result.append("</tr>\n");
1708                }
1709                // show overwrite inherited check box
1710                result.append("<tr>\n");
1711                result.append("\t<td class=\"dialogpermissioncell\">").append(
1712                    key(Messages.GUI_PERMISSION_OVERWRITE_INHERITED_0)).append("</td>\n");
1713                result.append("\t<td class=\"dialogpermissioncell textcenter\">");
1714                result.append("<input type=\"checkbox\" name=\"").append(PARAM_OVERWRITEINHERITED).append(
1715                    "\" value=\"true\"").append(disabled);
1716                if (isOverWritingInherited(entry.getFlags())) {
1717                    result.append(" checked=\"checked\"");
1718                }
1719                result.append("></td>\n");
1720                result.append("\t<td class=\"dialogpermissioncell\">&nbsp;</td>\n");
1721                result.append("</tr>\n");
1722
1723                // show inherit permissions check box on folders
1724                if (getInheritOption()) {
1725                    result.append("<tr>\n");
1726                    result.append("\t<td class=\"dialogpermissioncell\">").append(
1727                        key(Messages.GUI_PERMISSION_INHERIT_ON_SUBFOLDERS_0)).append("</td>\n");
1728                    result.append("\t<td class=\"dialogpermissioncell textcenter\">");
1729                    result.append("<input type=\"checkbox\" name=\"").append(PARAM_INHERIT).append(
1730                        "\" value=\"true\"").append(disabled);
1731                    if (entry.isInheriting()) {
1732                        result.append(" checked=\"checked\"");
1733                    }
1734                    result.append("></td>\n");
1735                    result.append("\t<td class=\"dialogpermissioncell\">&nbsp;</td>\n");
1736                    result.append("</tr>\n");
1737                }
1738
1739                // show "set" and "delete" buttons
1740                result.append("<tr>\n");
1741                result.append("\t<td>&nbsp;</td>\n");
1742                result.append(
1743                    "\t<td class=\"textcenter\"><input class=\"dialogbutton\" type=\"submit\" value=\"").append(
1744                        key(Messages.GUI_LABEL_SET_0)).append("\"></form></td>\n");
1745                result.append("\t<td class=\"textcenter\">\n");
1746                // build the form for the "delete" button
1747                result.append("\t\t<form class=\"nomargin\" action=\"").append(getDialogUri()).append(
1748                    "\" method=\"post\" name=\"delete").append(idValue).append("\">\n");
1749                // set parameters to show correct hidden input fields
1750                setParamAction(DIALOG_DELETE);
1751                result.append(paramsAsHidden());
1752                result.append("\t\t<input class=\"dialogbutton\" type=\"submit\" value=\"").append(
1753                    key(Messages.GUI_LABEL_DELETE_0)).append("\">\n");
1754                result.append("\t\t</form>\n");
1755                result.append("\t</td>\n");
1756                result.append("</tr>\n");
1757            } else {
1758                // close the form
1759                result.append("</form>\n");
1760            }
1761
1762            result.append("</table>\n");
1763            if (extendedView) {
1764                // close the hidden div for extended view
1765                result.append("</div>");
1766            }
1767        } else {
1768            result.append(dialogRow(HTML_START));
1769
1770            result.append("<table style='margin-left: 13px;' class=\"dialogpermissiondetails\">\n");
1771            // build headings for permission descriptions
1772            result.append("<tr>\n");
1773            result.append("\t<td style=\"width: 280px;\"><span class=\"textbold\" unselectable=\"on\">");
1774
1775            result.append("<img src=\"").append(getSkinUri()).append("commons/");
1776            result.append(typeImg);
1777            result.append(".png\" class=\"noborder\" width=\"16\" height=\"16\" alt=\"");
1778            result.append(typeLocalized);
1779            result.append("\" title=\"");
1780            result.append(typeLocalized);
1781            result.append("\">&nbsp;<span class=\"textbold\">");
1782            result.append(name);
1783            result.append("</span></td>\n");
1784            result.append(
1785                "\t<td class=\"dialogpermissioncell textcenter\"><span class=\"textbold\" unselectable=\"on\">");
1786            if (editable) {
1787                // build the form for the "delete" button
1788                result.append("\t\t<form class=\"nomargin\" action=\"").append(getDialogUri()).append(
1789                    "\" method=\"post\" name=\"delete").append(idValue).append("\">\n");
1790                // set parameters to show correct hidden input fields
1791                setParamAction(DIALOG_DELETE);
1792                result.append(paramsAsHidden());
1793                result.append("\t\t<input class=\"dialogbutton\" type=\"submit\" value=\"").append(
1794                    key(Messages.GUI_LABEL_DELETE_0)).append("\">\n");
1795                result.append("\t\t</form>\n");
1796            }
1797            result.append("</td>\n");
1798            result.append("</tr>");
1799            result.append("</table>\n");
1800            result.append(dialogRow(HTML_END));
1801
1802        }
1803        return result;
1804    }
1805
1806    /**
1807     * @see #buildPermissionEntryForm(CmsAccessControlEntry, boolean, boolean, String)
1808     *
1809     * @param id the UUID of the principal of the permission set
1810     * @param curSet the current permission set
1811     * @param editable boolean to determine if the form is editable
1812     * @param extendedView boolean to determine if the view is selectable with DHTML
1813     * @return String with HTML code of the form
1814     */
1815    private StringBuffer buildPermissionEntryForm(
1816        CmsUUID id,
1817        CmsPermissionSet curSet,
1818        boolean editable,
1819        boolean extendedView) {
1820
1821        String fileName = getParamResource();
1822        int flags = 0;
1823        try {
1824            I_CmsPrincipal p;
1825            try {
1826                p = CmsPrincipal.readPrincipalIncludingHistory(getCms(), id);
1827            } catch (CmsException e) {
1828                p = null;
1829            }
1830            if ((p != null) && p.isGroup()) {
1831                flags = CmsAccessControlEntry.ACCESS_FLAGS_GROUP;
1832            } else if ((p != null) && p.isUser()) {
1833                flags = CmsAccessControlEntry.ACCESS_FLAGS_USER;
1834            } else if ((p == null) && id.equals(CmsAccessControlEntry.PRINCIPAL_ALL_OTHERS_ID)) {
1835                flags = CmsAccessControlEntry.ACCESS_FLAGS_ALLOTHERS;
1836            } else if ((p == null) && id.equals(CmsAccessControlEntry.PRINCIPAL_OVERWRITE_ALL_ID)) {
1837                flags = CmsAccessControlEntry.ACCESS_FLAGS_OVERWRITE_ALL;
1838            } else {
1839                // check if it is the case of a role
1840                CmsRole role = CmsRole.valueOfId(id);
1841                if (role != null) {
1842                    flags = CmsAccessControlEntry.ACCESS_FLAGS_ROLE;
1843                }
1844            }
1845
1846            CmsResource res = getCms().readResource(fileName, CmsResourceFilter.ALL);
1847            CmsAccessControlEntry entry = new CmsAccessControlEntry(res.getResourceId(), id, curSet, flags);
1848            return buildPermissionEntryForm(entry, editable, extendedView, null);
1849        } catch (CmsException e) {
1850            // can usually be ignored
1851            if (LOG.isInfoEnabled()) {
1852                LOG.info(e.getLocalizedMessage());
1853            }
1854            return new StringBuffer("");
1855        }
1856    }
1857
1858    /**
1859     * Returns the actual real permissions (including role, and any other special check) for the current user.<p>
1860     *
1861     * @return the actual real permissions for the current user
1862     *
1863     * @throws CmsException if something goes wrong
1864     */
1865    private CmsPermissionSet buildPermissionsForCurrentUser() throws CmsException {
1866
1867        CmsResourceUtil resUtil = new CmsResourceUtil(
1868            getCms(),
1869            getCms().readResource(getParamResource(), CmsResourceFilter.ALL));
1870        return resUtil.getPermissionSet();
1871    }
1872
1873    /**
1874     * Builds a StringBuffer with HTML code for the access control entries of a resource.<p>
1875     *
1876     * @param entries all access control entries for the resource
1877     * @return StringBuffer with HTML code for all entries
1878     */
1879    private StringBuffer buildResourceList(ArrayList<CmsAccessControlEntry> entries) {
1880
1881        StringBuffer result = new StringBuffer(256);
1882        Iterator<CmsAccessControlEntry> i = entries.iterator();
1883        boolean hasEntries = i.hasNext();
1884
1885        if (hasEntries || !getInheritOption()) {
1886            // create headline for resource entries
1887            result.append(dialogSubheadline(key(Messages.GUI_PERMISSION_TITLE_0)));
1888        }
1889
1890        // create the internal form
1891        result.append(buildInternalForm());
1892
1893        if (hasEntries) {
1894            // only create output if entries are present
1895            result.append(dialogSpacer());
1896            // open white box
1897            result.append(dialogWhiteBox(HTML_START));
1898
1899            // list all entries
1900            while (i.hasNext()) {
1901                CmsAccessControlEntry curEntry = i.next();
1902                result.append(buildPermissionEntryForm(curEntry, getEditable(), false, null));
1903                if (i.hasNext()) {
1904                    result.append(dialogSeparator());
1905                }
1906            }
1907
1908            // close white box
1909            result.append(dialogWhiteBox(HTML_END));
1910        }
1911        return result;
1912    }
1913
1914    /**
1915     * Returns if the requested resource if blocking locked.<p>
1916     *
1917     * @return <code>true</code> if the resource is blocking locked
1918     */
1919    private boolean isBlockingLocked() {
1920
1921        boolean result = true;
1922        CmsLockFilter blockingFilter = CmsLockFilter.FILTER_ALL;
1923        blockingFilter = blockingFilter.filterNotLockableByUser(getCms().getRequestContext().getCurrentUser());
1924        try {
1925            List<String> blocking = getCms().getLockedResources(getParamResource(), blockingFilter);
1926            result = blocking.size() > 0;
1927        } catch (CmsException e) {
1928            if (LOG.isDebugEnabled()) {
1929                LOG.debug(e.getLocalizedMessage(), e);
1930            }
1931        }
1932        return result;
1933    }
1934
1935    /**
1936     * Checks if the current user has the vfs manager role for the current select resource.<p>
1937     *
1938     * @return <code>true</code> if the current user has the vfs manager role for the current select resource
1939     */
1940    private boolean isRoleEditable() {
1941
1942        CmsObject cms = getCms();
1943        String path = getParamResource();
1944        return CmsWorkplace.canEditPermissionsForRoles(cms, path);
1945
1946    }
1947}