diff --git a/server/objectives/inputs.py b/server/objectives/inputs.py index cd4a96cf..2c08ea01 100644 --- a/server/objectives/inputs.py +++ b/server/objectives/inputs.py @@ -4,13 +4,15 @@ from graphene import InputObjectType class ObjectiveInput(InputObjectType): text = graphene.String(required=True) + id = graphene.ID() -class ObjectiveGroupInput(InputObjectType): +class AddObjectiveGroupArgument(InputObjectType): title = graphene.String(required=True) module = graphene.ID(required=True) objectives = graphene.List(ObjectiveInput) -class AddObjectiveGroupArgument(ObjectiveGroupInput): - pass +class UpdateObjectiveGroupArgument(InputObjectType): + id = graphene.ID(required=True) + objectives = graphene.List(ObjectiveInput) diff --git a/server/objectives/mutations.py b/server/objectives/mutations.py index ee27bcd6..df9e50ff 100644 --- a/server/objectives/mutations.py +++ b/server/objectives/mutations.py @@ -1,10 +1,12 @@ import graphene from graphene import relay, InputObjectType +from graphql_relay import from_global_id + from api.utils import get_object from books.models import Module from books.schema.inputs import UserGroupBlockVisibility from core.utils import set_visible_for, set_hidden_for -from objectives.inputs import AddObjectiveGroupArgument +from objectives.inputs import AddObjectiveGroupArgument, UpdateObjectiveGroupArgument from objectives.models import ObjectiveProgressStatus, Objective, ObjectiveGroup from objectives.schema import ObjectiveNode, ObjectiveGroupNode @@ -79,7 +81,39 @@ class AddObjectiveGroup(relay.ClientIDMutation): return cls(objective_group=new_objective_group) +class UpdateObjectiveGroup(relay.ClientIDMutation): + class Input: + objective_group = graphene.Argument(UpdateObjectiveGroupArgument) + + objective_group = graphene.Field(ObjectiveGroupNode) + + @classmethod + def mutate_and_get_payload(cls, root, info, **kwargs): + objective_group_data = kwargs.get('objective_group') + id = objective_group_data.get('id') + objective_group = get_object(ObjectiveGroup, id) + objectives = objective_group_data.get('objectives') + existing_objective_ids = list(objective_group.objectives.values_list('id', flat=True)) + for objective in objectives: + if objective.get('id') is not None: + objective_id = objective.get('id') + updated_objective = get_object(Objective, objective_id) + updated_objective.text = objective.get('text') + updated_objective.save() + existing_objective_ids.remove(int(from_global_id(objective_id)[1])) + else: + Objective.objects.create(text=objective.get('text'), group=objective_group) + + # remove existing items that are not in payload + for objective_id in existing_objective_ids: + objective = Objective.objects.get(pk=objective_id) + objective.delete() + + return cls(objective_group=objective_group) + + class ObjectiveMutations: update_objective_progress = UpdateObjectiveProgress.Field() update_objective_group_visibility = UpdateObjectiveGroupVisibility.Field() add_objective_group = AddObjectiveGroup.Field() + update_objective_group = UpdateObjectiveGroup.Field() diff --git a/server/objectives/schema.py b/server/objectives/schema.py index cef4e1dd..0c6f136a 100644 --- a/server/objectives/schema.py +++ b/server/objectives/schema.py @@ -9,6 +9,7 @@ from objectives.models import ObjectiveGroup, Objective, ObjectiveProgressStatus class ObjectiveGroupNode(DjangoObjectType): pk = graphene.Int() display_title = graphene.String() + mine = graphene.Boolean() class Meta: model = ObjectiveGroup @@ -21,6 +22,9 @@ class ObjectiveGroupNode(DjangoObjectType): def resolve_display_title(self, *args, **kwargs): return self.get_title_display() + def resolve_mine(self, info, **kwargs): + return self.owner is not None and self.owner.pk == info.context.user.pk + class ObjectiveNode(DjangoObjectType):