001
014
015 package com.liferay.portal.search;
016
017 import com.liferay.portal.NoSuchResourceException;
018 import com.liferay.portal.kernel.log.Log;
019 import com.liferay.portal.kernel.log.LogFactoryUtil;
020 import com.liferay.portal.kernel.search.BooleanClauseOccur;
021 import com.liferay.portal.kernel.search.BooleanQuery;
022 import com.liferay.portal.kernel.search.BooleanQueryFactoryUtil;
023 import com.liferay.portal.kernel.search.Document;
024 import com.liferay.portal.kernel.search.Field;
025 import com.liferay.portal.kernel.search.Indexer;
026 import com.liferay.portal.kernel.search.IndexerRegistryUtil;
027 import com.liferay.portal.kernel.search.Query;
028 import com.liferay.portal.kernel.search.SearchContext;
029 import com.liferay.portal.kernel.search.SearchPermissionChecker;
030 import com.liferay.portal.kernel.util.GetterUtil;
031 import com.liferay.portal.kernel.util.StringPool;
032 import com.liferay.portal.kernel.util.UniqueList;
033 import com.liferay.portal.kernel.util.Validator;
034 import com.liferay.portal.model.Group;
035 import com.liferay.portal.model.GroupConstants;
036 import com.liferay.portal.model.ResourceConstants;
037 import com.liferay.portal.model.Role;
038 import com.liferay.portal.model.RoleConstants;
039 import com.liferay.portal.model.UserGroupRole;
040 import com.liferay.portal.security.permission.ActionKeys;
041 import com.liferay.portal.security.permission.AdvancedPermissionChecker;
042 import com.liferay.portal.security.permission.PermissionChecker;
043 import com.liferay.portal.security.permission.PermissionCheckerBag;
044 import com.liferay.portal.security.permission.PermissionThreadLocal;
045 import com.liferay.portal.security.permission.ResourceActionsUtil;
046 import com.liferay.portal.security.permission.ResourceBlockIdsBag;
047 import com.liferay.portal.service.GroupLocalServiceUtil;
048 import com.liferay.portal.service.ResourceBlockLocalServiceUtil;
049 import com.liferay.portal.service.ResourceBlockPermissionLocalServiceUtil;
050 import com.liferay.portal.service.ResourcePermissionLocalServiceUtil;
051 import com.liferay.portal.service.RoleLocalServiceUtil;
052 import com.liferay.portal.service.UserGroupRoleLocalServiceUtil;
053
054 import java.util.ArrayList;
055 import java.util.HashMap;
056 import java.util.List;
057 import java.util.Map;
058
059
065 public class SearchPermissionCheckerImpl implements SearchPermissionChecker {
066
067 public void addPermissionFields(long companyId, Document document) {
068 try {
069 long groupId = GetterUtil.getLong(document.get(Field.GROUP_ID));
070
071 String className = document.get(Field.ENTRY_CLASS_NAME);
072
073 if (Validator.isNull(className)) {
074 return;
075 }
076
077 String classPK = document.get(Field.ROOT_ENTRY_CLASS_PK);
078
079 if (Validator.isNull(classPK)) {
080 classPK = document.get(Field.ENTRY_CLASS_PK);
081 }
082
083 if (Validator.isNull(classPK)) {
084 return;
085 }
086
087 Indexer indexer = IndexerRegistryUtil.getIndexer(className);
088
089 if (!indexer.isPermissionAware()) {
090 return;
091 }
092
093 doAddPermissionFields_6(
094 companyId, groupId, className, classPK, document);
095 }
096 catch (NoSuchResourceException nsre) {
097 }
098 catch (Exception e) {
099 _log.error(e, e);
100 }
101 }
102
103 public Query getPermissionQuery(
104 long companyId, long[] groupIds, long userId, String className,
105 Query query, SearchContext searchContext) {
106
107 try {
108 query = doGetPermissionQuery(
109 companyId, groupIds, userId, className, query, searchContext);
110 }
111 catch (Exception e) {
112 _log.error(e, e);
113 }
114
115 return query;
116 }
117
118 public void updatePermissionFields(
119 String resourceName, String resourceClassPK) {
120
121 try {
122 doUpdatePermissionFields(resourceName, resourceClassPK);
123 }
124 catch (Exception e) {
125 _log.error(e, e);
126 }
127 }
128
129 protected void addRequiredMemberRole(
130 Group group, BooleanQuery permissionQuery)
131 throws Exception {
132
133 if (group.isOrganization()) {
134 Role organizationUserRole = RoleLocalServiceUtil.getRole(
135 group.getCompanyId(), RoleConstants.ORGANIZATION_USER);
136
137 permissionQuery.addTerm(
138 Field.GROUP_ROLE_ID,
139 group.getGroupId() + StringPool.DASH +
140 organizationUserRole.getRoleId());
141 }
142
143 if (group.isSite()) {
144 Role siteMemberRole = RoleLocalServiceUtil.getRole(
145 group.getCompanyId(), RoleConstants.SITE_MEMBER);
146
147 permissionQuery.addTerm(
148 Field.GROUP_ROLE_ID,
149 group.getGroupId() + StringPool.DASH +
150 siteMemberRole.getRoleId());
151 }
152 }
153
154 protected void doAddPermissionFields_6(
155 long companyId, long groupId, String className, String classPK,
156 Document doc)
157 throws Exception {
158
159 Group group = null;
160
161 if (groupId > 0) {
162 group = GroupLocalServiceUtil.getGroup(groupId);
163 }
164
165 List<Role> roles = ResourceActionsUtil.getRoles(
166 companyId, group, className, null);
167
168 long[] roleIdsArray = new long[roles.size()];
169
170 for (int i = 0; i < roleIdsArray.length; i++) {
171 Role role = roles.get(i);
172
173 roleIdsArray[i] = role.getRoleId();
174 }
175
176 boolean[] hasResourcePermissions = null;
177
178 if (ResourceBlockLocalServiceUtil.isSupported(className)) {
179 ResourceBlockIdsBag resourceBlockIdsBag =
180 ResourceBlockLocalServiceUtil.getResourceBlockIdsBag(
181 companyId, groupId, className, roleIdsArray);
182
183 long actionId = ResourceBlockLocalServiceUtil.getActionId(
184 className, ActionKeys.VIEW);
185
186 List<Long> resourceBlockIds =
187 resourceBlockIdsBag.getResourceBlockIds(actionId);
188
189 hasResourcePermissions = new boolean[roleIdsArray.length];
190
191 for (long resourceBlockId : resourceBlockIds) {
192 for (int i = 0; i < roleIdsArray.length; i++) {
193 int count =
194 ResourceBlockPermissionLocalServiceUtil.
195 getResourceBlockPermissionsCount(
196 resourceBlockId, roleIdsArray[i]);
197
198 hasResourcePermissions[i] = (count > 0);
199 }
200 }
201 }
202 else {
203 hasResourcePermissions =
204 ResourcePermissionLocalServiceUtil.hasResourcePermissions(
205 companyId, className, ResourceConstants.SCOPE_INDIVIDUAL,
206 classPK, roleIdsArray, ActionKeys.VIEW);
207 }
208
209 List<Long> roleIds = new ArrayList<Long>();
210 List<String> groupRoleIds = new ArrayList<String>();
211
212 for (int i = 0; i < hasResourcePermissions.length; i++) {
213 if (!hasResourcePermissions[i]) {
214 continue;
215 }
216
217 Role role = roles.get(i);
218
219 if ((role.getType() == RoleConstants.TYPE_ORGANIZATION) ||
220 (role.getType() == RoleConstants.TYPE_SITE)) {
221
222 groupRoleIds.add(groupId + StringPool.DASH + role.getRoleId());
223 }
224 else {
225 roleIds.add(role.getRoleId());
226 }
227 }
228
229 doc.addKeyword(
230 Field.ROLE_ID, roleIds.toArray(new Long[roleIds.size()]));
231 doc.addKeyword(
232 Field.GROUP_ROLE_ID,
233 groupRoleIds.toArray(new String[groupRoleIds.size()]));
234 }
235
236 protected Query doGetPermissionQuery(
237 long companyId, long[] groupIds, long userId, String className,
238 Query query, SearchContext searchContext)
239 throws Exception {
240
241 Indexer indexer = IndexerRegistryUtil.getIndexer(className);
242
243 if (!indexer.isPermissionAware()) {
244 return query;
245 }
246
247 PermissionChecker permissionChecker =
248 PermissionThreadLocal.getPermissionChecker();
249
250 AdvancedPermissionChecker advancedPermissionChecker = null;
251
252 if ((permissionChecker != null) &&
253 (permissionChecker instanceof AdvancedPermissionChecker)) {
254
255 advancedPermissionChecker =
256 (AdvancedPermissionChecker)permissionChecker;
257 }
258
259 if (advancedPermissionChecker == null) {
260 return query;
261 }
262
263 PermissionCheckerBag permissionCheckerBag = getPermissionCheckerBag(
264 advancedPermissionChecker, userId);
265
266 if (permissionCheckerBag == null) {
267 return query;
268 }
269
270 List<Group> groups = new UniqueList<Group>();
271 List<Role> roles = new UniqueList<Role>();
272 List<UserGroupRole> userGroupRoles = new UniqueList<UserGroupRole>();
273 Map<Long, List<Role>> groupIdsToRoles = new HashMap<Long, List<Role>>();
274
275 roles.addAll(permissionCheckerBag.getRoles());
276
277 if ((groupIds == null) || (groupIds.length == 0)) {
278 groups.addAll(GroupLocalServiceUtil.getUserGroups(userId, true));
279 groups.addAll(permissionCheckerBag.getGroups());
280
281 userGroupRoles = UserGroupRoleLocalServiceUtil.getUserGroupRoles(
282 userId);
283 }
284 else {
285 groups.addAll(permissionCheckerBag.getGroups());
286
287 for (long groupId : groupIds) {
288 if (GroupLocalServiceUtil.hasUserGroup(userId, groupId)) {
289 Group group = GroupLocalServiceUtil.getGroup(groupId);
290
291 groups.add(group);
292 }
293
294 userGroupRoles.addAll(
295 UserGroupRoleLocalServiceUtil.getUserGroupRoles(
296 userId, groupId));
297 userGroupRoles.addAll(
298 UserGroupRoleLocalServiceUtil.
299 getUserGroupRolesByUserUserGroupAndGroup(
300 userId, groupId));
301 }
302 }
303
304 if (advancedPermissionChecker.isSignedIn()) {
305 roles.add(
306 RoleLocalServiceUtil.getRole(companyId, RoleConstants.GUEST));
307 }
308
309 for (Group group : groups) {
310 PermissionCheckerBag userBag = advancedPermissionChecker.getUserBag(
311 userId, group.getGroupId());
312
313 List<Role> groupRoles = userBag.getRoles();
314
315 groupIdsToRoles.put(group.getGroupId(), groupRoles);
316
317 roles.addAll(groupRoles);
318 }
319
320 return doGetPermissionQuery_6(
321 companyId, groupIds, userId, className, query, searchContext,
322 advancedPermissionChecker, groups, roles, userGroupRoles,
323 groupIdsToRoles);
324 }
325
326 protected Query doGetPermissionQuery_6(
327 long companyId, long[] groupIds, long userId, String className,
328 Query query, SearchContext searchContext,
329 AdvancedPermissionChecker advancedPermissionChecker,
330 List<Group> groups, List<Role> roles,
331 List<UserGroupRole> userGroupRoles,
332 Map<Long, List<Role>> groupIdsToRoles)
333 throws Exception {
334
335 BooleanQuery permissionQuery = BooleanQueryFactoryUtil.create(
336 searchContext);
337
338 if (userId > 0) {
339 permissionQuery.addTerm(Field.USER_ID, userId);
340 }
341
342 BooleanQuery groupsQuery = BooleanQueryFactoryUtil.create(
343 searchContext);
344 BooleanQuery rolesQuery = BooleanQueryFactoryUtil.create(searchContext);
345
346 for (Role role : roles) {
347 String roleName = role.getName();
348
349 if (roleName.equals(RoleConstants.ADMINISTRATOR)) {
350 return query;
351 }
352
353 if (ResourcePermissionLocalServiceUtil.hasResourcePermission(
354 companyId, className, ResourceConstants.SCOPE_COMPANY,
355 String.valueOf(companyId), role.getRoleId(),
356 ActionKeys.VIEW)) {
357
358 return query;
359 }
360
361 if ((role.getType() == RoleConstants.TYPE_REGULAR) &&
362 ResourcePermissionLocalServiceUtil.hasResourcePermission(
363 companyId, className,
364 ResourceConstants.SCOPE_GROUP_TEMPLATE,
365 String.valueOf(GroupConstants.DEFAULT_PARENT_GROUP_ID),
366 role.getRoleId(), ActionKeys.VIEW)) {
367
368 return query;
369 }
370
371 for (Group group : groups) {
372 if (ResourcePermissionLocalServiceUtil.hasResourcePermission(
373 companyId, className, ResourceConstants.SCOPE_GROUP,
374 String.valueOf(group.getGroupId()), role.getRoleId(),
375 ActionKeys.VIEW)) {
376
377 groupsQuery.addTerm(Field.GROUP_ID, group.getGroupId());
378 }
379
380 if ((role.getType() != RoleConstants.TYPE_REGULAR) &&
381 ResourcePermissionLocalServiceUtil.hasResourcePermission(
382 companyId, className,
383 ResourceConstants.SCOPE_GROUP_TEMPLATE,
384 String.valueOf(GroupConstants.DEFAULT_PARENT_GROUP_ID),
385 role.getRoleId(), ActionKeys.VIEW)) {
386
387 List<Role> groupRoles = groupIdsToRoles.get(
388 group.getGroupId());
389
390 if (groupRoles.contains(role)) {
391 groupsQuery.addTerm(Field.GROUP_ID, group.getGroupId());
392 }
393 }
394 }
395
396 rolesQuery.addTerm(Field.ROLE_ID, role.getRoleId());
397 }
398
399 for (Group group : groups) {
400 addRequiredMemberRole(group, rolesQuery);
401 }
402
403 for (UserGroupRole userGroupRole : userGroupRoles) {
404 rolesQuery.addTerm(
405 Field.GROUP_ROLE_ID,
406 userGroupRole.getGroupId() + StringPool.DASH +
407 userGroupRole.getRoleId());
408 }
409
410 if (groupsQuery.hasClauses()) {
411 permissionQuery.add(groupsQuery, BooleanClauseOccur.SHOULD);
412 }
413
414 if (rolesQuery.hasClauses()) {
415 permissionQuery.add(rolesQuery, BooleanClauseOccur.SHOULD);
416 }
417
418 BooleanQuery fullQuery = BooleanQueryFactoryUtil.create(searchContext);
419
420 fullQuery.add(query, BooleanClauseOccur.MUST);
421 fullQuery.add(permissionQuery, BooleanClauseOccur.MUST);
422
423 return fullQuery;
424 }
425
426 protected void doUpdatePermissionFields(
427 String resourceName, String resourceClassPK)
428 throws Exception {
429
430 Indexer indexer = IndexerRegistryUtil.getIndexer(resourceName);
431
432 if (indexer != null) {
433 indexer.reindex(resourceName, GetterUtil.getLong(resourceClassPK));
434 }
435 }
436
437 protected PermissionCheckerBag getPermissionCheckerBag(
438 AdvancedPermissionChecker advancedPermissionChecker, long userId)
439 throws Exception {
440
441 if (!advancedPermissionChecker.isSignedIn()) {
442 return advancedPermissionChecker.getGuestUserBag();
443 }
444 else {
445 return advancedPermissionChecker.getUserBag(userId, 0);
446 }
447 }
448
449 private static Log _log = LogFactoryUtil.getLog(
450 SearchPermissionCheckerImpl.class);
451
452 }