parent
2d15639124
commit
4a4e4beb78
|
|
@ -29,7 +29,7 @@ import javax.enterprise.context.Dependent;
|
||||||
@Dependent
|
@Dependent
|
||||||
public class IdentifierParser {
|
public class IdentifierParser {
|
||||||
|
|
||||||
public Identifier extractIdentifier(final String identifierParam) {
|
public Identifier parseIdentifier(final String identifierParam) {
|
||||||
Objects.requireNonNull(identifierParam, "identifier param is null.");
|
Objects.requireNonNull(identifierParam, "identifier param is null.");
|
||||||
|
|
||||||
if (identifierParam.startsWith(ApiConstants.IDENTIFIER_PREFIX_ID)) {
|
if (identifierParam.startsWith(ApiConstants.IDENTIFIER_PREFIX_ID)) {
|
||||||
|
|
|
||||||
|
|
@ -18,6 +18,7 @@
|
||||||
*/
|
*/
|
||||||
package org.libreccm.api.admin.categorization;
|
package org.libreccm.api.admin.categorization;
|
||||||
|
|
||||||
|
import org.libreccm.api.admin.categorization.dto.CategorizationData;
|
||||||
import org.libreccm.api.admin.categorization.dto.CategoryData;
|
import org.libreccm.api.admin.categorization.dto.CategoryData;
|
||||||
import org.libreccm.api.dto.ListView;
|
import org.libreccm.api.dto.ListView;
|
||||||
import org.libreccm.core.CoreConstants;
|
import org.libreccm.core.CoreConstants;
|
||||||
|
|
@ -28,12 +29,14 @@ import javax.enterprise.context.RequestScoped;
|
||||||
import javax.transaction.Transactional;
|
import javax.transaction.Transactional;
|
||||||
import javax.ws.rs.Consumes;
|
import javax.ws.rs.Consumes;
|
||||||
import javax.ws.rs.DELETE;
|
import javax.ws.rs.DELETE;
|
||||||
|
import javax.ws.rs.DefaultValue;
|
||||||
import javax.ws.rs.GET;
|
import javax.ws.rs.GET;
|
||||||
import javax.ws.rs.POST;
|
import javax.ws.rs.POST;
|
||||||
import javax.ws.rs.PUT;
|
import javax.ws.rs.PUT;
|
||||||
import javax.ws.rs.Path;
|
import javax.ws.rs.Path;
|
||||||
import javax.ws.rs.PathParam;
|
import javax.ws.rs.PathParam;
|
||||||
import javax.ws.rs.Produces;
|
import javax.ws.rs.Produces;
|
||||||
|
import javax.ws.rs.QueryParam;
|
||||||
import javax.ws.rs.core.MediaType;
|
import javax.ws.rs.core.MediaType;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
@ -190,13 +193,56 @@ public class CategoriesApi {
|
||||||
throw new UnsupportedOperationException();
|
throw new UnsupportedOperationException();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@GET
|
||||||
|
@Path("/{domainIdentifier}/{path:^[\\w\\-/]+$}/subcategories")
|
||||||
|
@Produces(MediaType.APPLICATION_JSON)
|
||||||
|
@AuthorizationRequired
|
||||||
|
@RequiresPrivilege(CoreConstants.PRIVILEGE_ADMIN)
|
||||||
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
|
public ListView<CategoryData> getSubCategories(
|
||||||
|
@PathParam("domainIdentifier") final String domainIdentifierParam,
|
||||||
|
@PathParam("path") final String categoryPathTokens,
|
||||||
|
@QueryParam("limit") @DefaultValue("20") final int limit,
|
||||||
|
@QueryParam("offset") @DefaultValue("20") final int offset
|
||||||
|
) {
|
||||||
|
throw new UnsupportedOperationException();
|
||||||
|
}
|
||||||
|
|
||||||
|
@GET
|
||||||
|
@Path("/ID-{categoryId}/subcategories")
|
||||||
|
@Produces(MediaType.APPLICATION_JSON)
|
||||||
|
@AuthorizationRequired
|
||||||
|
@RequiresPrivilege(CoreConstants.PRIVILEGE_ADMIN)
|
||||||
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
|
public ListView<CategoryData> getSubCategories(
|
||||||
|
@PathParam("categoryId") final long categoryId,
|
||||||
|
@QueryParam("limit") @DefaultValue("20") final int limit,
|
||||||
|
@QueryParam("offset") @DefaultValue("20") final int offset
|
||||||
|
) {
|
||||||
|
throw new UnsupportedOperationException();
|
||||||
|
}
|
||||||
|
|
||||||
|
@GET
|
||||||
|
@Path("/UUID-{categoryId}/subcategories")
|
||||||
|
@Produces(MediaType.APPLICATION_JSON)
|
||||||
|
@AuthorizationRequired
|
||||||
|
@RequiresPrivilege(CoreConstants.PRIVILEGE_ADMIN)
|
||||||
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
|
public ListView<CategoryData> getSubCategories(
|
||||||
|
@PathParam("categoryUuid") final String uuid,
|
||||||
|
@QueryParam("limit") @DefaultValue("20") final int limit,
|
||||||
|
@QueryParam("offset") @DefaultValue("20") final int offset
|
||||||
|
) {
|
||||||
|
throw new UnsupportedOperationException();
|
||||||
|
}
|
||||||
|
|
||||||
@GET
|
@GET
|
||||||
@Path("/{domainIdentifier}/{path:^[\\w\\-/]+$}/objects")
|
@Path("/{domainIdentifier}/{path:^[\\w\\-/]+$}/objects")
|
||||||
@Produces(MediaType.APPLICATION_JSON)
|
@Produces(MediaType.APPLICATION_JSON)
|
||||||
@AuthorizationRequired
|
@AuthorizationRequired
|
||||||
@RequiresPrivilege(CoreConstants.PRIVILEGE_ADMIN)
|
@RequiresPrivilege(CoreConstants.PRIVILEGE_ADMIN)
|
||||||
@Transactional(Transactional.TxType.REQUIRED)
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
public CategoryData getObjectsInCategory(
|
public ListView<CategorizationData> getObjectsInCategory(
|
||||||
@PathParam("domainIdentifier") final String domainIdentifierParam,
|
@PathParam("domainIdentifier") final String domainIdentifierParam,
|
||||||
@PathParam("path") final String categoryPathTokens
|
@PathParam("path") final String categoryPathTokens
|
||||||
) {
|
) {
|
||||||
|
|
@ -209,7 +255,7 @@ public class CategoriesApi {
|
||||||
@AuthorizationRequired
|
@AuthorizationRequired
|
||||||
@RequiresPrivilege(CoreConstants.PRIVILEGE_ADMIN)
|
@RequiresPrivilege(CoreConstants.PRIVILEGE_ADMIN)
|
||||||
@Transactional(Transactional.TxType.REQUIRED)
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
public CategoryData getCategoryObjectsInCategory(
|
public ListView<CategorizationData> getCategoryObjectsInCategory(
|
||||||
@PathParam("categoryId") final long categoryId
|
@PathParam("categoryId") final long categoryId
|
||||||
) {
|
) {
|
||||||
throw new UnsupportedOperationException();
|
throw new UnsupportedOperationException();
|
||||||
|
|
@ -221,7 +267,7 @@ public class CategoriesApi {
|
||||||
@AuthorizationRequired
|
@AuthorizationRequired
|
||||||
@RequiresPrivilege(CoreConstants.PRIVILEGE_ADMIN)
|
@RequiresPrivilege(CoreConstants.PRIVILEGE_ADMIN)
|
||||||
@Transactional(Transactional.TxType.REQUIRED)
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
public CategoryData getObjectsInCategory(
|
public ListView<CategorizationData> getObjectsInCategory(
|
||||||
@PathParam("categoryId") final String categoryUuid
|
@PathParam("categoryId") final String categoryUuid
|
||||||
) {
|
) {
|
||||||
throw new UnsupportedOperationException();
|
throw new UnsupportedOperationException();
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,92 @@
|
||||||
|
/*
|
||||||
|
* Copyright (C) 2020 LibreCCM Foundation.
|
||||||
|
*
|
||||||
|
* This library is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU Lesser General Public
|
||||||
|
* License as published by the Free Software Foundation; either
|
||||||
|
* version 2.1 of the License, or (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This library is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||||
|
* Lesser General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU Lesser General Public
|
||||||
|
* License along with this library; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
|
||||||
|
* MA 02110-1301 USA
|
||||||
|
*/
|
||||||
|
package org.libreccm.api.admin.categorization;
|
||||||
|
|
||||||
|
import org.libreccm.api.Identifier;
|
||||||
|
import org.libreccm.api.IdentifierParser;
|
||||||
|
import org.libreccm.categorization.Domain;
|
||||||
|
import org.libreccm.categorization.DomainRepository;
|
||||||
|
|
||||||
|
import javax.enterprise.context.Dependent;
|
||||||
|
import javax.inject.Inject;
|
||||||
|
import javax.ws.rs.WebApplicationException;
|
||||||
|
import javax.ws.rs.core.Response;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Shared repository for the classes of the categorization RESTful api.
|
||||||
|
*
|
||||||
|
* All methods in this class will throw a {@link WebApplicationException} with a
|
||||||
|
* 404 status code if the requested entity is not found.
|
||||||
|
*
|
||||||
|
* @author <a href="mailto:jens.pelzetter@googlemail.com">Jens Pelzetter</a>
|
||||||
|
*/
|
||||||
|
@Dependent
|
||||||
|
public class CategorizationApiRepository {
|
||||||
|
|
||||||
|
@Inject
|
||||||
|
private DomainRepository domainRepository;
|
||||||
|
|
||||||
|
@Inject
|
||||||
|
private IdentifierParser identifierParser;
|
||||||
|
|
||||||
|
public Domain findDomain(final String domainIdentifier) {
|
||||||
|
final Identifier identifier = identifierParser.parseIdentifier(
|
||||||
|
domainIdentifier
|
||||||
|
);
|
||||||
|
switch (identifier.getType()) {
|
||||||
|
case ID:
|
||||||
|
return domainRepository
|
||||||
|
.findById(Long.parseLong(identifier.getIdentifier()))
|
||||||
|
.orElseThrow(
|
||||||
|
() -> new WebApplicationException(
|
||||||
|
String.format(
|
||||||
|
"No Domain with ID %s found.",
|
||||||
|
identifier.getIdentifier()
|
||||||
|
),
|
||||||
|
Response.Status.NOT_FOUND
|
||||||
|
)
|
||||||
|
);
|
||||||
|
case UUID:
|
||||||
|
return domainRepository
|
||||||
|
.findByUuid(identifier.getIdentifier())
|
||||||
|
.orElseThrow(
|
||||||
|
() -> new WebApplicationException(
|
||||||
|
String.format(
|
||||||
|
"No Domain with UUID %s found.",
|
||||||
|
identifier.getIdentifier()
|
||||||
|
),
|
||||||
|
Response.Status.NOT_FOUND
|
||||||
|
)
|
||||||
|
);
|
||||||
|
default:
|
||||||
|
return domainRepository
|
||||||
|
.findByDomainKey(identifier.getIdentifier())
|
||||||
|
.orElseThrow(
|
||||||
|
() -> new WebApplicationException(
|
||||||
|
String.format(
|
||||||
|
"No Domain with domain key %s found.",
|
||||||
|
identifier.getIdentifier()
|
||||||
|
),
|
||||||
|
Response.Status.NOT_FOUND
|
||||||
|
)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
@ -21,10 +21,7 @@ package org.libreccm.api.admin.categorization.dto;
|
||||||
import org.libreccm.categorization.Category;
|
import org.libreccm.categorization.Category;
|
||||||
import org.libreccm.l10n.LocalizedString;
|
import org.libreccm.l10n.LocalizedString;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
|
||||||
import java.util.List;
|
|
||||||
import java.util.Objects;
|
import java.util.Objects;
|
||||||
import java.util.stream.Collectors;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
|
|
@ -50,17 +47,12 @@ public class CategoryData {
|
||||||
|
|
||||||
private boolean abstractCategory;
|
private boolean abstractCategory;
|
||||||
|
|
||||||
private List<CategorizationData> objects;
|
|
||||||
|
|
||||||
private List<AssociatedCategoryData> subCategories;
|
|
||||||
|
|
||||||
private AssociatedCategoryData parentCategory;
|
private AssociatedCategoryData parentCategory;
|
||||||
|
|
||||||
private long categoryOrder;
|
private long categoryOrder;
|
||||||
|
|
||||||
public CategoryData() {
|
public CategoryData() {
|
||||||
objects = new ArrayList<>();
|
// Nothing
|
||||||
subCategories = new ArrayList<>();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public CategoryData(final Category fromCategory) {
|
public CategoryData(final Category fromCategory) {
|
||||||
|
|
@ -77,16 +69,6 @@ public class CategoryData {
|
||||||
enabled = fromCategory.isEnabled();
|
enabled = fromCategory.isEnabled();
|
||||||
visible = fromCategory.isVisible();
|
visible = fromCategory.isVisible();
|
||||||
abstractCategory = fromCategory.isAbstractCategory();
|
abstractCategory = fromCategory.isAbstractCategory();
|
||||||
objects = fromCategory
|
|
||||||
.getObjects()
|
|
||||||
.stream()
|
|
||||||
.map(CategorizationData::new)
|
|
||||||
.collect(Collectors.toList());
|
|
||||||
subCategories = fromCategory
|
|
||||||
.getSubCategories()
|
|
||||||
.stream()
|
|
||||||
.map(AssociatedCategoryData::new)
|
|
||||||
.collect(Collectors.toList());
|
|
||||||
parentCategory = new AssociatedCategoryData(
|
parentCategory = new AssociatedCategoryData(
|
||||||
fromCategory.getParentCategory()
|
fromCategory.getParentCategory()
|
||||||
);
|
);
|
||||||
|
|
@ -164,23 +146,6 @@ public class CategoryData {
|
||||||
this.abstractCategory = abstractCategory;
|
this.abstractCategory = abstractCategory;
|
||||||
}
|
}
|
||||||
|
|
||||||
public List<CategorizationData> getObjects() {
|
|
||||||
return new ArrayList<>(objects);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setObjects(final List<CategorizationData> objects) {
|
|
||||||
this.objects = new ArrayList<>(objects);
|
|
||||||
}
|
|
||||||
|
|
||||||
public List<AssociatedCategoryData> getSubCategories() {
|
|
||||||
return new ArrayList<>(subCategories);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setSubCategories(
|
|
||||||
final List<AssociatedCategoryData> subCategories) {
|
|
||||||
this.subCategories = new ArrayList<>(subCategories);
|
|
||||||
}
|
|
||||||
|
|
||||||
public AssociatedCategoryData getParentCategory() {
|
public AssociatedCategoryData getParentCategory() {
|
||||||
return parentCategory;
|
return parentCategory;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -203,14 +203,23 @@ public class GroupsApi {
|
||||||
@AuthorizationRequired
|
@AuthorizationRequired
|
||||||
@RequiresPrivilege(CoreConstants.PRIVILEGE_ADMIN)
|
@RequiresPrivilege(CoreConstants.PRIVILEGE_ADMIN)
|
||||||
@Transactional(Transactional.TxType.REQUIRED)
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
public List<GroupUserMembership> getMembers(
|
public ListView<GroupUserMembership> getMembers(
|
||||||
@PathParam("groupIdentifier") final String groupIdentifier
|
@PathParam("groupIdentifier") final String groupIdentifier,
|
||||||
|
@QueryParam("limit") @DefaultValue("20") final int limit,
|
||||||
|
@QueryParam("offset") @DefaultValue("0") final int offset
|
||||||
) {
|
) {
|
||||||
return repository.findGroup(groupIdentifier)
|
final Group group = repository.findGroup(groupIdentifier);
|
||||||
.getMemberships()
|
|
||||||
|
return new ListView<>(
|
||||||
|
groupRepository
|
||||||
|
.findGroupMemberships(group, limit, offset)
|
||||||
.stream()
|
.stream()
|
||||||
.map(GroupUserMembership::new)
|
.map(GroupUserMembership::new)
|
||||||
.collect(Collectors.toList());
|
.collect(Collectors.toList()),
|
||||||
|
groupRepository.countGroupMemberships(group),
|
||||||
|
limit,
|
||||||
|
offset
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
@PUT
|
@PUT
|
||||||
|
|
|
||||||
|
|
@ -48,6 +48,8 @@ import java.net.URI;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
import javax.ws.rs.WebApplicationException;
|
import javax.ws.rs.WebApplicationException;
|
||||||
|
import javax.ws.rs.core.Context;
|
||||||
|
import javax.ws.rs.core.UriInfo;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
|
|
@ -56,31 +58,34 @@ import javax.ws.rs.WebApplicationException;
|
||||||
@RequestScoped
|
@RequestScoped
|
||||||
@Path("/roles")
|
@Path("/roles")
|
||||||
public class RolesApi {
|
public class RolesApi {
|
||||||
|
|
||||||
|
@Context
|
||||||
|
private UriInfo uriInfo;
|
||||||
|
|
||||||
@Inject
|
@Inject
|
||||||
private CcmObjectRepository ccmObjectRepository;
|
private CcmObjectRepository ccmObjectRepository;
|
||||||
|
|
||||||
@Inject
|
@Inject
|
||||||
private IdentifierParser identifierExtractor;
|
private IdentifierParser identifierExtractor;
|
||||||
|
|
||||||
@Inject
|
@Inject
|
||||||
private PartyRepository partyRepository;
|
private PartyRepository partyRepository;
|
||||||
|
|
||||||
@Inject
|
@Inject
|
||||||
private PermissionManager permissionManager;
|
private PermissionManager permissionManager;
|
||||||
|
|
||||||
@Inject
|
@Inject
|
||||||
private PermissionRepository permissionRepository;
|
private PermissionRepository permissionRepository;
|
||||||
|
|
||||||
@Inject
|
@Inject
|
||||||
private SecurityApiRepository repository;
|
private SecurityApiRepository repository;
|
||||||
|
|
||||||
@Inject
|
@Inject
|
||||||
private RoleManager roleManager;
|
private RoleManager roleManager;
|
||||||
|
|
||||||
@Inject
|
@Inject
|
||||||
private RoleRepository roleRepository;
|
private RoleRepository roleRepository;
|
||||||
|
|
||||||
@GET
|
@GET
|
||||||
@Path("/")
|
@Path("/")
|
||||||
@Produces(MediaType.APPLICATION_JSON)
|
@Produces(MediaType.APPLICATION_JSON)
|
||||||
|
|
@ -93,7 +98,7 @@ public class RolesApi {
|
||||||
) {
|
) {
|
||||||
final long count = roleRepository.countAll();
|
final long count = roleRepository.countAll();
|
||||||
final List<Role> roles = roleRepository.findAll(limit, offset);
|
final List<Role> roles = roleRepository.findAll(limit, offset);
|
||||||
|
|
||||||
return new ListView<>(
|
return new ListView<>(
|
||||||
roles.stream().map(RoleData::new).collect(Collectors.toList()),
|
roles.stream().map(RoleData::new).collect(Collectors.toList()),
|
||||||
count,
|
count,
|
||||||
|
|
@ -101,7 +106,7 @@ public class RolesApi {
|
||||||
offset
|
offset
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
@GET
|
@GET
|
||||||
@Path("/{roleIdentifier}")
|
@Path("/{roleIdentifier}")
|
||||||
@Produces(MediaType.APPLICATION_JSON)
|
@Produces(MediaType.APPLICATION_JSON)
|
||||||
|
|
@ -113,7 +118,7 @@ public class RolesApi {
|
||||||
) {
|
) {
|
||||||
return new RoleData(repository.findRole(roleIdentifier));
|
return new RoleData(repository.findRole(roleIdentifier));
|
||||||
}
|
}
|
||||||
|
|
||||||
@POST
|
@POST
|
||||||
@Path("/")
|
@Path("/")
|
||||||
@Consumes(MediaType.APPLICATION_JSON)
|
@Consumes(MediaType.APPLICATION_JSON)
|
||||||
|
|
@ -124,14 +129,14 @@ public class RolesApi {
|
||||||
final Role role = new Role();
|
final Role role = new Role();
|
||||||
role.setName(roleData.getName());
|
role.setName(roleData.getName());
|
||||||
role.setDescription(roleData.getDescription());
|
role.setDescription(roleData.getDescription());
|
||||||
|
|
||||||
roleRepository.save(role);
|
roleRepository.save(role);
|
||||||
|
|
||||||
return Response.created(
|
return Response.created(
|
||||||
URI.create(String.format("/api/admin/roles/%s", role.getName()))
|
URI.create(String.format("/api/admin/roles/%s", role.getName()))
|
||||||
).build();
|
).build();
|
||||||
}
|
}
|
||||||
|
|
||||||
@PUT
|
@PUT
|
||||||
@Path("/{roleIdentifier}")
|
@Path("/{roleIdentifier}")
|
||||||
@Consumes(MediaType.APPLICATION_JSON)
|
@Consumes(MediaType.APPLICATION_JSON)
|
||||||
|
|
@ -143,20 +148,20 @@ public class RolesApi {
|
||||||
final RoleData roleData
|
final RoleData roleData
|
||||||
) {
|
) {
|
||||||
final Role role = repository.findRole(roleIdentifier);
|
final Role role = repository.findRole(roleIdentifier);
|
||||||
|
|
||||||
if (roleData != null
|
if (roleData != null
|
||||||
&& roleData.getName() != null
|
&& roleData.getName() != null
|
||||||
&& !roleData.getName().equals(role.getName())) {
|
&& !roleData.getName().equals(role.getName())) {
|
||||||
role.setName(roleData.getName());
|
role.setName(roleData.getName());
|
||||||
}
|
}
|
||||||
|
|
||||||
roleRepository.save(role);
|
roleRepository.save(role);
|
||||||
|
|
||||||
return Response
|
return Response
|
||||||
.ok(String.format("Role %s updated succesfully.", roleIdentifier))
|
.ok(String.format("Role %s updated succesfully.", roleIdentifier))
|
||||||
.build();
|
.build();
|
||||||
}
|
}
|
||||||
|
|
||||||
@DELETE
|
@DELETE
|
||||||
@Path("/{roleIdentifier}")
|
@Path("/{roleIdentifier}")
|
||||||
@Consumes(MediaType.APPLICATION_JSON)
|
@Consumes(MediaType.APPLICATION_JSON)
|
||||||
|
|
@ -172,23 +177,32 @@ public class RolesApi {
|
||||||
.ok(String.format("Role %s deleted successfully.", roleIdentifier))
|
.ok(String.format("Role %s deleted successfully.", roleIdentifier))
|
||||||
.build();
|
.build();
|
||||||
}
|
}
|
||||||
|
|
||||||
@GET
|
@GET
|
||||||
@Path("/{roleIdentifier}/members")
|
@Path("/{roleIdentifier}/members")
|
||||||
@Produces(MediaType.APPLICATION_JSON)
|
@Produces(MediaType.APPLICATION_JSON)
|
||||||
@AuthorizationRequired
|
@AuthorizationRequired
|
||||||
@RequiresPrivilege(CoreConstants.PRIVILEGE_ADMIN)
|
@RequiresPrivilege(CoreConstants.PRIVILEGE_ADMIN)
|
||||||
@Transactional(Transactional.TxType.REQUIRED)
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
public List<RolePartyMembership> getMembers(
|
public ListView<RolePartyMembership> getMembers(
|
||||||
@PathParam("roleIdentifier") final String roleIdentifier
|
@PathParam("roleIdentifier") final String roleIdentifier,
|
||||||
|
@QueryParam("limit") @DefaultValue("20") final int limit,
|
||||||
|
@QueryParam("offset") @DefaultValue("0") final int offset
|
||||||
) {
|
) {
|
||||||
return repository.findRole(roleIdentifier)
|
final Role role = repository.findRole(roleIdentifier);
|
||||||
.getMemberships()
|
final long count = roleRepository.countMembershipsByRole(role);
|
||||||
.stream()
|
return new ListView<>(
|
||||||
.map(RolePartyMembership::new)
|
roleRepository
|
||||||
.collect(Collectors.toList());
|
.findMembershipsByRole(role, limit, offset)
|
||||||
|
.stream()
|
||||||
|
.map(RolePartyMembership::new)
|
||||||
|
.collect(Collectors.toList()),
|
||||||
|
count,
|
||||||
|
limit,
|
||||||
|
offset
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
@PUT
|
@PUT
|
||||||
@Path("/{roleIdentifier}/members/{partyIdentifier}")
|
@Path("/{roleIdentifier}/members/{partyIdentifier}")
|
||||||
@AuthorizationRequired
|
@AuthorizationRequired
|
||||||
|
|
@ -200,9 +214,9 @@ public class RolesApi {
|
||||||
) {
|
) {
|
||||||
final Role role = repository.findRole(groupIdentifier);
|
final Role role = repository.findRole(groupIdentifier);
|
||||||
final Party party = repository.findParty(partyIdentifier);
|
final Party party = repository.findParty(partyIdentifier);
|
||||||
|
|
||||||
roleManager.assignRoleToParty(role, party);
|
roleManager.assignRoleToParty(role, party);
|
||||||
|
|
||||||
return Response
|
return Response
|
||||||
.ok(
|
.ok(
|
||||||
String.format(
|
String.format(
|
||||||
|
|
@ -212,7 +226,7 @@ public class RolesApi {
|
||||||
)
|
)
|
||||||
).build();
|
).build();
|
||||||
}
|
}
|
||||||
|
|
||||||
@DELETE
|
@DELETE
|
||||||
@Path("/{roleIdentifier}/members/{partyIdentifier}")
|
@Path("/{roleIdentifier}/members/{partyIdentifier}")
|
||||||
@AuthorizationRequired
|
@AuthorizationRequired
|
||||||
|
|
@ -224,9 +238,9 @@ public class RolesApi {
|
||||||
) {
|
) {
|
||||||
final Role role = repository.findRole(groupIdentifier);
|
final Role role = repository.findRole(groupIdentifier);
|
||||||
final Party party = repository.findParty(partyIdentifier);
|
final Party party = repository.findParty(partyIdentifier);
|
||||||
|
|
||||||
roleManager.removeRoleFromParty(role, party);
|
roleManager.removeRoleFromParty(role, party);
|
||||||
|
|
||||||
return Response
|
return Response
|
||||||
.ok(
|
.ok(
|
||||||
String.format(
|
String.format(
|
||||||
|
|
@ -237,23 +251,31 @@ public class RolesApi {
|
||||||
)
|
)
|
||||||
.build();
|
.build();
|
||||||
}
|
}
|
||||||
|
|
||||||
@GET
|
@GET
|
||||||
@Path("/{roleIdentifier}/permissions")
|
@Path("/{roleIdentifier}/permissions")
|
||||||
@Produces(MediaType.APPLICATION_JSON)
|
@Produces(MediaType.APPLICATION_JSON)
|
||||||
@AuthorizationRequired
|
@AuthorizationRequired
|
||||||
@RequiresPrivilege(CoreConstants.PRIVILEGE_ADMIN)
|
@RequiresPrivilege(CoreConstants.PRIVILEGE_ADMIN)
|
||||||
@Transactional(Transactional.TxType.REQUIRED)
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
public List<RolePermission> getPermissions(
|
public ListView<RolePermission> getPermissions(
|
||||||
@PathParam("roleIdentifier") final String roleIdentifier
|
@PathParam("roleIdentifier") final String roleIdentifier,
|
||||||
|
@QueryParam("limit") @DefaultValue("20") final int limit,
|
||||||
|
@QueryParam("offset") @DefaultValue("0") final int offset
|
||||||
) {
|
) {
|
||||||
return repository.findRole(roleIdentifier)
|
final Role role = repository.findRole(roleIdentifier);
|
||||||
.getPermissions()
|
return new ListView<>(
|
||||||
.stream()
|
permissionRepository
|
||||||
.map(RolePermission::new)
|
.findPermissionsForRole(role, limit, offset)
|
||||||
.collect(Collectors.toList());
|
.stream()
|
||||||
|
.map(RolePermission::new)
|
||||||
|
.collect(Collectors.toList()),
|
||||||
|
permissionRepository.countPermissionsForRole(role),
|
||||||
|
limit,
|
||||||
|
offset
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
@POST
|
@POST
|
||||||
@Path("/{roleIdentifier}/permissions")
|
@Path("/{roleIdentifier}/permissions")
|
||||||
@Consumes(MediaType.APPLICATION_JSON)
|
@Consumes(MediaType.APPLICATION_JSON)
|
||||||
|
|
@ -266,7 +288,7 @@ public class RolesApi {
|
||||||
) {
|
) {
|
||||||
final Role role = repository.findRole(roleIdentifier);
|
final Role role = repository.findRole(roleIdentifier);
|
||||||
final String privilege = permissionData.getGrantedPrivilege();
|
final String privilege = permissionData.getGrantedPrivilege();
|
||||||
|
|
||||||
final Permission permission;
|
final Permission permission;
|
||||||
if (permissionData.getObject() != null) {
|
if (permissionData.getObject() != null) {
|
||||||
final CcmObject object = ccmObjectRepository
|
final CcmObject object = ccmObjectRepository
|
||||||
|
|
@ -317,7 +339,7 @@ public class RolesApi {
|
||||||
).build();
|
).build();
|
||||||
} else {
|
} else {
|
||||||
permission = permissionManager.grantPrivilege(privilege, role);
|
permission = permissionManager.grantPrivilege(privilege, role);
|
||||||
|
|
||||||
return Response.created(
|
return Response.created(
|
||||||
URI.create(
|
URI.create(
|
||||||
String.format(
|
String.format(
|
||||||
|
|
@ -330,7 +352,7 @@ public class RolesApi {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@DELETE
|
@DELETE
|
||||||
@Path("/{roleIdentifier}/permissions/{permissionIdentifier}")
|
@Path("/{roleIdentifier}/permissions/{permissionIdentifier}")
|
||||||
@AuthorizationRequired
|
@AuthorizationRequired
|
||||||
|
|
@ -343,10 +365,10 @@ public class RolesApi {
|
||||||
final String permissionIdentifierParam
|
final String permissionIdentifierParam
|
||||||
) {
|
) {
|
||||||
final Role role = repository.findRole(roleIdentifier);
|
final Role role = repository.findRole(roleIdentifier);
|
||||||
|
|
||||||
final Identifier permissionIdentifier = identifierExtractor
|
final Identifier permissionIdentifier = identifierExtractor
|
||||||
.extractIdentifier(roleIdentifier);
|
.parseIdentifier(roleIdentifier);
|
||||||
|
|
||||||
final Permission permission;
|
final Permission permission;
|
||||||
switch (permissionIdentifier.getType()) {
|
switch (permissionIdentifier.getType()) {
|
||||||
case ID:
|
case ID:
|
||||||
|
|
@ -375,18 +397,18 @@ public class RolesApi {
|
||||||
Response.Status.NOT_FOUND
|
Response.Status.NOT_FOUND
|
||||||
)
|
)
|
||||||
);
|
);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
return Response
|
return Response
|
||||||
.status(Response.Status.BAD_REQUEST)
|
.status(Response.Status.BAD_REQUEST)
|
||||||
.entity("Permissions can only be identified by ID or UUID.")
|
.entity("Permissions can only be identified by ID or UUID.")
|
||||||
.build();
|
.build();
|
||||||
}
|
}
|
||||||
|
|
||||||
permissionRepository.delete(permission);
|
permissionRepository.delete(permission);
|
||||||
|
|
||||||
return Response.ok().build();
|
return Response.ok().build();
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -63,7 +63,7 @@ class SecurityApiRepository {
|
||||||
|
|
||||||
protected Group findGroup(final String groupIdentifier) {
|
protected Group findGroup(final String groupIdentifier) {
|
||||||
final Identifier identifier = identifierExtractor
|
final Identifier identifier = identifierExtractor
|
||||||
.extractIdentifier(groupIdentifier);
|
.parseIdentifier(groupIdentifier);
|
||||||
|
|
||||||
switch (identifier.getType()) {
|
switch (identifier.getType()) {
|
||||||
case ID:
|
case ID:
|
||||||
|
|
@ -107,7 +107,7 @@ class SecurityApiRepository {
|
||||||
|
|
||||||
protected Party findParty(final String partyIdentifier) {
|
protected Party findParty(final String partyIdentifier) {
|
||||||
final Identifier identifier = identifierExtractor
|
final Identifier identifier = identifierExtractor
|
||||||
.extractIdentifier(partyIdentifier);
|
.parseIdentifier(partyIdentifier);
|
||||||
|
|
||||||
switch (identifier.getType()) {
|
switch (identifier.getType()) {
|
||||||
case ID:
|
case ID:
|
||||||
|
|
@ -152,7 +152,7 @@ class SecurityApiRepository {
|
||||||
|
|
||||||
protected Role findRole(final String roleIdentifier) {
|
protected Role findRole(final String roleIdentifier) {
|
||||||
final Identifier identifier = identifierExtractor
|
final Identifier identifier = identifierExtractor
|
||||||
.extractIdentifier(roleIdentifier);
|
.parseIdentifier(roleIdentifier);
|
||||||
|
|
||||||
switch (identifier.getType()) {
|
switch (identifier.getType()) {
|
||||||
case ID:
|
case ID:
|
||||||
|
|
@ -196,7 +196,7 @@ class SecurityApiRepository {
|
||||||
|
|
||||||
protected User findUser(final String identifierParam) {
|
protected User findUser(final String identifierParam) {
|
||||||
final Identifier identifier = identifierExtractor
|
final Identifier identifier = identifierExtractor
|
||||||
.extractIdentifier(identifierParam);
|
.parseIdentifier(identifierParam);
|
||||||
|
|
||||||
switch (identifier.getType()) {
|
switch (identifier.getType()) {
|
||||||
case ID:
|
case ID:
|
||||||
|
|
|
||||||
|
|
@ -41,19 +41,19 @@ public class RoleData {
|
||||||
|
|
||||||
private LocalizedString description;
|
private LocalizedString description;
|
||||||
|
|
||||||
private List<RolePartyMembership> memberships;
|
// private List<RolePartyMembership> memberships;
|
||||||
|
|
||||||
private List<RolePermission> permissions;
|
private List<RolePermission> permissions;
|
||||||
|
|
||||||
private List<RoleAssignedTask> assignedTasks;
|
// private List<RoleAssignedTask> assignedTasks;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Parameterless constructor for creating empty instances.
|
* Parameterless constructor for creating empty instances.
|
||||||
*/
|
*/
|
||||||
public RoleData() {
|
public RoleData() {
|
||||||
memberships = new ArrayList<>();
|
// membership = new ArrayList<>();
|
||||||
permissions = new ArrayList<>();
|
permissions = new ArrayList<>();
|
||||||
assignedTasks = new ArrayList<>();
|
// assignedTasks = new ArrayList<>();
|
||||||
}
|
}
|
||||||
|
|
||||||
public RoleData(final Role role) {
|
public RoleData(final Role role) {
|
||||||
|
|
@ -64,23 +64,23 @@ public class RoleData {
|
||||||
name = role.getName();
|
name = role.getName();
|
||||||
description = role.getDescription();
|
description = role.getDescription();
|
||||||
|
|
||||||
memberships = role
|
// memberships = role
|
||||||
.getMemberships()
|
// .getMemberships()
|
||||||
.stream()
|
// .stream()
|
||||||
.map(RolePartyMembership::new)
|
// .map(RolePartyMembership::new)
|
||||||
.collect(Collectors.toList());
|
// .collect(Collectors.toList());
|
||||||
|
//
|
||||||
permissions = role
|
// permissions = role
|
||||||
.getPermissions()
|
// .getPermissions()
|
||||||
.stream()
|
// .stream()
|
||||||
.map(RolePermission::new)
|
// .map(RolePermission::new)
|
||||||
.collect(Collectors.toList());
|
// .collect(Collectors.toList());
|
||||||
|
//
|
||||||
assignedTasks = role
|
// assignedTasks = role
|
||||||
.getAssignedTasks()
|
// .getAssignedTasks()
|
||||||
.stream()
|
// .stream()
|
||||||
.map(RoleAssignedTask::new)
|
// .map(RoleAssignedTask::new)
|
||||||
.collect(Collectors.toList());
|
// .collect(Collectors.toList());
|
||||||
}
|
}
|
||||||
|
|
||||||
public long getRoleId() {
|
public long getRoleId() {
|
||||||
|
|
@ -107,21 +107,21 @@ public class RoleData {
|
||||||
this.name = name;
|
this.name = name;
|
||||||
}
|
}
|
||||||
|
|
||||||
public List<RolePartyMembership> getMemberships() {
|
// public List<RolePartyMembership> getMemberships() {
|
||||||
return new ArrayList<>(memberships);
|
// return new ArrayList<>(memberships);
|
||||||
}
|
// }
|
||||||
|
//
|
||||||
public void setMemberships(final List<RolePartyMembership> memberships) {
|
// public void setMemberships(final List<RolePartyMembership> memberships) {
|
||||||
this.memberships = new ArrayList<>(memberships);
|
// this.memberships = new ArrayList<>(memberships);
|
||||||
}
|
// }
|
||||||
|
//
|
||||||
public List<RoleAssignedTask> getAssignedTasks() {
|
// public List<RoleAssignedTask> getAssignedTasks() {
|
||||||
return new ArrayList<>(assignedTasks);
|
// return new ArrayList<>(assignedTasks);
|
||||||
}
|
// }
|
||||||
|
//
|
||||||
public void setAssignedTasks(final List<RoleAssignedTask> assignedTasks) {
|
// public void setAssignedTasks(final List<RoleAssignedTask> assignedTasks) {
|
||||||
this.assignedTasks = new ArrayList<>(assignedTasks);
|
// this.assignedTasks = new ArrayList<>(assignedTasks);
|
||||||
}
|
// }
|
||||||
|
|
||||||
public LocalizedString getDescription() {
|
public LocalizedString getDescription() {
|
||||||
return description;
|
return description;
|
||||||
|
|
|
||||||
|
|
@ -66,31 +66,38 @@ import javax.persistence.Table;
|
||||||
@NamedQuery(
|
@NamedQuery(
|
||||||
name = "Group.findByName",
|
name = "Group.findByName",
|
||||||
query = "SELECT g FROM Group g WHERE g.name = :name "
|
query = "SELECT g FROM Group g WHERE g.name = :name "
|
||||||
+ "ORDER BY g.name")
|
+ "ORDER BY g.name"),
|
||||||
,
|
|
||||||
@NamedQuery(
|
@NamedQuery(
|
||||||
name = "Group.searchByName",
|
name = "Group.searchByName",
|
||||||
query = "SELECT g FROM Group g "
|
query = "SELECT g FROM Group g "
|
||||||
+ "WHERE LOWER(g.name) LIKE CONCAT(LOWER(:name), '%') "
|
+ "WHERE LOWER(g.name) LIKE CONCAT(LOWER(:name), '%') "
|
||||||
+ "ORDER BY g.name")
|
+ "ORDER BY g.name"),
|
||||||
,
|
|
||||||
@NamedQuery(
|
@NamedQuery(
|
||||||
name = "Group.findAllOrderedByGroupName",
|
name = "Group.findAllOrderedByGroupName",
|
||||||
query = "SELECT g FROM Group g ORDER BY g.name")
|
query = "SELECT g FROM Group g ORDER BY g.name"),
|
||||||
,
|
|
||||||
@NamedQuery(
|
@NamedQuery(
|
||||||
name = "Group.findByMember",
|
name = "Group.findByMember",
|
||||||
query = "SELECT g FROM Group g "
|
query = "SELECT g FROM Group g "
|
||||||
+ "JOIN g.memberships m "
|
+ "JOIN g.memberships m "
|
||||||
+ "WHERE m.member = :member"
|
+ "WHERE m.member = :member"
|
||||||
|
),
|
||||||
|
@NamedQuery(
|
||||||
|
name = "Group.findMemberships",
|
||||||
|
query = "SELECT m FROM GroupMembership m "
|
||||||
|
+ "JOIN m.member u "
|
||||||
|
+ "WHERE m.group = :group "
|
||||||
|
+ "ORDER BY u.name"
|
||||||
|
),
|
||||||
|
@NamedQuery(
|
||||||
|
name = "Group.countMemberships",
|
||||||
|
query = "SELECT COUNT(m) FROM GroupMembership m WHERE m.group = :group"
|
||||||
)
|
)
|
||||||
})
|
})
|
||||||
@NamedEntityGraphs({
|
@NamedEntityGraphs({
|
||||||
@NamedEntityGraph(
|
@NamedEntityGraph(
|
||||||
name = "Group.withMembersAndRoleMemberships",
|
name = "Group.withMembersAndRoleMemberships",
|
||||||
attributeNodes = {
|
attributeNodes = {
|
||||||
@NamedAttributeNode(value = "memberships")
|
@NamedAttributeNode(value = "memberships"),
|
||||||
,
|
|
||||||
@NamedAttributeNode(value = "roleMemberships",
|
@NamedAttributeNode(value = "roleMemberships",
|
||||||
subgraph = "role")},
|
subgraph = "role")},
|
||||||
subgraphs = {
|
subgraphs = {
|
||||||
|
|
@ -99,8 +106,7 @@ import javax.persistence.Table;
|
||||||
attributeNodes = {
|
attributeNodes = {
|
||||||
@NamedAttributeNode(value = "role",
|
@NamedAttributeNode(value = "role",
|
||||||
subgraph = "permissions")
|
subgraph = "permissions")
|
||||||
})
|
}),
|
||||||
,
|
|
||||||
@NamedSubgraph(
|
@NamedSubgraph(
|
||||||
name = "permissions",
|
name = "permissions",
|
||||||
attributeNodes = {
|
attributeNodes = {
|
||||||
|
|
@ -177,4 +183,4 @@ public class Group extends Party implements Serializable, Exportable {
|
||||||
return super.hashCode();
|
return super.hashCode();
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -26,6 +26,7 @@ import javax.persistence.TypedQuery;
|
||||||
import javax.transaction.Transactional;
|
import javax.transaction.Transactional;
|
||||||
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Objects;
|
||||||
import java.util.Optional;
|
import java.util.Optional;
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
|
|
||||||
|
|
@ -62,11 +63,11 @@ public class GroupRepository extends AbstractEntityRepository<Long, Group> {
|
||||||
|
|
||||||
return entity.getPartyId() == 0;
|
return entity.getPartyId() == 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Optional<Group> findByUuid(final String uuid) {
|
public Optional<Group> findByUuid(final String uuid) {
|
||||||
|
|
||||||
final TypedQuery<Group> query = getEntityManager()
|
final TypedQuery<Group> query = getEntityManager()
|
||||||
.createNamedQuery("Group.findByUuid", Group.class);
|
.createNamedQuery("Group.findByUuid", Group.class);
|
||||||
query.setParameter("uuid", uuid);
|
query.setParameter("uuid", uuid);
|
||||||
final List<Group> result = query.getResultList();
|
final List<Group> result = query.getResultList();
|
||||||
if (result.isEmpty()) {
|
if (result.isEmpty()) {
|
||||||
|
|
@ -107,6 +108,38 @@ public class GroupRepository extends AbstractEntityRepository<Long, Group> {
|
||||||
return query.getResultList();
|
return query.getResultList();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public List<GroupMembership> findGroupMemberships(
|
||||||
|
final Group group,
|
||||||
|
final int limit,
|
||||||
|
final int offset
|
||||||
|
) {
|
||||||
|
return getEntityManager()
|
||||||
|
.createNamedQuery("Group.findMemberships", GroupMembership.class)
|
||||||
|
.setParameter(
|
||||||
|
"group",
|
||||||
|
Objects.requireNonNull(
|
||||||
|
group,
|
||||||
|
"Can't retrieve menberships for group null."
|
||||||
|
)
|
||||||
|
)
|
||||||
|
.setMaxResults(limit)
|
||||||
|
.setFirstResult(offset)
|
||||||
|
.getResultList();
|
||||||
|
}
|
||||||
|
|
||||||
|
public long countGroupMemberships(final Group group) {
|
||||||
|
return getEntityManager()
|
||||||
|
.createNamedQuery("Group.countMemberships", Long.class)
|
||||||
|
.setParameter(
|
||||||
|
"group",
|
||||||
|
Objects.requireNonNull(
|
||||||
|
group,
|
||||||
|
"Can't count menberships for group null."
|
||||||
|
)
|
||||||
|
)
|
||||||
|
.getSingleResult();
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Tries to find a group which name contains a provided token.
|
* Tries to find a group which name contains a provided token.
|
||||||
*
|
*
|
||||||
|
|
@ -134,10 +167,10 @@ public class GroupRepository extends AbstractEntityRepository<Long, Group> {
|
||||||
public void save(final Group group) {
|
public void save(final Group group) {
|
||||||
super.save(group);
|
super.save(group);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void initNewEntity(final Group group) {
|
public void initNewEntity(final Group group) {
|
||||||
|
|
||||||
group.setUuid(UUID.randomUUID().toString());
|
group.setUuid(UUID.randomUUID().toString());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -70,44 +70,65 @@ import javax.persistence.TemporalType;
|
||||||
@Entity
|
@Entity
|
||||||
@Table(name = "PERMISSIONS", schema = DB_SCHEMA)
|
@Table(name = "PERMISSIONS", schema = DB_SCHEMA)
|
||||||
@NamedQueries({
|
@NamedQueries({
|
||||||
@NamedQuery(name = "Permission.findByUuid",
|
@NamedQuery(
|
||||||
query = "SELECT p FROM Permission p WHERE p.uuid = :uuid"),
|
name = "Permission.findByUuid",
|
||||||
@NamedQuery(name = "Permission.findByCustomPermId",
|
query = "SELECT p FROM Permission p WHERE p.uuid = :uuid"
|
||||||
query = "SELECT p FROM Permission p "
|
),
|
||||||
+ "WHERE p.grantedPrivilege = :privilege "
|
@NamedQuery(
|
||||||
+ "AND p.grantee = :grantee "
|
name = "Permission.findByCustomPermId",
|
||||||
+ "AND p.object = :object"),
|
query = "SELECT p FROM Permission p "
|
||||||
@NamedQuery(name = "Permission.existsForPrivilegeRoleObject",
|
+ "WHERE p.grantedPrivilege = :privilege "
|
||||||
query = "SELECT COUNT(p) FROM Permission p "
|
+ "AND p.grantee = :grantee "
|
||||||
+ "WHERE p.grantedPrivilege = :privilege "
|
+ "AND p.object = :object"
|
||||||
+ "AND p.grantee = :grantee "
|
),
|
||||||
+ "AND p.object = :object"),
|
@NamedQuery(
|
||||||
@NamedQuery(name = "Permission.existsDirectForPrivilegeRoleObject",
|
name = "Permission.existsForPrivilegeRoleObject",
|
||||||
query = "SELECT COUNT(p) FROM Permission p "
|
query = "SELECT COUNT(p) FROM Permission p "
|
||||||
+ "WHERE p.grantedPrivilege = :privilege "
|
+ "WHERE p.grantedPrivilege = :privilege "
|
||||||
+ "AND p.grantee = :grantee "
|
+ "AND p.grantee = :grantee "
|
||||||
+ "AND p.object = :object "
|
+ "AND p.object = :object"
|
||||||
+ "AND p.inherited = false"),
|
),
|
||||||
@NamedQuery(name = "Permission.existsInheritedForPrivilegeRoleObject",
|
@NamedQuery(
|
||||||
query = "SELECT COUNT(p) FROM Permission p "
|
name = "Permission.existsDirectForPrivilegeRoleObject",
|
||||||
+ "WHERE p.grantedPrivilege = :privilege "
|
query = "SELECT COUNT(p) FROM Permission p "
|
||||||
+ "AND p.grantee = :grantee "
|
+ "WHERE p.grantedPrivilege = :privilege "
|
||||||
+ "AND p.object = :object "
|
+ "AND p.grantee = :grantee "
|
||||||
+ "AND p.inherited = true"),
|
+ "AND p.object = :object "
|
||||||
@NamedQuery(name = "Permission.existsForPrivilegeAndRole",
|
+ "AND p.inherited = false"
|
||||||
query = "SELECT COUNT(p) FROM Permission p "
|
),
|
||||||
+ "WHERE p.grantedPrivilege = :privilege "
|
@NamedQuery(
|
||||||
+ "AND p.grantee = :grantee "
|
name = "Permission.existsInheritedForPrivilegeRoleObject",
|
||||||
+ "AND p.object IS NULL"),
|
query = "SELECT COUNT(p) FROM Permission p "
|
||||||
@NamedQuery(name = "Permission.findPermissionsForRole",
|
+ "WHERE p.grantedPrivilege = :privilege "
|
||||||
query = "SELECT p FROM Permission p "
|
+ "AND p.grantee = :grantee "
|
||||||
+ "WHERE p.grantee = :grantee"),
|
+ "AND p.object = :object "
|
||||||
@NamedQuery(name = "Permission.findPermissionsForCcmObject",
|
+ "AND p.inherited = true"
|
||||||
query = "SELECT p FROM Permission p "
|
),
|
||||||
+ "WHERE p.object = :object"),
|
@NamedQuery(
|
||||||
@NamedQuery(name = "Permission.findPermissionsForRoleAndObject",
|
name = "Permission.existsForPrivilegeAndRole",
|
||||||
query = "SELECT p FROM Permission p "
|
query = "SELECT COUNT(p) FROM Permission p "
|
||||||
+ "WHERE p.object = :object and p.grantee = :grantee")
|
+ "WHERE p.grantedPrivilege = :privilege "
|
||||||
|
+ "AND p.grantee = :grantee "
|
||||||
|
+ "AND p.object IS NULL"
|
||||||
|
),
|
||||||
|
@NamedQuery(
|
||||||
|
name = "Permission.findPermissionsForRole",
|
||||||
|
query = "SELECT p FROM Permission p WHERE p.grantee = :grantee"
|
||||||
|
),
|
||||||
|
@NamedQuery(
|
||||||
|
name = "Permission.countPermissionsForRole",
|
||||||
|
query = "SELECT COUNT(p) FROM Permission p WHERE p.grantee = :grantee"
|
||||||
|
),
|
||||||
|
@NamedQuery(
|
||||||
|
name = "Permission.findPermissionsForCcmObject",
|
||||||
|
query = "SELECT p FROM Permission p "
|
||||||
|
+ "WHERE p.object = :object"
|
||||||
|
),
|
||||||
|
@NamedQuery(
|
||||||
|
name = "Permission.findPermissionsForRoleAndObject",
|
||||||
|
query = "SELECT p FROM Permission p "
|
||||||
|
+ "WHERE p.object = :object and p.grantee = :grantee"
|
||||||
|
)
|
||||||
|
|
||||||
})
|
})
|
||||||
@XmlRootElement(name = "permission", namespace = CORE_XML_NS)
|
@XmlRootElement(name = "permission", namespace = CORE_XML_NS)
|
||||||
|
|
@ -408,7 +429,7 @@ public class Permission implements Serializable, Exportable {
|
||||||
public JsonObject toJson() {
|
public JsonObject toJson() {
|
||||||
return buildJson().build();
|
return buildJson().build();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String toString() {
|
public String toString() {
|
||||||
return String.format("%s{ "
|
return String.format("%s{ "
|
||||||
|
|
|
||||||
|
|
@ -21,6 +21,9 @@ package org.libreccm.security;
|
||||||
import org.libreccm.core.AbstractEntityRepository;
|
import org.libreccm.core.AbstractEntityRepository;
|
||||||
import org.libreccm.core.CcmObject;
|
import org.libreccm.core.CcmObject;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Objects;
|
||||||
|
|
||||||
import javax.enterprise.context.RequestScoped;
|
import javax.enterprise.context.RequestScoped;
|
||||||
import javax.persistence.NoResultException;
|
import javax.persistence.NoResultException;
|
||||||
import javax.persistence.TypedQuery;
|
import javax.persistence.TypedQuery;
|
||||||
|
|
@ -28,6 +31,8 @@ import javax.persistence.TypedQuery;
|
||||||
import java.util.Optional;
|
import java.util.Optional;
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
|
|
||||||
|
import javax.transaction.Transactional;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A repository class for {@link Permission}.
|
* A repository class for {@link Permission}.
|
||||||
*
|
*
|
||||||
|
|
@ -55,11 +60,13 @@ public class PermissionRepository
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
public String getIdAttributeName() {
|
public String getIdAttributeName() {
|
||||||
return "permissionId";
|
return "permissionId";
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
public Long getIdOfEntity(final Permission entity) {
|
public Long getIdOfEntity(final Permission entity) {
|
||||||
return entity.getPermissionId();
|
return entity.getPermissionId();
|
||||||
}
|
}
|
||||||
|
|
@ -73,6 +80,7 @@ public class PermissionRepository
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
public void initNewEntity(final Permission permission) {
|
public void initNewEntity(final Permission permission) {
|
||||||
|
|
||||||
permission.setUuid(UUID.randomUUID().toString());
|
permission.setUuid(UUID.randomUUID().toString());
|
||||||
|
|
@ -97,6 +105,7 @@ public class PermissionRepository
|
||||||
*
|
*
|
||||||
* @return An optional either with the found item or empty
|
* @return An optional either with the found item or empty
|
||||||
*/
|
*/
|
||||||
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
public Optional<Permission> findByCustomPermId(final String privilege,
|
public Optional<Permission> findByCustomPermId(final String privilege,
|
||||||
final Role grantee,
|
final Role grantee,
|
||||||
final Object object) {
|
final Object object) {
|
||||||
|
|
@ -116,6 +125,38 @@ public class PermissionRepository
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
|
public List<Permission> findPermissionsForRole(
|
||||||
|
final Role role, final int limit, final int offset
|
||||||
|
) {
|
||||||
|
return getEntityManager()
|
||||||
|
.createNamedQuery(
|
||||||
|
"Permission.findPermissionsForRole", Permission.class)
|
||||||
|
.setParameter(
|
||||||
|
"grantee",
|
||||||
|
Objects.requireNonNull(
|
||||||
|
role,
|
||||||
|
"Can't retrieve permissions for role null"
|
||||||
|
)
|
||||||
|
)
|
||||||
|
.setMaxResults(limit)
|
||||||
|
.setFirstResult(offset)
|
||||||
|
.getResultList();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
|
public long countPermissionsForRole(final Role role) {
|
||||||
|
return getEntityManager()
|
||||||
|
.createNamedQuery("Permission.countPermissionsForRole", Long.class)
|
||||||
|
.setParameter(
|
||||||
|
"grantee",
|
||||||
|
Objects.requireNonNull(
|
||||||
|
role,
|
||||||
|
"Can't count permissions for role null."
|
||||||
|
)
|
||||||
|
)
|
||||||
|
.getSingleResult();
|
||||||
|
}
|
||||||
/**
|
/**
|
||||||
* Checks if a not inherited permission granting the provided
|
* Checks if a not inherited permission granting the provided
|
||||||
* {@code privilege} on the provided {@code object} to the provided
|
* {@code privilege} on the provided {@code object} to the provided
|
||||||
|
|
@ -128,6 +169,8 @@ public class PermissionRepository
|
||||||
* @return {@code true} if there is a matching permission, {@code false} if
|
* @return {@code true} if there is a matching permission, {@code false} if
|
||||||
* not.
|
* not.
|
||||||
*/
|
*/
|
||||||
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
|
|
||||||
public boolean existsPermission(final String privilege,
|
public boolean existsPermission(final String privilege,
|
||||||
final Role grantee,
|
final Role grantee,
|
||||||
final CcmObject object) {
|
final CcmObject object) {
|
||||||
|
|
@ -141,10 +184,11 @@ public class PermissionRepository
|
||||||
|
|
||||||
return query.getSingleResult() > 0;
|
return query.getSingleResult() > 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean existsInheritedPermission(final String privilege,
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
final Role grantee,
|
public boolean existsInheritedPermission(final String privilege,
|
||||||
final CcmObject object) {
|
final Role grantee,
|
||||||
|
final CcmObject object) {
|
||||||
final TypedQuery<Long> query = getEntityManager().createNamedQuery(
|
final TypedQuery<Long> query = getEntityManager().createNamedQuery(
|
||||||
"Permission.existsInheritedForPrivilegeRoleObject", Long.class);
|
"Permission.existsInheritedForPrivilegeRoleObject", Long.class);
|
||||||
query.setParameter(QUERY_PARAM_PRIVILEGE, privilege);
|
query.setParameter(QUERY_PARAM_PRIVILEGE, privilege);
|
||||||
|
|
@ -164,8 +208,9 @@ public class PermissionRepository
|
||||||
* @return {@code true} if there is a matching permission, {@code false} if
|
* @return {@code true} if there is a matching permission, {@code false} if
|
||||||
* not.
|
* not.
|
||||||
*/
|
*/
|
||||||
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
public boolean existsPermission(final String privilege,
|
public boolean existsPermission(final String privilege,
|
||||||
final Role grantee) {
|
final Role grantee) {
|
||||||
final TypedQuery<Long> query = getEntityManager().createNamedQuery(
|
final TypedQuery<Long> query = getEntityManager().createNamedQuery(
|
||||||
"Permission.existsForPrivilegeAndRole", Long.class);
|
"Permission.existsForPrivilegeAndRole", Long.class);
|
||||||
query.setParameter(QUERY_PARAM_PRIVILEGE, privilege);
|
query.setParameter(QUERY_PARAM_PRIVILEGE, privilege);
|
||||||
|
|
|
||||||
|
|
@ -57,11 +57,31 @@ import javax.persistence.Table;
|
||||||
@Entity
|
@Entity
|
||||||
@Table(name = "ROLE_MEMBERSHIPS", schema = DB_SCHEMA)
|
@Table(name = "ROLE_MEMBERSHIPS", schema = DB_SCHEMA)
|
||||||
@NamedQueries({
|
@NamedQueries({
|
||||||
@NamedQuery(name = "RoleMembership.findByUuid",
|
@NamedQuery(
|
||||||
query = "SELECT m FROM RoleMembership m WHERE m.uuid = :uuid"),
|
name = "RoleMembership.findByUuid",
|
||||||
@NamedQuery(name = "RoleMembership.findByRoleAndMember",
|
query = "SELECT m FROM RoleMembership m WHERE m.uuid = :uuid"
|
||||||
query = "SELECT m FROM RoleMembership m "
|
),
|
||||||
+ "WHERE m.member = :member AND m.role = :role")
|
@NamedQuery(
|
||||||
|
name = "RoleMembership.findByRoleAndMember",
|
||||||
|
query = "SELECT m FROM RoleMembership m "
|
||||||
|
+ "WHERE m.member = :member AND m.role = :role"
|
||||||
|
),
|
||||||
|
@NamedQuery(
|
||||||
|
name = "RoleMembership.countByParty",
|
||||||
|
query = "SELECT COUNT(m) FROM RoleMembership m WHERE m.member = :party"
|
||||||
|
),
|
||||||
|
@NamedQuery(
|
||||||
|
name = "RoleMembership.countByRole",
|
||||||
|
query = "SELECT COUNT(m) FROM RoleMembership m WHERE m.role = :role"
|
||||||
|
),
|
||||||
|
@NamedQuery(
|
||||||
|
name = "RoleMembership.findByParty",
|
||||||
|
query = "SELECT m FROM RoleMembership m WHERE m.member = :party"
|
||||||
|
),
|
||||||
|
@NamedQuery(
|
||||||
|
name = "RoleMembership.findByRole",
|
||||||
|
query = "SELECT m FROM RoleMembership m WHERE m.role = :role"
|
||||||
|
)
|
||||||
})
|
})
|
||||||
@XmlRootElement(name = "role-membership", namespace = CORE_XML_NS)
|
@XmlRootElement(name = "role-membership", namespace = CORE_XML_NS)
|
||||||
@JsonIdentityInfo(generator = ObjectIdGenerators.PropertyGenerator.class,
|
@JsonIdentityInfo(generator = ObjectIdGenerators.PropertyGenerator.class,
|
||||||
|
|
@ -161,7 +181,7 @@ public class RoleMembership implements Serializable, Exportable {
|
||||||
public boolean canEqual(final Object obj) {
|
public boolean canEqual(final Object obj) {
|
||||||
return obj instanceof RoleMembership;
|
return obj instanceof RoleMembership;
|
||||||
}
|
}
|
||||||
|
|
||||||
public JsonObject toJson() {
|
public JsonObject toJson() {
|
||||||
return buildJson().build();
|
return buildJson().build();
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -55,7 +55,7 @@ public class RoleRepository extends AbstractEntityRepository<Long, Role> {
|
||||||
public Long getIdOfEntity(final Role entity) {
|
public Long getIdOfEntity(final Role entity) {
|
||||||
return entity.getRoleId();
|
return entity.getRoleId();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean isNew(final Role entity) {
|
public boolean isNew(final Role entity) {
|
||||||
if (entity == null) {
|
if (entity == null) {
|
||||||
|
|
@ -63,12 +63,12 @@ public class RoleRepository extends AbstractEntityRepository<Long, Role> {
|
||||||
}
|
}
|
||||||
return entity.getRoleId() == 0;
|
return entity.getRoleId() == 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void initNewEntity(final Role role) {
|
public void initNewEntity(final Role role) {
|
||||||
|
|
||||||
role.setUuid(UUID.randomUUID().toString());
|
role.setUuid(UUID.randomUUID().toString());
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public long count() {
|
public long count() {
|
||||||
|
|
@ -76,13 +76,13 @@ public class RoleRepository extends AbstractEntityRepository<Long, Role> {
|
||||||
"Role.count", Long.class);
|
"Role.count", Long.class);
|
||||||
return query.getSingleResult();
|
return query.getSingleResult();
|
||||||
}
|
}
|
||||||
|
|
||||||
public Optional<Role> findByUuid(final String uuid) {
|
public Optional<Role> findByUuid(final String uuid) {
|
||||||
|
|
||||||
final TypedQuery<Role> query = getEntityManager()
|
final TypedQuery<Role> query = getEntityManager()
|
||||||
.createNamedQuery("Role.findByUuid", Role.class);
|
.createNamedQuery("Role.findByUuid", Role.class);
|
||||||
query.setParameter("uuid", uuid);
|
query.setParameter("uuid", uuid);
|
||||||
|
|
||||||
return getSingleResult(query);
|
return getSingleResult(query);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -150,6 +150,24 @@ public class RoleRepository extends AbstractEntityRepository<Long, Role> {
|
||||||
return query.getResultList();
|
return query.getResultList();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public long countMembershipsByRole(final Role role) {
|
||||||
|
return getEntityManager()
|
||||||
|
.createNamedQuery("RoleMembership.countByRole", Long.class)
|
||||||
|
.setParameter("role", role)
|
||||||
|
.getSingleResult();
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<RoleMembership> findMembershipsByRole(
|
||||||
|
final Role role, final int limit, final int offset
|
||||||
|
) {
|
||||||
|
return getEntityManager()
|
||||||
|
.createNamedQuery("RoleMembership.findByRole", RoleMembership.class)
|
||||||
|
.setParameter("role", role)
|
||||||
|
.setMaxResults(limit)
|
||||||
|
.setFirstResult(offset)
|
||||||
|
.getResultList();
|
||||||
|
}
|
||||||
|
|
||||||
public List<Role> searchByName(final String name) {
|
public List<Role> searchByName(final String name) {
|
||||||
final TypedQuery<Role> query = getEntityManager().createNamedQuery(
|
final TypedQuery<Role> query = getEntityManager().createNamedQuery(
|
||||||
"Role.searchByName", Role.class);
|
"Role.searchByName", Role.class);
|
||||||
|
|
|
||||||
|
|
@ -116,7 +116,7 @@ import javax.xml.bind.annotation.XmlTransient;
|
||||||
@NamedQuery(name = "User.findByGroup",
|
@NamedQuery(name = "User.findByGroup",
|
||||||
query = "SELECT u FROM User u "
|
query = "SELECT u FROM User u "
|
||||||
+ "JOIN u.groupMemberships m "
|
+ "JOIN u.groupMemberships m "
|
||||||
+ "WHERE m.group = :group")
|
+ "WHERE m.group = :group"),
|
||||||
})
|
})
|
||||||
@NamedEntityGraphs({
|
@NamedEntityGraphs({
|
||||||
@NamedEntityGraph(
|
@NamedEntityGraph(
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue