Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Cherry-pick-2.0.2][Feature][Dolphinscheduler-api] cherry-pick from dev to 2.0.2 #7373

Merged
merged 4 commits into from
Dec 13, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@

package org.apache.dolphinscheduler.api.controller;

import static org.apache.dolphinscheduler.api.enums.Status.QUERY_ACCESSTOKEN_BY_USER_ERROR;
import static org.apache.dolphinscheduler.api.enums.Status.CREATE_ACCESS_TOKEN_ERROR;
import static org.apache.dolphinscheduler.api.enums.Status.DELETE_ACCESS_TOKEN_ERROR;
import static org.apache.dolphinscheduler.api.enums.Status.GENERATE_TOKEN_ERROR;
Expand Down Expand Up @@ -140,6 +141,27 @@ public Result queryAccessTokenList(@ApiIgnore @RequestAttribute(value = Constant
return result;
}

/**
* query access token for specified user
*
* @param loginUser login user
* @param userId user id
* @return token list for specified user
*/
@ApiOperation(value = "queryAccessTokenByUser", notes = "QUERY_ACCESS_TOKEN_BY_USER_NOTES")
@ApiImplicitParams({
@ApiImplicitParam(name = "userId", value = "USER_ID", dataType = "Int")
})
@GetMapping(value = "/user/{userId}")
@ResponseStatus(HttpStatus.OK)
@ApiException(QUERY_ACCESSTOKEN_BY_USER_ERROR)
@AccessLogAnnotation(ignoreRequestArgs = "loginUser")
public Result queryAccessTokenByUser(@ApiIgnore @RequestAttribute(value = Constants.SESSION_USER) User loginUser,
@PathVariable("userId") Integer userId) {
Map<String, Object> result = this.accessTokenService.queryAccessTokenByUser(loginUser, userId);
return this.returnDataList(result);
}

/**
* delete access token by id
*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@

package org.apache.dolphinscheduler.api.controller;

import static org.apache.dolphinscheduler.api.enums.Status.QUERY_AUTHORIZED_USER;
import static org.apache.dolphinscheduler.api.enums.Status.CREATE_PROJECT_ERROR;
import static org.apache.dolphinscheduler.api.enums.Status.DELETE_PROJECT_ERROR;
import static org.apache.dolphinscheduler.api.enums.Status.LOGIN_USER_QUERY_PROJECT_LIST_PAGING_ERROR;
Expand Down Expand Up @@ -237,6 +238,27 @@ public Result queryAuthorizedProject(@ApiIgnore @RequestAttribute(value = Consta
return returnDataList(result);
}

/**
* query authorized user
*
* @param loginUser login user
* @param projectCode project code
* @return users who have permission for the specified project
*/
@ApiOperation(value = "queryAuthorizedUser", notes = "QUERY_AUTHORIZED_USER_NOTES")
@ApiImplicitParams({
@ApiImplicitParam(name = "projectCode", value = "PROJECT_CODE", dataType = "Long", example = "100")
})
@GetMapping(value = "/authed-user")
@ResponseStatus(HttpStatus.OK)
@ApiException(QUERY_AUTHORIZED_USER)
@AccessLogAnnotation(ignoreRequestArgs = "loginUser")
public Result queryAuthorizedUser(@ApiIgnore @RequestAttribute(value = Constants.SESSION_USER) User loginUser,
@RequestParam("projectCode") Long projectCode) {
Map<String, Object> result = this.projectService.queryAuthorizedUser(loginUser, projectCode);
return this.returnDataList(result);
}

/**
* query authorized and user created project
*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@

package org.apache.dolphinscheduler.api.controller;

import static org.apache.dolphinscheduler.api.enums.Status.REVOKE_PROJECT_ERROR;
import static org.apache.dolphinscheduler.api.enums.Status.AUTHORIZED_USER_ERROR;
import static org.apache.dolphinscheduler.api.enums.Status.CREATE_USER_ERROR;
import static org.apache.dolphinscheduler.api.enums.Status.DELETE_USER_BY_ID_ERROR;
Expand Down Expand Up @@ -234,6 +235,54 @@ public Result grantProject(@ApiIgnore @RequestAttribute(value = Constants.SESSIO
return returnDataList(result);
}

/**
* grant project by code
*
* @param loginUser login user
* @param userId user id
* @param projectCode project code
* @return grant result code
*/
@ApiOperation(value = "grantProjectByCode", notes = "GRANT_PROJECT_BY_CODE_NOTES")
@ApiImplicitParams({
@ApiImplicitParam(name = "userId", value = "USER_ID", required = true, dataType = "Int", example = "100"),
@ApiImplicitParam(name = "projectCode", value = "PROJECT_CODE", required = true, type = "Long")
})
@PostMapping(value = "/grant-project-by-code")
@ResponseStatus(HttpStatus.OK)
@ApiException(GRANT_PROJECT_ERROR)
@AccessLogAnnotation
public Result grantProjectByCode(@ApiIgnore @RequestAttribute(value = Constants.SESSION_USER) User loginUser,
@RequestParam(value = "userId") int userId,
@RequestParam(value = "projectCode") long projectCode) {
Map<String, Object> result = this.usersService.grantProjectByCode(loginUser, userId, projectCode);
return this.returnDataList(result);
}

/**
* revoke project
*
* @param loginUser login user
* @param userId user id
* @param projectCode project code
* @return revoke result code
*/
@ApiOperation(value = "revokeProject", notes = "REVOKE_PROJECT_NOTES")
@ApiImplicitParams({
@ApiImplicitParam(name = "userId", value = "USER_ID", required = true, dataType = "Int", example = "100"),
@ApiImplicitParam(name = "projectCode", value = "PROJECT_CODE", required = true, type = "Long", example = "100")
})
@PostMapping(value = "/revoke-project")
@ResponseStatus(HttpStatus.OK)
@ApiException(REVOKE_PROJECT_ERROR)
@AccessLogAnnotation
public Result revokeProject(@ApiIgnore @RequestAttribute(value = Constants.SESSION_USER) User loginUser,
@RequestParam(value = "userId") int userId,
@RequestParam(value = "projectCode") long projectCode) {
Map<String, Object> result = this.usersService.revokeProject(loginUser, userId, projectCode);
return returnDataList(result);
}

/**
* grant resource
*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -212,7 +212,8 @@ public enum Status {
TRANSFORM_PROJECT_OWNERSHIP(10179, "Please transform project ownership [{0}]", "请先转移项目所有权[{0}]"),
QUERY_ALERT_GROUP_ERROR(10180, "query alert group error", "查询告警组错误"),
CURRENT_LOGIN_USER_TENANT_NOT_EXIST(10181, "the tenant of the currently login user is not specified", "未指定当前登录用户的租户"),

REVOKE_PROJECT_ERROR(10182, "revoke project error", "撤销项目授权错误"),
QUERY_AUTHORIZED_USER(10183, "query authorized user error", "查询拥有项目权限的用户错误"),

UDF_FUNCTION_NOT_EXIST(20001, "UDF function not found", "UDF函数不存在"),
UDF_FUNCTION_EXISTS(20002, "UDF function already exists", "UDF函数已存在"),
Expand Down Expand Up @@ -304,6 +305,7 @@ public enum Status {
UPDATE_ACCESS_TOKEN_ERROR(70013, "update access token error", "更新访问token错误"),
DELETE_ACCESS_TOKEN_ERROR(70014, "delete access token error", "删除访问token错误"),
ACCESS_TOKEN_NOT_EXIST(70015, "access token not exist", "访问token不存在"),
QUERY_ACCESSTOKEN_BY_USER_ERROR(70016, "query access token by user error", "查询访问指定用户的token错误"),


COMMAND_STATE_COUNT_ERROR(80001, "task instance state count error", "查询各状态任务实例数错误"),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,15 @@ public interface AccessTokenService {
*/
Result queryAccessTokenList(User loginUser, String searchVal, Integer pageNo, Integer pageSize);

/**
* query access token for specified user
*
* @param loginUser login user
* @param userId user id
* @return token list for specified user
*/
Map<String, Object> queryAccessTokenByUser(User loginUser, Integer userId);

/**
* create token
*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -110,6 +110,15 @@ public interface ProjectService {
*/
Map<String, Object> queryAuthorizedProject(User loginUser, Integer userId);

/**
* query authorized user
*
* @param loginUser login user
* @param projectCode project code
* @return users who have permission for the specified project
*/
Map<String, Object> queryAuthorizedUser(User loginUser, Long projectCode);

/**
* query authorized project
*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -153,6 +153,25 @@ Map<String, Object> updateUser(User loginUser, int userId, String userName, Stri
Map<String, Object> grantProject(User loginUser, int userId, String projectIds);


/**
* grant project by code
*
* @param loginUser login user
* @param userId user id
* @param projectCode project code
* @return grant result code
*/
Map<String, Object> grantProjectByCode(User loginUser, int userId, long projectCode);

/**
* revoke the project permission for specified user.
* @param loginUser Login user
* @param userId User id
* @param projectCode Project Code
* @return
*/
Map<String, Object> revokeProject(User loginUser, int userId, long projectCode);

/**
* grant resource
*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@

import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.slf4j.Logger;
Expand Down Expand Up @@ -78,6 +79,30 @@ public Result queryAccessTokenList(User loginUser, String searchVal, Integer pag
return result;
}

/**
* query access token for specified user
*
* @param loginUser login user
* @param userId user id
* @return token list for specified user
*/
@Override
public Map<String, Object> queryAccessTokenByUser(User loginUser, Integer userId) {
Map<String, Object> result = new HashMap<>();
result.put(Constants.STATUS, false);

// only admin can operate
if (isNotAdmin(loginUser, result)) {
return result;
}

// query access token for specified user
List<AccessToken> accessTokenList = this.accessTokenMapper.queryAccessTokenByUser(userId);
result.put(Constants.DATA_LIST, accessTokenList);
this.putMsg(result, Status.SUCCESS);
return result;
}

/**
* create token
*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -389,6 +389,31 @@ public Map<String, Object> queryAuthorizedProject(User loginUser, Integer userId
return result;
}

/**
* query authorized user
*
* @param loginUser login user
* @param projectCode project code
* @return users who have permission for the specified project
*/
@Override
public Map<String, Object> queryAuthorizedUser(User loginUser, Long projectCode) {
Map<String, Object> result = new HashMap<>();

// 1. check read permission
Project project = this.projectMapper.queryByCode(projectCode);
boolean hasProjectAndPerm = this.hasProjectAndPerm(loginUser, project, result);
if (!hasProjectAndPerm) {
return result;
}

// 2. query authorized user list
List<User> users = this.userMapper.queryAuthedUserListByProjectId(project.getId());
result.put(Constants.DATA_LIST, users);
this.putMsg(result, Status.SUCCESS);
return result;
}

/**
* query authorized project
*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -579,6 +579,90 @@ public Map<String, Object> grantProject(User loginUser, int userId, String proje
return result;
}

/**
* grant project by code
*
* @param loginUser login user
* @param userId user id
* @param projectCode project code
* @return grant result code
*/
@Override
public Map<String, Object> grantProjectByCode(final User loginUser, final int userId, final long projectCode) {
Map<String, Object> result = new HashMap<>();
result.put(Constants.STATUS, false);

// 1. check if user is existed
User tempUser = this.userMapper.selectById(userId);
if (tempUser == null) {
this.putMsg(result, Status.USER_NOT_EXIST, userId);
return result;
}

// 2. check if project is existed
Project project = this.projectMapper.queryByCode(projectCode);
if (project == null) {
this.putMsg(result, Status.PROJECT_NOT_FOUNT, projectCode);
return result;
}

// 3. only project owner can operate
if (!this.hasPerm(loginUser, project.getUserId())) {
this.putMsg(result, Status.USER_NO_OPERATION_PERM);
return result;
}

// 4. maintain the relationship between project and user
final Date today = new Date();
ProjectUser projectUser = new ProjectUser();
projectUser.setUserId(userId);
projectUser.setProjectId(project.getId());
projectUser.setPerm(7);
projectUser.setCreateTime(today);
projectUser.setUpdateTime(today);
this.projectUserMapper.insert(projectUser);

this.putMsg(result, Status.SUCCESS);
return result;
}

/**
* revoke the project permission for specified user.
* @param loginUser Login user
* @param userId User id
* @param projectCode Project Code
* @return
*/
@Override
public Map<String, Object> revokeProject(User loginUser, int userId, long projectCode) {
Map<String, Object> result = new HashMap<>();
result.put(Constants.STATUS, false);

// 1. only admin can operate
if (this.check(result, !this.isAdmin(loginUser), Status.USER_NO_OPERATION_PERM)) {
return result;
}

// 2. check if user is existed
User user = this.userMapper.selectById(userId);
if (user == null) {
this.putMsg(result, Status.USER_NOT_EXIST, userId);
return result;
}

// 3. check if project is existed
Project project = this.projectMapper.queryByCode(projectCode);
if (project == null) {
this.putMsg(result, Status.PROJECT_NOT_FOUNT, projectCode);
return result;
}

// 4. delete the relationship between project and user
this.projectUserMapper.deleteProjectRelation(project.getId(), user.getId());
this.putMsg(result, Status.SUCCESS);
return result;
}

/**
* grant resource
*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -140,10 +140,12 @@ DELETE_PROJECT_BY_ID_NOTES=delete project by id
QUERY_UNAUTHORIZED_PROJECT_NOTES=query unauthorized project
QUERY_ALL_PROJECT_LIST_NOTES=query all project list
QUERY_AUTHORIZED_PROJECT_NOTES=query authorized project
QUERY_AUTHORIZED_USER_NOTES=query authorized user
TASK_RECORD_TAG=task record related operation
QUERY_TASK_RECORD_LIST_PAGING_NOTES=query task record list paging
CREATE_TOKEN_NOTES=create token ,note: please login first
QUERY_ACCESS_TOKEN_LIST_NOTES=query access token list paging
QUERY_ACCESS_TOKEN_BY_USER_NOTES=query access token for specified user
SCHEDULE=schedule
WARNING_TYPE=warning type(sending strategy)
WARNING_GROUP_ID=warning group id
Expand Down Expand Up @@ -221,6 +223,9 @@ UPDATE_USER_NOTES=update user
DELETE_USER_BY_ID_NOTES=delete user by id
GRANT_PROJECT_NOTES=GRANT PROJECT
PROJECT_IDS=project ids(string format, multiple projects separated by ",")
GRANT_PROJECT_BY_CODE_NOTES=GRANT PROJECT BY CODE
REVOKE_PROJECT_NOTES=REVOKE PROJECT FOR USER
PROJECT_CODE=project codes
GRANT_RESOURCE_NOTES=grant resource file
RESOURCE_IDS=resource ids(string format, multiple resources separated by ",")
GET_USER_INFO_NOTES=get user info
Expand Down
Loading