add updateSpeedGraderSettings mutation

flag=platform_service_speedgrader

Test Plan:
- ensure you can update the gradeByQuestion speed grader setting via
  the new updateSpeedGraderSettings mutation.

Change-Id: If5bab4c1629cd094c570ce43263eb2068e1f59eb
Reviewed-on: https://gerrit.instructure.com/c/canvas-lms/+/358055
Tested-by: Service Cloud Jenkins <svc.cloudjenkins@instructure.com>
Reviewed-by: Aaron Shafovaloff <ashafovaloff@instructure.com>
Product-Review: Aaron Shafovaloff <ashafovaloff@instructure.com>
QA-Review: Spencer Olson <solson@instructure.com>
This commit is contained in:
Spencer Olson 2024-09-20 11:01:53 -05:00
parent b9b5f39a45
commit c29d7b6bf8
8 changed files with 196 additions and 0 deletions

View File

@ -0,0 +1,35 @@
# frozen_string_literal: true
#
# Copyright (C) 2024 - present Instructure, Inc.
#
# This file is part of Canvas.
#
# Canvas is free software: you can redistribute it and/or modify it under
# the terms of the GNU Affero General Public License as published by the Free
# Software Foundation, version 3 of the License.
#
# Canvas is distributed in the hope that it will be useful, but WITHOUT ANY
# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
# A PARTICULAR PURPOSE. See the GNU Affero General Public License for more
# details.
#
# You should have received a copy of the GNU Affero General Public License along
# with this program. If not, see <http://www.gnu.org/licenses/>.
#
class Mutations::UpdateSpeedGraderSettings < Mutations::BaseMutation
argument :grade_by_question, Boolean, required: true
field :speed_grader_settings, Types::SpeedGraderSettingsType, null: false
def resolve(input:)
unless current_user.grants_right?(current_user, :update_speed_grader_settings)
raise GraphQL::ExecutionError, "Not authorized to update speed grader settings"
end
current_user.preferences[:enable_speedgrader_grade_by_question] = input.fetch(:grade_by_question)
current_user.save!
current_user
end
end

View File

@ -116,6 +116,7 @@ class Types::MutationType < Types::ApplicationObjectType
field :create_user_inbox_label, mutation: Mutations::CreateUserInboxLabel
field :delete_user_inbox_label, mutation: Mutations::DeleteUserInboxLabel
field :update_my_inbox_settings, mutation: Mutations::UpdateMyInboxSettings
field :update_speed_grader_settings, mutation: Mutations::UpdateSpeedGraderSettings
# TODO: Remove the in active development string from here once this is more
# finalized.

View File

@ -0,0 +1,22 @@
# frozen_string_literal: true
#
# Copyright (C) 2024 - present Instructure, Inc.
#
# This file is part of Canvas.
#
# Canvas is free software: you can redistribute it and/or modify it under
# the terms of the GNU Affero General Public License as published by the Free
# Software Foundation, version 3 of the License.
#
# Canvas is distributed in the hope that it will be useful, but WITHOUT ANY
# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
# A PARTICULAR PURPOSE. See the GNU Affero General Public License for more
# details.
#
# You should have received a copy of the GNU Affero General Public License along
# with this program. If not, see <http://www.gnu.org/licenses/>.
class Types::SpeedGraderSettingsType < GraphQL::Schema::Object
field :grade_by_question, Boolean, null: false
end

View File

@ -1374,6 +1374,7 @@ class User < ActiveRecord::Base
read_email_addresses
view_user_logins
generate_observer_pairing_code
update_speed_grader_settings
]
given { |user| user == self && user.user_can_edit_name? }
@ -1766,6 +1767,12 @@ class User < ActiveRecord::Base
read_or_initialize_attribute(:preferences, {})
end
def speed_grader_settings
{
grade_by_question: preferences.fetch(:enable_speedgrader_grade_by_question, false)
}
end
def new_user_tutorial_statuses
get_preference(:new_user_tutorial_statuses) || {}
end

View File

@ -0,0 +1,66 @@
# frozen_string_literal: true
#
# Copyright (C) 2023 - present Instructure, Inc.
#
# This file is part of Canvas.
#
# Canvas is free software: you can redistribute it and/or modify it under
# the terms of the GNU Affero General Public License as published by the Free
# Software Foundation, version 3 of the License.
#
# Canvas is distributed in the hope that it will be useful, but WITHOUT ANY
# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
# A PARTICULAR PURPOSE. See the GNU Affero General Public License for more
# details.
#
# You should have received a copy of the GNU Affero General Public License along
# with this program. If not, see <http://www.gnu.org/licenses/>.
#
require "spec_helper"
require_relative "../graphql_spec_helper"
describe Mutations::UpdateSpeedGraderSettings do
before :once do
teacher_in_course(active_all: true)
end
def execute_with_input(input)
mutation_command = <<~GQL
mutation {
updateSpeedGraderSettings(input: {
#{input}
}) {
speedGraderSettings {
gradeByQuestion
}
}
}
GQL
context = {
current_user: @teacher,
domain_root_account: @course.root_account,
request: ActionDispatch::TestRequest.create,
session: {},
}
CanvasSchema.execute(mutation_command, context:)
end
it "updates the speed grader settings" do
expect do
execute_with_input <<~GQL
gradeByQuestion: true
GQL
end.to change {
@teacher.reload.speed_grader_settings.fetch(:grade_by_question)
}.from(false).to(true)
end
it "returns the updated value" do
result = execute_with_input <<~GQL
gradeByQuestion: true
GQL
expect(result.dig("data", "updateSpeedGraderSettings", "speedGraderSettings", "gradeByQuestion")).to be true
end
end

View File

@ -75,6 +75,15 @@ describe User do
end
end
describe "#speed_grader_settings" do
it "stores the user's speed grader settings" do
user = user_model
expect { user.preferences[:enable_speedgrader_grade_by_question] = true }.to change {
user.speed_grader_settings
}.from({ grade_by_question: false }).to({ grade_by_question: true })
end
end
it "adds an lti_id on creation" do
user = User.new
expect(user.lti_id).to be_blank
@ -3035,6 +3044,17 @@ describe User do
end
describe "permissions" do
it "allows a user to update their own speed grader settings" do
user = user_model
expect(user.grants_right?(user, :update_speed_grader_settings)).to be true
end
it "does not allow a user to update someone else's speed grader settings" do
user1 = user_model
user2 = user_model
expect(user1.grants_right?(user2, :update_speed_grader_settings)).to be false
end
it "does not allow account admin to modify admin privileges of other account admins" do
expect(RoleOverride.readonly_for(Account.default, :manage_role_overrides, admin_role)).to be_truthy
expect(RoleOverride.readonly_for(Account.default, :manage_account_memberships, admin_role)).to be_truthy

View File

@ -33,6 +33,7 @@ import {getAssignmentsByCourseId} from './queries/assignmentsByCourseIdQuery'
import {getEnrollmentsByCourse} from './queries/enrollmentsByCourseQuery'
import {getCommentBankItems} from './queries/commentBankQuery'
import {updateSpeedGraderSettings} from './mutations/updateSpeedGraderSettingsMutation'
import {updateSubmissionGrade} from './mutations/updateSubmissionGradeMutation'
import {createSubmissionComment} from './mutations/createSubmissionCommentMutation'
import {hideAssignmentGradesForSections} from './mutations/hideAssignmentGradesForSectionsMutation'
@ -141,6 +142,7 @@ ready(() => {
createCommentBankItem,
deleteCommentBankItem,
updateCommentBankItem,
updateSpeedGraderSettings,
},
postMessageAliases,
context: {

View File

@ -0,0 +1,43 @@
/*
* Copyright (C) 2024 - present Instructure, Inc.
*
* This file is part of Canvas.
*
* Canvas is free software: you can redistribute it and/or modify it under
* the terms of the GNU Affero General Public License as published by the Free
* Software Foundation, version 3 of the License.
*
* Canvas is distributed in the hope that it will be useful, but WITHOUT ANY
* WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
* A PARTICULAR PURPOSE. See the GNU Affero General Public License for more
* details.
*
* You should have received a copy of the GNU Affero General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
import {z} from 'zod'
import {executeQuery} from '@canvas/query/graphql'
import gql from 'graphql-tag'
export const UPDATE_SPEED_GRADER_SETTINGS = gql`
mutation UpdateSpeedGraderSettingsPlatformSG($gradeByQuestion: Boolean!) {
__typename
updateSpeedGraderSettings(input: {gradeByQuestion: $gradeByQuestion}) {
speedGraderSettings {
gradeByQuestion
}
}
}
`
export const ZUpdateSpeedGraderSettingsParams = z.object({gradeByQuestion: z.boolean()})
type UpdateSpeedGraderSettingsParams = z.infer<typeof ZUpdateSpeedGraderSettingsParams>
export async function updateSpeedGraderSettings(
params: UpdateSpeedGraderSettingsParams
): Promise<any> {
const result = executeQuery<any>(UPDATE_SPEED_GRADER_SETTINGS, params)
return result
}