DeleteUser removes a user or group from the repository.
(req *restful.Request, rsp *restful.Response)
| 225 | |
| 226 | // DeleteUser removes a user or group from the repository. |
| 227 | func (s *UserHandler) DeleteUser(req *restful.Request, rsp *restful.Response) error { |
| 228 | |
| 229 | login := req.PathParameter("Login") |
| 230 | ctx := req.Request.Context() |
| 231 | singleQ := &idm.UserSingleQuery{} |
| 232 | claims, ok := claim.FromContext(ctx) |
| 233 | if !ok { |
| 234 | return errors.WithStack(errors.MissingClaims) |
| 235 | } |
| 236 | |
| 237 | if strings.HasSuffix(req.Request.RequestURI, "%2F") || strings.HasSuffix(req.Request.RequestURI, "/") { |
| 238 | log.Logger(ctx).Info("Received User.Delete API request (GROUP)", zap.String("login", login), zap.String("crtGroup", claims.GroupPath), zap.String("request", req.Request.RequestURI)) |
| 239 | if strings.HasPrefix(claims.GroupPath, "/"+login) { |
| 240 | return errors.WithAPICode(errors.StatusForbidden, errors.ApiGroupCannotDeleteOwn) |
| 241 | } |
| 242 | singleQ.GroupPath = login |
| 243 | singleQ.Recursive = true |
| 244 | } else { |
| 245 | if claims.Name == login { |
| 246 | return errors.WithAPICode(errors.StatusForbidden, errors.ApiUserCannotDeleteOwn) |
| 247 | } |
| 248 | log.Logger(ctx).Debug("Received User.Delete API request (LOGIN)", zap.String("login", login), zap.String("request", req.Request.RequestURI)) |
| 249 | singleQ.Login = login |
| 250 | } |
| 251 | query, _ := anypb.New(singleQ) |
| 252 | mainQuery := &service2.Query{SubQueries: []*anypb.Any{query}} |
| 253 | cli := idmc.UserServiceClient(ctx) |
| 254 | |
| 255 | // Search first to check policies |
| 256 | stream, err := cli.SearchUser(ctx, &idm.SearchUserRequest{Query: mainQuery}) |
| 257 | err = commons.ForEach(stream, err, func(response *idm.SearchUserResponse) error { |
| 258 | if s.MatchPolicies(ctx, response.User.Uuid, response.User.Policies, service2.ResourcePolicyAction_WRITE) { |
| 259 | return nil |
| 260 | } |
| 261 | jj, _ := json.Marshal(response.User.Policies) |
| 262 | subj, _ := auth.SubjectsForResourcePolicyQuery(ctx, nil) |
| 263 | ss, _ := json.Marshal(subj) |
| 264 | log.Auditer(ctx).Error( |
| 265 | fmt.Sprintf("Forbidden action: could not delete user [%s], policies were %s, subjects %s", response.User.Login, string(jj), string(ss)), |
| 266 | log.GetAuditId(common.AuditUserDelete), |
| 267 | response.User.ZapUuid(), |
| 268 | ) |
| 269 | return errors.WithMessage(errors.StatusForbidden, "You are not allowed to edit this resource") |
| 270 | }) |
| 271 | if err != nil { |
| 272 | return err |
| 273 | } |
| 274 | |
| 275 | if singleQ.GroupPath != "" { |
| 276 | |
| 277 | uName := claim.UserNameFromContext(ctx) |
| 278 | // This is a group deletion - send it in background |
| 279 | jobUuid := uuid.New() |
| 280 | job := &jobs.Job{ |
| 281 | ID: "delete-group-" + jobUuid, |
| 282 | Owner: uName, |
| 283 | Label: "Delete groups in background", |
| 284 | MaxConcurrency: 1, |
nothing calls this directly
no test coverage detected