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