mirror of https://github.com/sismics/docs.git
448 lines
16 KiB
Java
448 lines
16 KiB
Java
package com.sismics.docs.rest.resource;
|
|
|
|
import com.google.common.base.Strings;
|
|
import com.google.common.collect.Sets;
|
|
import com.sismics.docs.core.constant.AclTargetType;
|
|
import com.sismics.docs.core.dao.GroupDao;
|
|
import com.sismics.docs.core.dao.RoleBaseFunctionDao;
|
|
import com.sismics.docs.core.dao.UserDao;
|
|
import com.sismics.docs.core.dao.criteria.GroupCriteria;
|
|
import com.sismics.docs.core.dao.criteria.UserCriteria;
|
|
import com.sismics.docs.core.dao.dto.GroupDto;
|
|
import com.sismics.docs.core.dao.dto.UserDto;
|
|
import com.sismics.docs.core.model.jpa.Group;
|
|
import com.sismics.docs.core.model.jpa.User;
|
|
import com.sismics.docs.core.model.jpa.UserGroup;
|
|
import com.sismics.docs.core.util.RoutingUtil;
|
|
import com.sismics.docs.core.util.jpa.SortCriteria;
|
|
import com.sismics.docs.rest.constant.BaseFunction;
|
|
import com.sismics.rest.exception.ClientException;
|
|
import com.sismics.rest.exception.ForbiddenClientException;
|
|
import com.sismics.rest.util.ValidationUtil;
|
|
import com.sismics.util.JsonUtil;
|
|
|
|
import jakarta.json.Json;
|
|
import jakarta.json.JsonArrayBuilder;
|
|
import jakarta.json.JsonObjectBuilder;
|
|
import jakarta.ws.rs.*;
|
|
import jakarta.ws.rs.core.Response;
|
|
import java.text.MessageFormat;
|
|
import java.util.List;
|
|
import java.util.Set;
|
|
|
|
/**
|
|
* Group REST resources.
|
|
*
|
|
* @author bgamard
|
|
*/
|
|
@Path("/group")
|
|
public class GroupResource extends BaseResource {
|
|
/**
|
|
* Add a group.
|
|
*
|
|
* @api {put} /group Add a group
|
|
* @apiName PutGroup
|
|
* @apiGroup Group
|
|
* @apiParam {String} name Group name
|
|
* @apiParam {String} [parent] Parent group name
|
|
* @apiSuccess {String} status Status OK
|
|
* @apiError (client) ForbiddenError Access denied
|
|
* @apiError (client) ValidationError Validation error
|
|
* @apiError (client) GroupAlreadyExists This group already exists
|
|
* @apiError (client) ParentGroupNotFound Parent group not found
|
|
* @apiPermission admin
|
|
* @apiVersion 1.5.0
|
|
*
|
|
* @return Response
|
|
*/
|
|
@PUT
|
|
public Response add(@FormParam("parent") String parentName,
|
|
@FormParam("name") String name) {
|
|
if (!authenticate()) {
|
|
throw new ForbiddenClientException();
|
|
}
|
|
checkBaseFunction(BaseFunction.ADMIN);
|
|
|
|
// Validate input
|
|
name = ValidationUtil.validateLength(name, "name", 1, 50, false);
|
|
ValidationUtil.validateAlphanumeric(name, "name");
|
|
|
|
// Avoid duplicates
|
|
GroupDao groupDao = new GroupDao();
|
|
Group existingGroup = groupDao.getActiveByName(name);
|
|
if (existingGroup != null) {
|
|
throw new ClientException("GroupAlreadyExists", MessageFormat.format("This group already exists: {0}", name));
|
|
}
|
|
|
|
// Validate parent
|
|
String parentId = null;
|
|
if (!Strings.isNullOrEmpty(parentName)) {
|
|
Group parentGroup = groupDao.getActiveByName(parentName);
|
|
if (parentGroup == null) {
|
|
throw new ClientException("ParentGroupNotFound", MessageFormat.format("This group does not exists: {0}", parentName));
|
|
}
|
|
parentId = parentGroup.getId();
|
|
}
|
|
|
|
// Create the group
|
|
groupDao.create(new Group()
|
|
.setName(name)
|
|
.setParentId(parentId), principal.getId());
|
|
|
|
// Always return OK
|
|
JsonObjectBuilder response = Json.createObjectBuilder()
|
|
.add("status", "ok");
|
|
return Response.ok().entity(response.build()).build();
|
|
}
|
|
|
|
/**
|
|
* Update a group.
|
|
*
|
|
* @api {post} /group/:name Update a group
|
|
* @apiName PostGroup
|
|
* @apiGroup Group
|
|
* @apiParam {String} name Group name
|
|
* @apiParam {String} [parent] Parent group name
|
|
* @apiSuccess {String} status Status OK
|
|
* @apiError (client) ForbiddenError Access denied
|
|
* @apiError (client) ValidationError Validation error
|
|
* @apiError (client) GroupAlreadyExists This group already exists
|
|
* @apiError (client) ParentGroupNotFound Parent group not found
|
|
* @apiError (client) NotFound Group not found
|
|
* @apiPermission admin
|
|
* @apiVersion 1.5.0
|
|
*
|
|
* @return Response
|
|
*/
|
|
@POST
|
|
@Path("{groupName: [a-zA-Z0-9_]+}")
|
|
public Response update(@PathParam("groupName") String groupName,
|
|
@FormParam("parent") String parentName,
|
|
@FormParam("name") String name) {
|
|
if (!authenticate()) {
|
|
throw new ForbiddenClientException();
|
|
}
|
|
checkBaseFunction(BaseFunction.ADMIN);
|
|
|
|
// Validate input
|
|
name = ValidationUtil.validateLength(name, "name", 1, 50, false);
|
|
ValidationUtil.validateAlphanumeric(name, "name");
|
|
|
|
// Get the group (by its old name)
|
|
GroupDao groupDao = new GroupDao();
|
|
Group group = groupDao.getActiveByName(groupName);
|
|
if (group == null) {
|
|
throw new NotFoundException();
|
|
}
|
|
|
|
// Avoid duplicates
|
|
Group existingGroup = groupDao.getActiveByName(name);
|
|
if (existingGroup != null && !existingGroup.getId().equals(group.getId())) {
|
|
throw new ClientException("GroupAlreadyExists", MessageFormat.format("This group already exists: {0}", name));
|
|
}
|
|
|
|
// Validate parent
|
|
String parentId = null;
|
|
if (!Strings.isNullOrEmpty(parentName)) {
|
|
Group parentGroup = groupDao.getActiveByName(parentName);
|
|
if (parentGroup == null) {
|
|
throw new ClientException("ParentGroupNotFound", MessageFormat.format("This group does not exists: {0}", parentName));
|
|
}
|
|
parentId = parentGroup.getId();
|
|
}
|
|
|
|
// Check that this group is not used in any workflow in case of renaming
|
|
if (!name.equals(groupName)) {
|
|
String routeModelName = RoutingUtil.findRouteModelNameByTargetName(AclTargetType.GROUP, groupName);
|
|
if (routeModelName != null) {
|
|
throw new ClientException("GroupUsedInRouteModel", routeModelName);
|
|
}
|
|
}
|
|
|
|
// Update the group
|
|
groupDao.update(group.setName(name)
|
|
.setParentId(parentId), principal.getId());
|
|
|
|
// Always return OK
|
|
JsonObjectBuilder response = Json.createObjectBuilder()
|
|
.add("status", "ok");
|
|
return Response.ok().entity(response.build()).build();
|
|
}
|
|
|
|
/**
|
|
* Delete a group.
|
|
*
|
|
* @api {delete} /group/:name Delete a group
|
|
* @apiName DeleteGroup
|
|
* @apiGroup Group
|
|
* @apiParam {String} name Group name
|
|
* @apiSuccess {String} status Status OK
|
|
* @apiError (client) ForbiddenError Access denied
|
|
* @apiError (client) NotFound Group not found
|
|
* @apiError (client) GroupUsedInRouteModel The group is used in a route model
|
|
* @apiPermission admin
|
|
* @apiVersion 1.5.0
|
|
*
|
|
* @return Response
|
|
*/
|
|
@DELETE
|
|
@Path("{groupName: [a-zA-Z0-9_]+}")
|
|
public Response delete(@PathParam("groupName") String groupName) {
|
|
if (!authenticate()) {
|
|
throw new ForbiddenClientException();
|
|
}
|
|
checkBaseFunction(BaseFunction.ADMIN);
|
|
|
|
// Get the group
|
|
GroupDao groupDao = new GroupDao();
|
|
Group group = groupDao.getActiveByName(groupName);
|
|
if (group == null) {
|
|
throw new NotFoundException();
|
|
}
|
|
|
|
// Ensure that the admin group is not deleted
|
|
if (group.getRoleId() != null) {
|
|
RoleBaseFunctionDao roleBaseFunctionDao = new RoleBaseFunctionDao();
|
|
Set<String> baseFunctionSet = roleBaseFunctionDao.findByRoleId(Sets.newHashSet(group.getRoleId()));
|
|
if (baseFunctionSet.contains(BaseFunction.ADMIN.name())) {
|
|
throw new ClientException("ForbiddenError", "The administrators group cannot be deleted");
|
|
}
|
|
}
|
|
|
|
// Check that this group is not used in any workflow
|
|
String routeModelName = RoutingUtil.findRouteModelNameByTargetName(AclTargetType.GROUP, groupName);
|
|
if (routeModelName != null) {
|
|
throw new ClientException("GroupUsedInRouteModel", routeModelName);
|
|
}
|
|
|
|
// Delete the group
|
|
groupDao.delete(group.getId(), principal.getId());
|
|
|
|
// Always return OK
|
|
JsonObjectBuilder response = Json.createObjectBuilder()
|
|
.add("status", "ok");
|
|
return Response.ok().entity(response.build()).build();
|
|
}
|
|
|
|
/**
|
|
* Add a user to a group.
|
|
*
|
|
* @api {put} /group/:name Add a user to a group
|
|
* @apiName PutGroupMember
|
|
* @apiGroup Group
|
|
* @apiParam {String} name Group name
|
|
* @apiParam {String} username Username
|
|
* @apiSuccess {String} status Status OK
|
|
* @apiError (client) ForbiddenError Access denied
|
|
* @apiError (client) ValidationError Validation error
|
|
* @apiError (client) NotFound Group or user not found
|
|
* @apiPermission admin
|
|
* @apiVersion 1.5.0
|
|
*
|
|
* @param groupName Group name
|
|
* @param username Username
|
|
* @return Response
|
|
*/
|
|
@PUT
|
|
@Path("{groupName: [a-zA-Z0-9_]+}")
|
|
public Response addMember(@PathParam("groupName") String groupName,
|
|
@FormParam("username") String username) {
|
|
if (!authenticate()) {
|
|
throw new ForbiddenClientException();
|
|
}
|
|
checkBaseFunction(BaseFunction.ADMIN);
|
|
|
|
// Validate input
|
|
groupName = ValidationUtil.validateLength(groupName, "name", 1, 50, false);
|
|
username = ValidationUtil.validateLength(username, "username", 1, 50, false);
|
|
|
|
// Get the group
|
|
GroupDao groupDao = new GroupDao();
|
|
Group group = groupDao.getActiveByName(groupName);
|
|
if (group == null) {
|
|
throw new NotFoundException();
|
|
}
|
|
|
|
// Get the user
|
|
UserDao userDao = new UserDao();
|
|
User user = userDao.getActiveByUsername(username);
|
|
if (user == null) {
|
|
throw new NotFoundException();
|
|
}
|
|
|
|
// Avoid duplicates
|
|
List<GroupDto> groupDtoList = groupDao.findByCriteria(new GroupCriteria().setUserId(user.getId()), null);
|
|
boolean found = false;
|
|
for (GroupDto groupDto : groupDtoList) {
|
|
if (groupDto.getId().equals(group.getId())) {
|
|
found = true;
|
|
}
|
|
}
|
|
|
|
if (!found) {
|
|
// Add the membership
|
|
UserGroup userGroup = new UserGroup();
|
|
userGroup.setGroupId(group.getId());
|
|
userGroup.setUserId(user.getId());
|
|
groupDao.addMember(userGroup);
|
|
}
|
|
|
|
// Always return OK
|
|
JsonObjectBuilder response = Json.createObjectBuilder()
|
|
.add("status", "ok");
|
|
return Response.ok().entity(response.build()).build();
|
|
}
|
|
|
|
/**
|
|
* Remove an user from a group.
|
|
*
|
|
* @api {delete} /group/:name/:username Remove a user from a group
|
|
* @apiName DeleteGroupMember
|
|
* @apiGroup Group
|
|
* @apiParam {String} name Group name
|
|
* @apiParam {String} username Username
|
|
* @apiSuccess {String} status Status OK
|
|
* @apiError (client) ForbiddenError Access denied
|
|
* @apiError (client) ValidationError Validation error
|
|
* @apiError (client) NotFound Group or user not found
|
|
* @apiPermission admin
|
|
* @apiVersion 1.5.0
|
|
*
|
|
* @param groupName Group name
|
|
* @param username Username
|
|
* @return Response
|
|
*/
|
|
@DELETE
|
|
@Path("{groupName: [a-zA-Z0-9_]+}/{username: [a-zA-Z0-9_@.-]+}")
|
|
public Response removeMember(@PathParam("groupName") String groupName,
|
|
@PathParam("username") String username) {
|
|
if (!authenticate()) {
|
|
throw new ForbiddenClientException();
|
|
}
|
|
checkBaseFunction(BaseFunction.ADMIN);
|
|
|
|
// Validate input
|
|
groupName = ValidationUtil.validateLength(groupName, "name", 1, 50, false);
|
|
username = ValidationUtil.validateLength(username, "username", 1, 50, false);
|
|
|
|
// Get the group
|
|
GroupDao groupDao = new GroupDao();
|
|
Group group = groupDao.getActiveByName(groupName);
|
|
if (group == null) {
|
|
throw new NotFoundException();
|
|
}
|
|
|
|
// Get the user
|
|
UserDao userDao = new UserDao();
|
|
User user = userDao.getActiveByUsername(username);
|
|
if (user == null) {
|
|
throw new NotFoundException();
|
|
}
|
|
|
|
// Remove the membership
|
|
groupDao.removeMember(group.getId(), user.getId());
|
|
|
|
// Always return OK
|
|
JsonObjectBuilder response = Json.createObjectBuilder()
|
|
.add("status", "ok");
|
|
return Response.ok().entity(response.build()).build();
|
|
}
|
|
|
|
/**
|
|
* Returns all active groups.
|
|
*
|
|
* @api {get} /group Get groups
|
|
* @apiName GetGroupList
|
|
* @apiGroup Group
|
|
* @apiParam {Number} sort_column Column index to sort on
|
|
* @apiParam {Boolean} asc If true, sort in ascending order
|
|
* @apiSuccess {Object[]} groups List of groups
|
|
* @apiSuccess {String} groups.name Name
|
|
* @apiSuccess {String} groups.parent Parent name
|
|
* @apiError (client) ForbiddenError Access denied
|
|
* @apiPermission user
|
|
* @apiVersion 1.5.0
|
|
*
|
|
* @param sortColumn Sort index
|
|
* @param asc If true, ascending sorting, else descending
|
|
* @return Response
|
|
*/
|
|
@GET
|
|
public Response list(
|
|
@QueryParam("sort_column") Integer sortColumn,
|
|
@QueryParam("asc") Boolean asc) {
|
|
if (!authenticate()) {
|
|
throw new ForbiddenClientException();
|
|
}
|
|
|
|
JsonArrayBuilder groups = Json.createArrayBuilder();
|
|
SortCriteria sortCriteria = new SortCriteria(sortColumn, asc);
|
|
|
|
GroupDao groupDao = new GroupDao();
|
|
List<GroupDto> groupDtoList = groupDao.findByCriteria(new GroupCriteria(), sortCriteria);
|
|
for (GroupDto groupDto : groupDtoList) {
|
|
groups.add(Json.createObjectBuilder()
|
|
.add("name", groupDto.getName())
|
|
.add("parent", JsonUtil.nullable(groupDto.getParentName())));
|
|
}
|
|
|
|
JsonObjectBuilder response = Json.createObjectBuilder()
|
|
.add("groups", groups);
|
|
return Response.ok().entity(response.build()).build();
|
|
}
|
|
|
|
/**
|
|
* Get a group.
|
|
*
|
|
* @api {get} /group/:name Get a group
|
|
* @apiName GetGroup
|
|
* @apiGroup Group
|
|
* @apiParam {String} name Group name
|
|
* @apiSuccess {String} name Group name
|
|
* @apiSuccess {String} parent Parent name
|
|
* @apiSuccess {String[]} members List of members
|
|
* @apiError (client) ForbiddenError Access denied
|
|
* @apiError (client) NotFound Group not found
|
|
* @apiPermission user
|
|
* @apiVersion 1.5.0
|
|
*
|
|
* @param groupName Group name
|
|
* @return Response
|
|
*/
|
|
@GET
|
|
@Path("{groupName: [a-zA-Z0-9_]+}")
|
|
public Response get(@PathParam("groupName") String groupName) {
|
|
if (!authenticate()) {
|
|
throw new ForbiddenClientException();
|
|
}
|
|
|
|
// Get the group
|
|
GroupDao groupDao = new GroupDao();
|
|
Group group = groupDao.getActiveByName(groupName);
|
|
if (group == null) {
|
|
throw new NotFoundException();
|
|
}
|
|
|
|
// Build the response
|
|
JsonObjectBuilder response = Json.createObjectBuilder()
|
|
.add("name", group.getName());
|
|
|
|
// Get the parent
|
|
if (group.getParentId() != null) {
|
|
Group parentGroup = groupDao.getActiveById(group.getParentId());
|
|
response.add("parent", parentGroup.getName());
|
|
}
|
|
|
|
// Members
|
|
JsonArrayBuilder members = Json.createArrayBuilder();
|
|
UserDao userDao = new UserDao();
|
|
List<UserDto> userDtoList = userDao.findByCriteria(new UserCriteria().setGroupId(group.getId()), new SortCriteria(1, true));
|
|
for (UserDto userDto : userDtoList) {
|
|
members.add(userDto.getUsername());
|
|
}
|
|
response.add("members", members);
|
|
|
|
return Response.ok().entity(response.build()).build();
|
|
}
|
|
}
|