@Override
public boolean hasCapability(String methodName, Object target, Object[] arguments) throws RepositoryException {
sd.checkAlive();
if (target instanceof ItemImpl) {
ItemDelegate dlg = ((ItemImpl) target).dlg;
if (dlg.isProtected()) {
return false;
}
boolean isNode = ((ItemImpl) target).isNode();
Node parent = (isNode) ? (Node) target : ((ItemImpl) target).getParent();
if (!parent.isCheckedOut()) {
return false;
}
if (parent.isLocked()) {
return false;
}
AccessManager accessMgr = sessionContext.getAccessManager();
long permission = Permissions.NO_PERMISSION;
if (isNode) {
Tree tree = ((NodeDelegate) dlg).getTree();
if ("addNode".equals(methodName)) {
if (arguments != null && arguments.length > 0) {
// add-node needs to be checked on the (path of) the
// new node that has/will be added
String path = PathUtils.concat(tree.getPath(), sessionContext.getOakName(arguments[0].toString()));
return accessMgr.hasPermissions(path, Session.ACTION_ADD_NODE);
}
} else if ("setPrimaryType".equals(methodName) || "addMixin".equals(methodName) || "removeMixin".equals(methodName)) {
permission = Permissions.NODE_TYPE_MANAGEMENT;
} else if ("orderBefore".equals(methodName)) {
if (tree.isRoot()) {
return false;
} else {
permission = Permissions.MODIFY_CHILD_NODE_COLLECTION;
tree = tree.getParent();
}
} else if ("setProperty".equals(methodName)) {
permission = Permissions.ADD_PROPERTY;
} else if ("remove".equals(methodName)) {
permission = Permissions.REMOVE_NODE;
}
return accessMgr.hasPermissions(tree, null, permission);
} else {
if (methodName.equals("setValue")) {
permission = Permissions.MODIFY_PROPERTY;
} else if ("remove".equals(methodName)) {
permission = Permissions.REMOVE_PROPERTY;
}
Tree tree = dlg.getParent().getTree();
return accessMgr.hasPermissions(tree, ((PropertyDelegate) dlg).getPropertyState(), permission);
}
}
// TODO: add more best-effort checks
return true;