1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34 package info.magnolia.cms.core;
35
36
37 import info.magnolia.cms.security.AccessManager;
38 import info.magnolia.cms.security.AccessManagerImpl;
39 import info.magnolia.cms.security.Permission;
40
41 import java.util.List;
42 import java.util.Map;
43
44 import javax.jcr.NamespaceException;
45 import javax.jcr.RepositoryException;
46
47 import org.apache.jackrabbit.core.SessionImpl;
48 import org.apache.jackrabbit.core.cache.GrowingLRUMap;
49 import org.apache.jackrabbit.core.id.ItemId;
50 import org.apache.jackrabbit.core.id.PropertyId;
51 import org.apache.jackrabbit.core.security.authorization.AbstractCompiledPermissions;
52 import org.apache.jackrabbit.core.security.authorization.PrivilegeManagerImpl;
53 import org.apache.jackrabbit.spi.Name;
54 import org.apache.jackrabbit.spi.Path;
55 import org.apache.jackrabbit.spi.commons.conversion.CachingPathResolver;
56 import org.apache.jackrabbit.spi.commons.conversion.IllegalNameException;
57 import org.apache.jackrabbit.spi.commons.conversion.NameResolver;
58 import org.apache.jackrabbit.spi.commons.conversion.ParsingPathResolver;
59 import org.apache.jackrabbit.spi.commons.conversion.PathResolver;
60 import org.slf4j.Logger;
61 import org.slf4j.LoggerFactory;
62
63
64
65
66
67 public class DefaultACLBasedPermissions extends AbstractCompiledPermissions {
68
69 protected final AccessManager ami = new AccessManagerImpl();
70 @SuppressWarnings("unchecked")
71 protected final Map<ItemId, Boolean> readCache = new GrowingLRUMap(1024, 5000);
72 protected final Object monitor = new Object();
73 protected SessionImpl session;
74
75 private static final Logger log = LoggerFactory.getLogger(DefaultACLBasedPermissions.class);
76
77 protected final long permissionMapping[][] = {
78 {org.apache.jackrabbit.core.security.authorization.Permission.READ, Permission.READ},
79 {org.apache.jackrabbit.core.security.authorization.Permission.SET_PROPERTY, Permission.SET},
80 {org.apache.jackrabbit.core.security.authorization.Permission.ADD_NODE, Permission.ADD},
81 {org.apache.jackrabbit.core.security.authorization.Permission.REMOVE_NODE, Permission.REMOVE},
82 {org.apache.jackrabbit.core.security.authorization.Permission.REMOVE_PROPERTY, Permission.REMOVE},
83 {org.apache.jackrabbit.core.security.authorization.Permission.READ_AC, Permission.EXECUTE},
84 {org.apache.jackrabbit.core.security.authorization.Permission.MODIFY_AC, Permission.EXECUTE},
85 {org.apache.jackrabbit.core.security.authorization.Permission.NODE_TYPE_MNGMT, Permission.ADD},
86 {org.apache.jackrabbit.core.security.authorization.Permission.VERSION_MNGMT, Permission.EXECUTE},
87 {org.apache.jackrabbit.core.security.authorization.Permission.LOCK_MNGMT, Permission.EXECUTE},
88 {org.apache.jackrabbit.core.security.authorization.Permission.LIFECYCLE_MNGMT, Permission.EXECUTE},
89 {org.apache.jackrabbit.core.security.authorization.Permission.RETENTION_MNGMT, Permission.EXECUTE},
90 };
91
92 protected long convertJackrabbitPermissionsToMagnoliaPermissions(long jackRabbitPermissions) {
93 long magnoliaPermissions = 0;
94 for (long[] mapping : permissionMapping) {
95 long jackrabbitPermission = mapping[0];
96 long magnoliaPermission = mapping[1];
97 if ((jackRabbitPermissions & jackrabbitPermission) != 0) {
98 magnoliaPermissions = magnoliaPermissions | magnoliaPermission;
99 }
100 }
101 return magnoliaPermissions;
102 }
103
104
105
106
107
108 protected final PathResolver pathResolver = new CachingPathResolver(new ParsingPathResolver(null, new NameResolver() {
109
110 @Override
111 public Name getQName(String name) throws IllegalNameException, NamespaceException {
112 throw new UnsupportedOperationException();
113 }
114
115 @Override
116 public String getJCRName(Name name) throws NamespaceException {
117 return name.getLocalName();
118 }
119 }));
120
121 public DefaultACLBasedPermissions(List<Permission> permissions, SessionImpl systemSession, Map<?, ?> configuration) {
122
123 ami.setPermissionList(permissions);
124 this.session = systemSession;
125 }
126
127 @Override
128 public boolean canRead(Path itemPath, ItemId itemId) throws RepositoryException {
129
130 if ((itemId != null && "cafebabe-cafe-babe-cafe-babecafebabe".equals(itemId.toString())) || (itemPath != null && "/".equals(itemPath.toString()))) {
131
132 return true;
133 }
134
135 if (itemPath == null) {
136
137
138 if (!itemId.denotesNode()) {
139 itemId = ((PropertyId)itemId).getParentId();
140 }
141
142 synchronized (monitor) {
143
144 if (readCache.containsKey(itemId)) {
145 return readCache.get(itemId);
146 }
147
148 itemPath = session.getHierarchyManager().getPath(itemId);
149 boolean canRead = canRead(itemPath, itemId);
150 readCache.put(itemId, canRead);
151 return canRead;
152 }
153 }
154
155 String path = pathResolver.getJCRPath(itemPath);
156 log.debug("Read request for " + path + " :: " + itemId);
157 return ami.isGranted(path, Permission.READ);
158 }
159
160 @Override
161 protected Result buildResult(Path absPath) throws RepositoryException {
162 throw new UnsupportedOperationException();
163 }
164
165 @Override
166 public Result getResult(Path absPath) throws RepositoryException {
167 throw new UnsupportedOperationException();
168 }
169
170 @Override
171 public boolean grants(Path absPath, int permissions) throws RepositoryException {
172 long magnoliaPermissions = convertJackrabbitPermissionsToMagnoliaPermissions(permissions);
173 return ami.isGranted(pathResolver.getJCRPath(absPath), magnoliaPermissions);
174 }
175
176 @Override
177 public int getPrivileges(Path absPath) throws RepositoryException {
178 throw new UnsupportedOperationException();
179 }
180
181 @Override
182 protected Result buildRepositoryResult() throws RepositoryException {
183 throw new UnsupportedOperationException();
184 }
185
186 @Override
187 protected PrivilegeManagerImpl getPrivilegeManagerImpl() throws RepositoryException {
188 throw new UnsupportedOperationException();
189 }
190
191 }