Skip to content

Commit

Permalink
Activate/Deactivate User By ID (#95)
Browse files Browse the repository at this point in the history
  • Loading branch information
jarydo authored Oct 12, 2023
1 parent 7615de0 commit f016d52
Show file tree
Hide file tree
Showing 12 changed files with 321 additions and 4 deletions.
2 changes: 2 additions & 0 deletions backend/app/graphql/types.py
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,7 @@ class UserInfo(graphene.ObjectType):
role_info = graphene.Field(RoleInfo)
primary_contact = graphene.Field(Contact)
onsite_contacts = graphene.List(Contact)
active = graphene.Boolean()


class ContactInput(graphene.InputObjectType):
Expand Down Expand Up @@ -88,6 +89,7 @@ class UserInfoInput(graphene.InputObjectType):
role_info = graphene.Field(RoleInfoInput)
primary_contact = graphene.Field(ContactInput, required=True)
onsite_contacts = graphene.List(ContactInput, required=True)
active = graphene.Boolean()


class User(graphene.ObjectType):
Expand Down
42 changes: 42 additions & 0 deletions backend/app/graphql/user_mutations.py
Original file line number Diff line number Diff line change
Expand Up @@ -41,5 +41,47 @@ def mutate(self, info, requestor_id, id, userInfo):
)


class ActivateUserByID(Mutation):
class Arguments:
requestor_id = graphene.String(required=True)
id = graphene.String(required=True)

user = graphene.Field(User)

def mutate(self, info, requestor_id, id):
user_service = services["user_service"]
requestor_auth_id = user_service.get_auth_id_by_user_id(requestor_id)
requestor_role = user_service.get_user_role_by_auth_id(requestor_auth_id)

if requestor_role == "Admin":
activate_user_dto = user_service.activate_user_by_id(id)

return ActivateUserByID(
user=User(id=activate_user_dto.id, info=activate_user_dto.info)
)


class DeactivateUserByID(Mutation):
class Arguments:
requestor_id = graphene.String(required=True)
id = graphene.String(required=True)

user = graphene.Field(User)

def mutate(self, info, requestor_id, id):
user_service = services["user_service"]
requestor_auth_id = user_service.get_auth_id_by_user_id(requestor_id)
requestor_role = user_service.get_user_role_by_auth_id(requestor_auth_id)

if requestor_role == "Admin" or requestor_id == id:
deactivate_user_dto = user_service.deactivate_user_by_id(id)

return DeactivateUserByID(
user=User(id=deactivate_user_dto.id, info=deactivate_user_dto.info)
)


class UserMutations(MutationList):
updateUserByID = UpdateUserByID.Field()
activateUserByID = ActivateUserByID.Field()
deactivateUserByID = DeactivateUserByID.Field()
1 change: 1 addition & 0 deletions backend/app/models/user_info.py
Original file line number Diff line number Diff line change
Expand Up @@ -40,5 +40,6 @@ class UserInfo(mg.EmbeddedDocument):
role_info = mg.EmbeddedDocumentField(RoleInfo)
primary_contact = mg.EmbeddedDocumentField(Contact, required=True)
onsite_contacts = mg.EmbeddedDocumentListField(Contact, required=True)
active = mg.BooleanField(default=True)

meta = {"allow_inheritance": True}
5 changes: 4 additions & 1 deletion backend/app/resources/validate_utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,7 @@ def validate_userinfo(userinfo, error_list):
"role_info",
"primary_contact",
"onsite_contacts",
"active",
]
if not isinstance(userinfo, dict):
error_list.append("The info supplied is not a dict.")
Expand All @@ -83,7 +84,9 @@ def validate_userinfo(userinfo, error_list):
error_list = validate_role_info(
userinfo["role"], val, "info.role_info", error_list
)
elif type(val) is not str:
elif key == "active" and type(val) is not bool:
error_list.append("The field info.active supplied is not a boolean.")
elif type(val) is not str and key != "active":
error_list.append(f"The field info.{key} supplied is not a string.")
elif val == "":
error_list.append(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ def create_onboarding_request(self, userInfo):
role_info=userInfo.role_info,
primary_contact=userInfo.primary_contact,
onsite_contacts=userInfo.onsite_contacts,
active=userInfo.active,
)
# Create OnboardingRequest object
new_onboarding_request = OnboardingRequest(
Expand Down
42 changes: 42 additions & 0 deletions backend/app/services/implementations/user_service.py
Original file line number Diff line number Diff line change
Expand Up @@ -264,6 +264,48 @@ def update_user_by_id(self, user_id, update_user_dto):
}
return UserDTO(**kwargs)

def activate_user_by_id(self, user_id):
try:
user = User.objects(id=user_id).first()
if not user:
raise Exception(f"user_id {user_id} not found")

user.info.active = True # activate user

user.save() # save changes

updated_user_dict = (
UserService.__user_to_serializable_dict_and_remove_auth_id(user)
)
kwargs = {"id": updated_user_dict["id"], "info": updated_user_dict["info"]}

return UserDTO(**kwargs)

except Exception as e:
self.logger.error(f"Failed to activate user. Reason = {e}")
raise e

def deactivate_user_by_id(self, user_id):
try:
user = User.objects(id=user_id).first()
if not user:
raise Exception(f"user_id {user_id} not found")

user.info.active = False # deactivate user

user.save() # save changes

updated_user_dict = (
UserService.__user_to_serializable_dict_and_remove_auth_id(user)
)
kwargs = {"id": updated_user_dict["id"], "info": updated_user_dict["info"]}

return UserDTO(**kwargs)

except Exception as e:
self.logger.error(f"Failed to deactivate user. Reason = {e}")
raise e

def delete_user_by_id(self, user_id):
try:
deleted_user = User.objects(id=user_id).modify(remove=True, new=False)
Expand Down
26 changes: 26 additions & 0 deletions backend/app/services/interfaces/user_service.py
Original file line number Diff line number Diff line change
Expand Up @@ -116,6 +116,32 @@ def update_user_by_id(self, user_id, user):
"""
pass

@abstractmethod
def activate_user_by_id(self, user_id):
"""
Activate a user
:param user_id: user's id
:type user_id: str
:return: the activated user
:rtype: UserDTO
:raises Exception: if user update fails
"""
pass

@abstractmethod
def deactivate_user_by_id(self, user_id):
"""
Deactivate a user
:param user_id: user's id
:type user_id: str
:return: the deactivated user
:rtype: UserDTO
:raises Exception: if user update fails
"""
pass

@abstractmethod
def delete_user_by_id(self, user_id):
"""
Expand Down
6 changes: 6 additions & 0 deletions backend/tests/graphql/mock_test_data.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
{"name": "abc", "phone": "123-456-7890", "email": "[email protected]"},
{"name": "Jane Doe", "phone": "111-222-3333", "email": "[email protected]"},
],
"active": True,
}

MOCK_INFO1_CAMEL = {
Expand All @@ -42,6 +43,7 @@
{"name": "abc", "phone": "123-456-7890", "email": "[email protected]"},
{"name": "Jane Doe", "phone": "111-222-3333", "email": "[email protected]"},
],
"active": True,
}

MOCK_INFO2_SNAKE = {
Expand All @@ -66,6 +68,7 @@
{"name": "def", "phone": "098-765-4321", "email": "[email protected]"},
{"name": "John Doe", "phone": "444-555-6666", "email": "[email protected]"},
],
"active": True,
}

MOCK_INFO2_CAMEL = {
Expand All @@ -90,6 +93,7 @@
{"name": "def", "phone": "098-765-4321", "email": "[email protected]"},
{"name": "John Doe", "phone": "444-555-6666", "email": "[email protected]"},
],
"active": True,
}

MOCK_INFO3_SNAKE = {
Expand All @@ -108,6 +112,7 @@
{"name": "ghi", "phone": "135-792-4680", "email": "[email protected]"},
{"name": "Jack Doe", "phone": "777-888-999", "email": "[email protected]"},
],
"active": False,
}

MOCK_INFO3_CAMEL = {
Expand All @@ -126,6 +131,7 @@
{"name": "ghi", "phone": "135-792-4680", "email": "[email protected]"},
{"name": "Jack Doe", "phone": "777-888-999", "email": "[email protected]"},
],
"active": False,
}

MOCK_USER1_SNAKE = {
Expand Down
Loading

0 comments on commit f016d52

Please sign in to comment.