instructure/canvas-lms · error · GraphQL::ExecutionError

and cannot be used together

Error message

{a} and {b} cannot be used together

What it means

hideAssignmentGrades rejects simultaneous use of the mutually exclusive inputs only_student_ids and skip_student_ids; the I18n template {a} and {b} cannot be used together interpolates the argument names, so the surfaced message reads 'only_student_ids and skip_student_ids cannot be used together'.

Solutions

  1. Send only one of the two fields; omit (don't send) the other entirely.
  2. In client code, build variables conditionally so the two filters can never coexist.
  3. Reset the opposite filter in the UI when one is chosen.
  4. If both semantics are needed (hide some, skip others), compute the final student id list client-side and pass a single only_student_ids.

Example fix

// before
mutate({ variables: { assignmentId, onlyStudentIds: ids, skipStudentIds: skips } });
// after
const vars = { assignmentId };
if (ids?.length) vars.onlyStudentIds = ids;
else if (skips?.length) vars.skipStudentIds = skips;
mutate({ variables: vars });
Defensive patterns

Strategy: validation

Validate before calling

if (onlyStudentIds?.length && skipStudentIds?.length) {
  throw new ValidationError('only_student_ids and skip_student_ids are mutually exclusive');
}

Try / catch

try { await hideGrades(vars); }
catch (e) {
  if (String(e).includes('cannot be used together')) {
    delete vars.skipStudentIds; // keep only one filter
    return hideGrades(vars);
  }
  throw e;
}

Prevention

When it happens

Trigger: Calling the mutation with both onlyStudentIds and skipStudentIds non-nil in the same input object.

Common situations: Client form state where both filter fields retain values from previous edits; generic wrapper functions that forward all variables including null-vs-omitted confusion; assembling variables programmatically from a filter object.

Related errors


AI-assisted analysis of instructure/canvas-lms@1c9f0bb801 (2026-09-15). Data as JSON: /api/errors/2931394bb854139e. Report an issue: GitHub.

Appendix: source

Thrown at app/graphql/mutations/hide_assignment_grades.rb:50

  def resolve(input:)
    begin
      assignment = AbstractAssignment.find_assignment_or_peer_review(input[:assignment_id])
      course = assignment.context
      sections = input[:section_ids] ? course.course_sections.where(id: input[:section_ids]) : nil
    rescue ActiveRecord::RecordNotFound
      raise GraphQL::ExecutionError, "not found"
    end

    verify_authorized_action!(assignment, :grade)

    unless assignment.grades_published?
      raise GraphQL::ExecutionError, "Assignments under moderation cannot be hidden before grades are published"
    end
    raise GraphQL::ExecutionError, "Anonymous assignments cannot be posted by section" if sections && assignment.anonymous_grading?

    if input[:only_student_ids] && input[:skip_student_ids]
      raise GraphQL::ExecutionError, I18n.t("{a} and {b} cannot be used together", a: "only_student_ids", b: "skip_student_ids")
    end

    visible_enrollments = course.apply_enrollment_visibility(course.student_enrollments, current_user, sections)
    visible_enrollments = visible_enrollments.where(user_id: input[:only_student_ids]) if input[:only_student_ids]
    visible_enrollments = visible_enrollments.where.not(user_id: input[:skip_student_ids]) if input[:skip_student_ids]

    submissions_scope = assignment.submissions.active.joins(user: :enrollments)
    submissions_scope = course.apply_enrollment_visibility(submissions_scope, current_user).merge(visible_enrollments)
    progress = course.progresses.new(tag: "hide_assignment_grades")

    if progress.save
      progress.process_job(
        assignment,
        :hide_submissions,
        { preserve_method_args: true, priority: Delayed::HIGH_PRIORITY },
        progress:,
        submission_ids: submissions_scope.pluck(:id),
        skip_content_participation_refresh: false

View on GitHub (pinned to 1c9f0bb801)