UndeleteUser undeletes a user.
(ctx context.Context, request *connect.Request[v1pb.UndeleteUserRequest])
| 597 | |
| 598 | // UndeleteUser undeletes a user. |
| 599 | func (s *UserService) UndeleteUser(ctx context.Context, request *connect.Request[v1pb.UndeleteUserRequest]) (*connect.Response[v1pb.User], error) { |
| 600 | if s.profile.SaaS { |
| 601 | return nil, connect.NewError(connect.CodeUnimplemented, errors.Errorf("CreateUser is not available in SaaS mode, add users via workspace IAM policy instead")) |
| 602 | } |
| 603 | |
| 604 | callerUser, ok := GetUserFromContext(ctx) |
| 605 | if !ok { |
| 606 | return nil, connect.NewError(connect.CodePermissionDenied, errors.Errorf("failed to get caller user")) |
| 607 | } |
| 608 | workspaceID := common.GetWorkspaceIDFromContext(ctx) |
| 609 | ok, err := s.iamManager.CheckPermission(ctx, permission.UsersUndelete, callerUser, workspaceID) |
| 610 | if err != nil { |
| 611 | return nil, connect.NewError(connect.CodeInternal, errors.Errorf("failed to check permission with error: %v", err.Error())) |
| 612 | } |
| 613 | if !ok { |
| 614 | return nil, connect.NewError(connect.CodePermissionDenied, errors.Errorf("user does not have permission %q", permission.UsersUndelete)) |
| 615 | } |
| 616 | |
| 617 | email, err := common.GetUserEmail(request.Msg.Name) |
| 618 | if err != nil { |
| 619 | return nil, connect.NewError(connect.CodeInvalidArgument, err) |
| 620 | } |
| 621 | if err := validateEndUserEmail(email); err != nil { |
| 622 | return nil, err |
| 623 | } |
| 624 | user, err := s.store.GetUserByEmail(ctx, email) |
| 625 | if err != nil { |
| 626 | return nil, connect.NewError(connect.CodeInternal, errors.Wrapf(err, "failed to get user")) |
| 627 | } |
| 628 | if user == nil { |
| 629 | return nil, connect.NewError(connect.CodeNotFound, errors.Errorf("user %q not found", email)) |
| 630 | } |
| 631 | if !user.MemberDeleted { |
| 632 | return nil, connect.NewError(connect.CodeInvalidArgument, errors.Errorf("user %q is already active", email)) |
| 633 | } |
| 634 | |
| 635 | if err := s.preUndeleteUserGuard(ctx, workspaceID, user); err != nil { |
| 636 | return nil, err |
| 637 | } |
| 638 | |
| 639 | user, err = s.store.UpdateUser(ctx, user, &store.UpdateUserMessage{Delete: &undeletePatch}) |
| 640 | if err != nil { |
| 641 | return nil, connect.NewError(connect.CodeInternal, err) |
| 642 | } |
| 643 | |
| 644 | v1User, err := convertToUser(ctx, s.iamManager, user) |
| 645 | if err != nil { |
| 646 | return nil, connect.NewError(connect.CodeInternal, errors.Wrapf(err, "failed to convert user")) |
| 647 | } |
| 648 | return connect.NewResponse(v1User), nil |
| 649 | } |
| 650 | |
| 651 | // UpdateEmail updates a user's email address. |
| 652 | func (s *UserService) UpdateEmail(ctx context.Context, request *connect.Request[v1pb.UpdateEmailRequest]) (*connect.Response[v1pb.User], error) { |
nothing calls this directly
no test coverage detected