2011-02-01 09:57:29 +08:00
|
|
|
#
|
|
|
|
# Copyright (C) 2011 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/>.
|
|
|
|
#
|
|
|
|
|
|
|
|
# Assocates a rubric with an "association", or idea. An assignment, for example.
|
|
|
|
# RubricAssessments, then, are concrete assessments of the artifacts associated
|
|
|
|
# with this idea, such as assignment submissions.
|
|
|
|
# The other purpose of this class is just to make rubrics reusable.
|
|
|
|
class RubricAssociation < ActiveRecord::Base
|
2011-11-11 00:44:12 +08:00
|
|
|
attr_accessor :skip_updating_points_possible
|
2014-01-23 01:54:27 +08:00
|
|
|
attr_accessible :rubric, :association_object, :context, :use_for_grading, :title, :description, :summary_data, :purpose, :url, :hide_score_total, :bookmarked
|
2011-02-01 09:57:29 +08:00
|
|
|
belongs_to :rubric
|
2014-01-23 01:54:27 +08:00
|
|
|
belongs_to :association_object, :polymorphic => true, :foreign_type => :association_type, :foreign_key => :association_id
|
learning outcomes refactor
This list is *NOT* complete, some items may have snuck in that I forgot
to note, and/or some of the noted items may not be completely functional
yet.
Specs need to be written around a lot of this, other specs will no doubt
need to be fixed.
Some things, particularly around LearningOutcomeGroups will need data
migrations that aren't there yet.
* remove LearningOutcome.non_rubric_outcomes? and replace with false
where invoked
* remove LearningOutcome.enabled? and replace with true where invoked
* remove never-taken branches
* remove the shared/aligned_outcomes partial and it's supporting
javascript, since it's now empty
* remove js handler for add_outcome_alignment_link and supporting
method since it only occurred in never-taken branches
* mix LearningOutcomeContext into Course and Account
* replace LearningOutcomeGroup.default_for(context) with
LearningOutcomeContext#root_outcome_group
* rename LearningOutcome#content_tags to LearningOutcome#alignments
* rename LearningOutcomeGroup#content_tags to
LearningOutcomeGroup#child_links, and properly restrict
* remove ContentTag[Alignment]#rubric_association_id, add
ContentTag[Alignment]#has_rubric_association? that looks at the
presence of the content's rubric_association_id
* condition off the assignment having a rubric_association rather than
filtering tags by has_rubric_association (which just looks back at
the assignment). all or none of the assignment's alignments are
forced to have the association (via the assignment). this was true in
practice before, is now codified (and more efficient)
* rename AssessmentQuestionBank#learning_outcome_tags to
AssessmentQuestionBank#learning_outcome_alignments
* rename Assignment#learning_outcome_tags to
Assignment#learning_outcome_alignments
* rename Rubric#learning_outcome_tags to
Rubric#learning_outcome_alignments
* move/rename (Course|Account)#learning_outcome_tags to
LearningOutcomeContext#learning_outcome_links
* move/rename Account#learning_outcomes (corrected) and
Course#learning_outcomes to
LearningOutcomeContext#linked_learning_outcomes
* move/rename Account#created_learning_outcomes and
Course#created_learning_outcomes to
LearningOutcomeContext#created_learning_outcomes
* clarify and correct usage of linked_learning_outcomes vs.
created_learning_outcomes
* move/rename (Account|Account)#learning_outcome_groups to
LearningOutcomeContext#learning_outcome_groups
* remove unused Account#associated_learning_outcomes
* just remove one link to a learning outcome when deleting
* merge Account#has_outcomes?, Course#has_outcomes? and
Course#has_outcomes into LearningOutcomeContext#has_outcomes?, add a
use in Context#active_record_types
* kill LearningOutcomeGroup#root_learning_outcome_group (unused)
* rename LearningOutcomeResult#content_tag to
LearningOutcomeResult#alignment
* kill unused (and broken) OutcomesController#add_outcome_group
* kill unused OutcomesController#update_outcomes_for_asset
* kill unused OutcomesController#outcomes_for_asset
* remove unused (outside specs, correct specs)
AssessmentQuestionBank#outcomes=
* remove unused ContentTag#learning_outcome_content
* replace ContentTag.learning_outcome_tags_for(asset) (only ever called
with asset=an assignment) with call to
Assignment#learning_outcome_alignments
* remove unused ContentTag.not_rubric
* remove (now) unused ContentTag.include_outcome
* remove unused LearningOutcome#learning_outcome_group_associations
* avoid explicit use of ContentTag in outcome-related specs
* replace LearningOutcomeGroup#learning_outcome_tags with
LearningOutcomeGroup#child_outcome_links (and only use for outcome
links; not tags for child groups)
* split ContentTag#create_outcome_result into
Submission#create_outcome_result,
QuizSubmission#create_outcome_result, and
RubricAssessment#create_outcome_result. fix some bugs along the way
* refactor ContentTag.outcome_tags_for_banks and some code from
QuizSubmission#(track_outcomes|update_outcomes_for_assessment_questions)
into QuizSubmission#questions_and_alignments
* refactor RubricAssociation#update_outcome_relations and
Rubric#update_alignments into LearningOutcome.update_alignments
* don't use ContentTag#rubric_association with outcome alignments; use
the tag's content's rubric_association in its place (they should have
been equal anyways)
* refactor LearningOutcome.available_in_context and
@context.root_outcome_group.sorted_all_outcomes (only time
sorted_all_outcomes is used) into
LearningOutcomeContext#available_outcomes and
LearningOutcomeContext#available_outcome
* overhaul LearningOutcomeGroup#sorted_content and rename to
LearningOutcomeGroup#sorted_children. it not returns ContentTags
(outcome links) and LearningOutcomeGroups, vs. LearningOutcomes and
LearningOutcomeGroups; fix usages appropriately
* fix UI for arranging/deleting outcome links and groups within a group
to refer to the outcome link rather than the outcome
Change-Id: I85d99f2634f7206332cb1f5d5ea575b428988d4b
Reviewed-on: https://gerrit.instructure.com/12590
Reviewed-by: Jacob Fugal <jacob@instructure.com>
Tested-by: Jacob Fugal <jacob@instructure.com>
2012-07-13 01:16:13 +08:00
|
|
|
|
2011-02-01 09:57:29 +08:00
|
|
|
belongs_to :context, :polymorphic => true
|
2012-06-13 02:39:53 +08:00
|
|
|
has_many :rubric_assessments, :dependent => :nullify
|
2011-02-01 09:57:29 +08:00
|
|
|
has_many :assessment_requests, :dependent => :destroy
|
|
|
|
|
|
|
|
has_a_broadcast_policy
|
|
|
|
|
2013-08-08 06:19:48 +08:00
|
|
|
validates_presence_of :purpose, :rubric_id, :association_id, :association_type, :context_id, :context_type
|
2011-02-01 09:57:29 +08:00
|
|
|
validates_length_of :description, :maximum => maximum_text_length, :allow_nil => true, :allow_blank => true
|
|
|
|
|
|
|
|
before_save :update_assignment_points
|
|
|
|
before_save :update_values
|
|
|
|
after_create :update_rubric
|
2012-05-01 05:57:13 +08:00
|
|
|
after_create :link_to_assessments
|
2011-02-01 09:57:29 +08:00
|
|
|
before_save :update_old_rubric
|
|
|
|
after_destroy :update_rubric
|
correctly maintain assignment/rubric <-> outcome links
There are a few old LearningOutcomeResults that have a nil artifact, and
many that have a Submission as an artifact. We want to get rid of these
because they come from bad data, and step 1 toward that goal is to stop
creating them and hide them in the UI.
The LORs with a nil artifact are very old and I believe came from a very
early incarnation of outcomes. The LORs with a Submission as an artifact
came from a combination of two code problems. The first was old code
that allowed an assignment that was aligned with an outcome but did not
have a rubric to create LORs directly based on it's submission. The
second was a bug that prevented the assignment <-> outcome link from
being destroyed when a rubric with an outcome was removed from an
assignment.
fixes CNVS-7495
fixes CNVS-7498
test plan:
- try different combinations of adding a rubric with an outcome to an
assignment.
- when you grade the assignment, the grade create a learning outcome result
(which can be seen on the outcome show page, or in the account outcome
report) if the rubric+outcome are currently attached to the assignment.
- so for example, add a rubric with an outcome, check, remove just the outcome
row, check, add a new outcome row, check, remove the whole rubric, check.
- be sure to check both the show page and the outcome report
TODO:
- datafix migration
Change-Id: I37700e3e5c08fc6cfb8fcf1cac42ea6693fcaba3
Reviewed-on: https://gerrit.instructure.com/23303
Tested-by: Jenkins <jenkins@instructure.com>
Reviewed-by: Cameron Matheson <cameron@instructure.com>
QA-Review: Amber Taniuchi <amber@instructure.com>
Product-Review: Simon Williams <simon@instructure.com>
2013-08-14 07:15:15 +08:00
|
|
|
after_destroy :update_alignments
|
2011-02-01 09:57:29 +08:00
|
|
|
after_save :assert_uniqueness
|
correctly maintain assignment/rubric <-> outcome links
There are a few old LearningOutcomeResults that have a nil artifact, and
many that have a Submission as an artifact. We want to get rid of these
because they come from bad data, and step 1 toward that goal is to stop
creating them and hide them in the UI.
The LORs with a nil artifact are very old and I believe came from a very
early incarnation of outcomes. The LORs with a Submission as an artifact
came from a combination of two code problems. The first was old code
that allowed an assignment that was aligned with an outcome but did not
have a rubric to create LORs directly based on it's submission. The
second was a bug that prevented the assignment <-> outcome link from
being destroyed when a rubric with an outcome was removed from an
assignment.
fixes CNVS-7495
fixes CNVS-7498
test plan:
- try different combinations of adding a rubric with an outcome to an
assignment.
- when you grade the assignment, the grade create a learning outcome result
(which can be seen on the outcome show page, or in the account outcome
report) if the rubric+outcome are currently attached to the assignment.
- so for example, add a rubric with an outcome, check, remove just the outcome
row, check, add a new outcome row, check, remove the whole rubric, check.
- be sure to check both the show page and the outcome report
TODO:
- datafix migration
Change-Id: I37700e3e5c08fc6cfb8fcf1cac42ea6693fcaba3
Reviewed-on: https://gerrit.instructure.com/23303
Tested-by: Jenkins <jenkins@instructure.com>
Reviewed-by: Cameron Matheson <cameron@instructure.com>
QA-Review: Amber Taniuchi <amber@instructure.com>
Product-Review: Simon Williams <simon@instructure.com>
2013-08-14 07:15:15 +08:00
|
|
|
after_save :update_alignments
|
2011-02-01 09:57:29 +08:00
|
|
|
serialize :summary_data
|
|
|
|
|
|
|
|
ValidAssociationModels = {
|
|
|
|
'Course' => ::Course,
|
|
|
|
'Assignment' => ::Assignment,
|
|
|
|
'Account' => ::Account,
|
|
|
|
}
|
|
|
|
|
|
|
|
# takes params[:association_type] and params[:association_id] and finds the
|
|
|
|
# valid association object, if possible. Valid types are listed in
|
|
|
|
# ValidAssociationModels. This doesn't verify the user has access to the
|
|
|
|
# object.
|
|
|
|
def self.get_association_object(params)
|
|
|
|
return nil unless params
|
|
|
|
a_type = params.delete(:association_type)
|
|
|
|
a_id = params.delete(:association_id)
|
|
|
|
return @context if a_type == @context.class.to_s && a_id == @context.id
|
|
|
|
klass = ValidAssociationModels[a_type]
|
|
|
|
return nil unless klass
|
2011-04-27 11:55:24 +08:00
|
|
|
klass.find_by_id(a_id) if a_id.present? # authorization is checked in the calling method
|
2011-02-01 09:57:29 +08:00
|
|
|
end
|
|
|
|
|
|
|
|
set_broadcast_policy do |p|
|
|
|
|
p.dispatch :rubric_association_created
|
|
|
|
p.to { self.context.students rescue [] }
|
|
|
|
p.whenever {|record|
|
|
|
|
record.just_created && !record.context.is_a?(Course)
|
|
|
|
}
|
|
|
|
end
|
|
|
|
|
2013-03-21 03:38:19 +08:00
|
|
|
scope :bookmarked, where(:bookmarked => true)
|
|
|
|
scope :for_purpose, lambda { |purpose| where(:purpose => purpose) }
|
|
|
|
scope :for_grading, where(:purpose => 'grading')
|
|
|
|
scope :for_context_codes, lambda { |codes| where(:context_code => codes) }
|
|
|
|
scope :include_rubric, includes(:rubric)
|
|
|
|
scope :before, lambda { |date| where("rubric_associations.created_at<?", date) }
|
|
|
|
|
2011-02-01 09:57:29 +08:00
|
|
|
def assert_uniqueness
|
|
|
|
if purpose == 'grading'
|
|
|
|
RubricAssociation.find_all_by_association_id_and_association_type_and_purpose(association_id, association_type, 'grading').each do |ra|
|
|
|
|
ra.destroy unless ra == self
|
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
learning outcomes refactor
This list is *NOT* complete, some items may have snuck in that I forgot
to note, and/or some of the noted items may not be completely functional
yet.
Specs need to be written around a lot of this, other specs will no doubt
need to be fixed.
Some things, particularly around LearningOutcomeGroups will need data
migrations that aren't there yet.
* remove LearningOutcome.non_rubric_outcomes? and replace with false
where invoked
* remove LearningOutcome.enabled? and replace with true where invoked
* remove never-taken branches
* remove the shared/aligned_outcomes partial and it's supporting
javascript, since it's now empty
* remove js handler for add_outcome_alignment_link and supporting
method since it only occurred in never-taken branches
* mix LearningOutcomeContext into Course and Account
* replace LearningOutcomeGroup.default_for(context) with
LearningOutcomeContext#root_outcome_group
* rename LearningOutcome#content_tags to LearningOutcome#alignments
* rename LearningOutcomeGroup#content_tags to
LearningOutcomeGroup#child_links, and properly restrict
* remove ContentTag[Alignment]#rubric_association_id, add
ContentTag[Alignment]#has_rubric_association? that looks at the
presence of the content's rubric_association_id
* condition off the assignment having a rubric_association rather than
filtering tags by has_rubric_association (which just looks back at
the assignment). all or none of the assignment's alignments are
forced to have the association (via the assignment). this was true in
practice before, is now codified (and more efficient)
* rename AssessmentQuestionBank#learning_outcome_tags to
AssessmentQuestionBank#learning_outcome_alignments
* rename Assignment#learning_outcome_tags to
Assignment#learning_outcome_alignments
* rename Rubric#learning_outcome_tags to
Rubric#learning_outcome_alignments
* move/rename (Course|Account)#learning_outcome_tags to
LearningOutcomeContext#learning_outcome_links
* move/rename Account#learning_outcomes (corrected) and
Course#learning_outcomes to
LearningOutcomeContext#linked_learning_outcomes
* move/rename Account#created_learning_outcomes and
Course#created_learning_outcomes to
LearningOutcomeContext#created_learning_outcomes
* clarify and correct usage of linked_learning_outcomes vs.
created_learning_outcomes
* move/rename (Account|Account)#learning_outcome_groups to
LearningOutcomeContext#learning_outcome_groups
* remove unused Account#associated_learning_outcomes
* just remove one link to a learning outcome when deleting
* merge Account#has_outcomes?, Course#has_outcomes? and
Course#has_outcomes into LearningOutcomeContext#has_outcomes?, add a
use in Context#active_record_types
* kill LearningOutcomeGroup#root_learning_outcome_group (unused)
* rename LearningOutcomeResult#content_tag to
LearningOutcomeResult#alignment
* kill unused (and broken) OutcomesController#add_outcome_group
* kill unused OutcomesController#update_outcomes_for_asset
* kill unused OutcomesController#outcomes_for_asset
* remove unused (outside specs, correct specs)
AssessmentQuestionBank#outcomes=
* remove unused ContentTag#learning_outcome_content
* replace ContentTag.learning_outcome_tags_for(asset) (only ever called
with asset=an assignment) with call to
Assignment#learning_outcome_alignments
* remove unused ContentTag.not_rubric
* remove (now) unused ContentTag.include_outcome
* remove unused LearningOutcome#learning_outcome_group_associations
* avoid explicit use of ContentTag in outcome-related specs
* replace LearningOutcomeGroup#learning_outcome_tags with
LearningOutcomeGroup#child_outcome_links (and only use for outcome
links; not tags for child groups)
* split ContentTag#create_outcome_result into
Submission#create_outcome_result,
QuizSubmission#create_outcome_result, and
RubricAssessment#create_outcome_result. fix some bugs along the way
* refactor ContentTag.outcome_tags_for_banks and some code from
QuizSubmission#(track_outcomes|update_outcomes_for_assessment_questions)
into QuizSubmission#questions_and_alignments
* refactor RubricAssociation#update_outcome_relations and
Rubric#update_alignments into LearningOutcome.update_alignments
* don't use ContentTag#rubric_association with outcome alignments; use
the tag's content's rubric_association in its place (they should have
been equal anyways)
* refactor LearningOutcome.available_in_context and
@context.root_outcome_group.sorted_all_outcomes (only time
sorted_all_outcomes is used) into
LearningOutcomeContext#available_outcomes and
LearningOutcomeContext#available_outcome
* overhaul LearningOutcomeGroup#sorted_content and rename to
LearningOutcomeGroup#sorted_children. it not returns ContentTags
(outcome links) and LearningOutcomeGroups, vs. LearningOutcomes and
LearningOutcomeGroups; fix usages appropriately
* fix UI for arranging/deleting outcome links and groups within a group
to refer to the outcome link rather than the outcome
Change-Id: I85d99f2634f7206332cb1f5d5ea575b428988d4b
Reviewed-on: https://gerrit.instructure.com/12590
Reviewed-by: Jacob Fugal <jacob@instructure.com>
Tested-by: Jacob Fugal <jacob@instructure.com>
2012-07-13 01:16:13 +08:00
|
|
|
def assignment
|
2014-01-23 01:54:27 +08:00
|
|
|
if self.association_object.is_a?(Assignment)
|
|
|
|
self.association_object
|
learning outcomes refactor
This list is *NOT* complete, some items may have snuck in that I forgot
to note, and/or some of the noted items may not be completely functional
yet.
Specs need to be written around a lot of this, other specs will no doubt
need to be fixed.
Some things, particularly around LearningOutcomeGroups will need data
migrations that aren't there yet.
* remove LearningOutcome.non_rubric_outcomes? and replace with false
where invoked
* remove LearningOutcome.enabled? and replace with true where invoked
* remove never-taken branches
* remove the shared/aligned_outcomes partial and it's supporting
javascript, since it's now empty
* remove js handler for add_outcome_alignment_link and supporting
method since it only occurred in never-taken branches
* mix LearningOutcomeContext into Course and Account
* replace LearningOutcomeGroup.default_for(context) with
LearningOutcomeContext#root_outcome_group
* rename LearningOutcome#content_tags to LearningOutcome#alignments
* rename LearningOutcomeGroup#content_tags to
LearningOutcomeGroup#child_links, and properly restrict
* remove ContentTag[Alignment]#rubric_association_id, add
ContentTag[Alignment]#has_rubric_association? that looks at the
presence of the content's rubric_association_id
* condition off the assignment having a rubric_association rather than
filtering tags by has_rubric_association (which just looks back at
the assignment). all or none of the assignment's alignments are
forced to have the association (via the assignment). this was true in
practice before, is now codified (and more efficient)
* rename AssessmentQuestionBank#learning_outcome_tags to
AssessmentQuestionBank#learning_outcome_alignments
* rename Assignment#learning_outcome_tags to
Assignment#learning_outcome_alignments
* rename Rubric#learning_outcome_tags to
Rubric#learning_outcome_alignments
* move/rename (Course|Account)#learning_outcome_tags to
LearningOutcomeContext#learning_outcome_links
* move/rename Account#learning_outcomes (corrected) and
Course#learning_outcomes to
LearningOutcomeContext#linked_learning_outcomes
* move/rename Account#created_learning_outcomes and
Course#created_learning_outcomes to
LearningOutcomeContext#created_learning_outcomes
* clarify and correct usage of linked_learning_outcomes vs.
created_learning_outcomes
* move/rename (Account|Account)#learning_outcome_groups to
LearningOutcomeContext#learning_outcome_groups
* remove unused Account#associated_learning_outcomes
* just remove one link to a learning outcome when deleting
* merge Account#has_outcomes?, Course#has_outcomes? and
Course#has_outcomes into LearningOutcomeContext#has_outcomes?, add a
use in Context#active_record_types
* kill LearningOutcomeGroup#root_learning_outcome_group (unused)
* rename LearningOutcomeResult#content_tag to
LearningOutcomeResult#alignment
* kill unused (and broken) OutcomesController#add_outcome_group
* kill unused OutcomesController#update_outcomes_for_asset
* kill unused OutcomesController#outcomes_for_asset
* remove unused (outside specs, correct specs)
AssessmentQuestionBank#outcomes=
* remove unused ContentTag#learning_outcome_content
* replace ContentTag.learning_outcome_tags_for(asset) (only ever called
with asset=an assignment) with call to
Assignment#learning_outcome_alignments
* remove unused ContentTag.not_rubric
* remove (now) unused ContentTag.include_outcome
* remove unused LearningOutcome#learning_outcome_group_associations
* avoid explicit use of ContentTag in outcome-related specs
* replace LearningOutcomeGroup#learning_outcome_tags with
LearningOutcomeGroup#child_outcome_links (and only use for outcome
links; not tags for child groups)
* split ContentTag#create_outcome_result into
Submission#create_outcome_result,
QuizSubmission#create_outcome_result, and
RubricAssessment#create_outcome_result. fix some bugs along the way
* refactor ContentTag.outcome_tags_for_banks and some code from
QuizSubmission#(track_outcomes|update_outcomes_for_assessment_questions)
into QuizSubmission#questions_and_alignments
* refactor RubricAssociation#update_outcome_relations and
Rubric#update_alignments into LearningOutcome.update_alignments
* don't use ContentTag#rubric_association with outcome alignments; use
the tag's content's rubric_association in its place (they should have
been equal anyways)
* refactor LearningOutcome.available_in_context and
@context.root_outcome_group.sorted_all_outcomes (only time
sorted_all_outcomes is used) into
LearningOutcomeContext#available_outcomes and
LearningOutcomeContext#available_outcome
* overhaul LearningOutcomeGroup#sorted_content and rename to
LearningOutcomeGroup#sorted_children. it not returns ContentTags
(outcome links) and LearningOutcomeGroups, vs. LearningOutcomes and
LearningOutcomeGroups; fix usages appropriately
* fix UI for arranging/deleting outcome links and groups within a group
to refer to the outcome link rather than the outcome
Change-Id: I85d99f2634f7206332cb1f5d5ea575b428988d4b
Reviewed-on: https://gerrit.instructure.com/12590
Reviewed-by: Jacob Fugal <jacob@instructure.com>
Tested-by: Jacob Fugal <jacob@instructure.com>
2012-07-13 01:16:13 +08:00
|
|
|
else
|
|
|
|
nil
|
2011-02-01 09:57:29 +08:00
|
|
|
end
|
|
|
|
end
|
learning outcomes refactor
This list is *NOT* complete, some items may have snuck in that I forgot
to note, and/or some of the noted items may not be completely functional
yet.
Specs need to be written around a lot of this, other specs will no doubt
need to be fixed.
Some things, particularly around LearningOutcomeGroups will need data
migrations that aren't there yet.
* remove LearningOutcome.non_rubric_outcomes? and replace with false
where invoked
* remove LearningOutcome.enabled? and replace with true where invoked
* remove never-taken branches
* remove the shared/aligned_outcomes partial and it's supporting
javascript, since it's now empty
* remove js handler for add_outcome_alignment_link and supporting
method since it only occurred in never-taken branches
* mix LearningOutcomeContext into Course and Account
* replace LearningOutcomeGroup.default_for(context) with
LearningOutcomeContext#root_outcome_group
* rename LearningOutcome#content_tags to LearningOutcome#alignments
* rename LearningOutcomeGroup#content_tags to
LearningOutcomeGroup#child_links, and properly restrict
* remove ContentTag[Alignment]#rubric_association_id, add
ContentTag[Alignment]#has_rubric_association? that looks at the
presence of the content's rubric_association_id
* condition off the assignment having a rubric_association rather than
filtering tags by has_rubric_association (which just looks back at
the assignment). all or none of the assignment's alignments are
forced to have the association (via the assignment). this was true in
practice before, is now codified (and more efficient)
* rename AssessmentQuestionBank#learning_outcome_tags to
AssessmentQuestionBank#learning_outcome_alignments
* rename Assignment#learning_outcome_tags to
Assignment#learning_outcome_alignments
* rename Rubric#learning_outcome_tags to
Rubric#learning_outcome_alignments
* move/rename (Course|Account)#learning_outcome_tags to
LearningOutcomeContext#learning_outcome_links
* move/rename Account#learning_outcomes (corrected) and
Course#learning_outcomes to
LearningOutcomeContext#linked_learning_outcomes
* move/rename Account#created_learning_outcomes and
Course#created_learning_outcomes to
LearningOutcomeContext#created_learning_outcomes
* clarify and correct usage of linked_learning_outcomes vs.
created_learning_outcomes
* move/rename (Account|Account)#learning_outcome_groups to
LearningOutcomeContext#learning_outcome_groups
* remove unused Account#associated_learning_outcomes
* just remove one link to a learning outcome when deleting
* merge Account#has_outcomes?, Course#has_outcomes? and
Course#has_outcomes into LearningOutcomeContext#has_outcomes?, add a
use in Context#active_record_types
* kill LearningOutcomeGroup#root_learning_outcome_group (unused)
* rename LearningOutcomeResult#content_tag to
LearningOutcomeResult#alignment
* kill unused (and broken) OutcomesController#add_outcome_group
* kill unused OutcomesController#update_outcomes_for_asset
* kill unused OutcomesController#outcomes_for_asset
* remove unused (outside specs, correct specs)
AssessmentQuestionBank#outcomes=
* remove unused ContentTag#learning_outcome_content
* replace ContentTag.learning_outcome_tags_for(asset) (only ever called
with asset=an assignment) with call to
Assignment#learning_outcome_alignments
* remove unused ContentTag.not_rubric
* remove (now) unused ContentTag.include_outcome
* remove unused LearningOutcome#learning_outcome_group_associations
* avoid explicit use of ContentTag in outcome-related specs
* replace LearningOutcomeGroup#learning_outcome_tags with
LearningOutcomeGroup#child_outcome_links (and only use for outcome
links; not tags for child groups)
* split ContentTag#create_outcome_result into
Submission#create_outcome_result,
QuizSubmission#create_outcome_result, and
RubricAssessment#create_outcome_result. fix some bugs along the way
* refactor ContentTag.outcome_tags_for_banks and some code from
QuizSubmission#(track_outcomes|update_outcomes_for_assessment_questions)
into QuizSubmission#questions_and_alignments
* refactor RubricAssociation#update_outcome_relations and
Rubric#update_alignments into LearningOutcome.update_alignments
* don't use ContentTag#rubric_association with outcome alignments; use
the tag's content's rubric_association in its place (they should have
been equal anyways)
* refactor LearningOutcome.available_in_context and
@context.root_outcome_group.sorted_all_outcomes (only time
sorted_all_outcomes is used) into
LearningOutcomeContext#available_outcomes and
LearningOutcomeContext#available_outcome
* overhaul LearningOutcomeGroup#sorted_content and rename to
LearningOutcomeGroup#sorted_children. it not returns ContentTags
(outcome links) and LearningOutcomeGroups, vs. LearningOutcomes and
LearningOutcomeGroups; fix usages appropriately
* fix UI for arranging/deleting outcome links and groups within a group
to refer to the outcome link rather than the outcome
Change-Id: I85d99f2634f7206332cb1f5d5ea575b428988d4b
Reviewed-on: https://gerrit.instructure.com/12590
Reviewed-by: Jacob Fugal <jacob@instructure.com>
Tested-by: Jacob Fugal <jacob@instructure.com>
2012-07-13 01:16:13 +08:00
|
|
|
|
correctly maintain assignment/rubric <-> outcome links
There are a few old LearningOutcomeResults that have a nil artifact, and
many that have a Submission as an artifact. We want to get rid of these
because they come from bad data, and step 1 toward that goal is to stop
creating them and hide them in the UI.
The LORs with a nil artifact are very old and I believe came from a very
early incarnation of outcomes. The LORs with a Submission as an artifact
came from a combination of two code problems. The first was old code
that allowed an assignment that was aligned with an outcome but did not
have a rubric to create LORs directly based on it's submission. The
second was a bug that prevented the assignment <-> outcome link from
being destroyed when a rubric with an outcome was removed from an
assignment.
fixes CNVS-7495
fixes CNVS-7498
test plan:
- try different combinations of adding a rubric with an outcome to an
assignment.
- when you grade the assignment, the grade create a learning outcome result
(which can be seen on the outcome show page, or in the account outcome
report) if the rubric+outcome are currently attached to the assignment.
- so for example, add a rubric with an outcome, check, remove just the outcome
row, check, add a new outcome row, check, remove the whole rubric, check.
- be sure to check both the show page and the outcome report
TODO:
- datafix migration
Change-Id: I37700e3e5c08fc6cfb8fcf1cac42ea6693fcaba3
Reviewed-on: https://gerrit.instructure.com/23303
Tested-by: Jenkins <jenkins@instructure.com>
Reviewed-by: Cameron Matheson <cameron@instructure.com>
QA-Review: Amber Taniuchi <amber@instructure.com>
Product-Review: Simon Williams <simon@instructure.com>
2013-08-14 07:15:15 +08:00
|
|
|
def update_alignments
|
learning outcomes refactor
This list is *NOT* complete, some items may have snuck in that I forgot
to note, and/or some of the noted items may not be completely functional
yet.
Specs need to be written around a lot of this, other specs will no doubt
need to be fixed.
Some things, particularly around LearningOutcomeGroups will need data
migrations that aren't there yet.
* remove LearningOutcome.non_rubric_outcomes? and replace with false
where invoked
* remove LearningOutcome.enabled? and replace with true where invoked
* remove never-taken branches
* remove the shared/aligned_outcomes partial and it's supporting
javascript, since it's now empty
* remove js handler for add_outcome_alignment_link and supporting
method since it only occurred in never-taken branches
* mix LearningOutcomeContext into Course and Account
* replace LearningOutcomeGroup.default_for(context) with
LearningOutcomeContext#root_outcome_group
* rename LearningOutcome#content_tags to LearningOutcome#alignments
* rename LearningOutcomeGroup#content_tags to
LearningOutcomeGroup#child_links, and properly restrict
* remove ContentTag[Alignment]#rubric_association_id, add
ContentTag[Alignment]#has_rubric_association? that looks at the
presence of the content's rubric_association_id
* condition off the assignment having a rubric_association rather than
filtering tags by has_rubric_association (which just looks back at
the assignment). all or none of the assignment's alignments are
forced to have the association (via the assignment). this was true in
practice before, is now codified (and more efficient)
* rename AssessmentQuestionBank#learning_outcome_tags to
AssessmentQuestionBank#learning_outcome_alignments
* rename Assignment#learning_outcome_tags to
Assignment#learning_outcome_alignments
* rename Rubric#learning_outcome_tags to
Rubric#learning_outcome_alignments
* move/rename (Course|Account)#learning_outcome_tags to
LearningOutcomeContext#learning_outcome_links
* move/rename Account#learning_outcomes (corrected) and
Course#learning_outcomes to
LearningOutcomeContext#linked_learning_outcomes
* move/rename Account#created_learning_outcomes and
Course#created_learning_outcomes to
LearningOutcomeContext#created_learning_outcomes
* clarify and correct usage of linked_learning_outcomes vs.
created_learning_outcomes
* move/rename (Account|Account)#learning_outcome_groups to
LearningOutcomeContext#learning_outcome_groups
* remove unused Account#associated_learning_outcomes
* just remove one link to a learning outcome when deleting
* merge Account#has_outcomes?, Course#has_outcomes? and
Course#has_outcomes into LearningOutcomeContext#has_outcomes?, add a
use in Context#active_record_types
* kill LearningOutcomeGroup#root_learning_outcome_group (unused)
* rename LearningOutcomeResult#content_tag to
LearningOutcomeResult#alignment
* kill unused (and broken) OutcomesController#add_outcome_group
* kill unused OutcomesController#update_outcomes_for_asset
* kill unused OutcomesController#outcomes_for_asset
* remove unused (outside specs, correct specs)
AssessmentQuestionBank#outcomes=
* remove unused ContentTag#learning_outcome_content
* replace ContentTag.learning_outcome_tags_for(asset) (only ever called
with asset=an assignment) with call to
Assignment#learning_outcome_alignments
* remove unused ContentTag.not_rubric
* remove (now) unused ContentTag.include_outcome
* remove unused LearningOutcome#learning_outcome_group_associations
* avoid explicit use of ContentTag in outcome-related specs
* replace LearningOutcomeGroup#learning_outcome_tags with
LearningOutcomeGroup#child_outcome_links (and only use for outcome
links; not tags for child groups)
* split ContentTag#create_outcome_result into
Submission#create_outcome_result,
QuizSubmission#create_outcome_result, and
RubricAssessment#create_outcome_result. fix some bugs along the way
* refactor ContentTag.outcome_tags_for_banks and some code from
QuizSubmission#(track_outcomes|update_outcomes_for_assessment_questions)
into QuizSubmission#questions_and_alignments
* refactor RubricAssociation#update_outcome_relations and
Rubric#update_alignments into LearningOutcome.update_alignments
* don't use ContentTag#rubric_association with outcome alignments; use
the tag's content's rubric_association in its place (they should have
been equal anyways)
* refactor LearningOutcome.available_in_context and
@context.root_outcome_group.sorted_all_outcomes (only time
sorted_all_outcomes is used) into
LearningOutcomeContext#available_outcomes and
LearningOutcomeContext#available_outcome
* overhaul LearningOutcomeGroup#sorted_content and rename to
LearningOutcomeGroup#sorted_children. it not returns ContentTags
(outcome links) and LearningOutcomeGroups, vs. LearningOutcomes and
LearningOutcomeGroups; fix usages appropriately
* fix UI for arranging/deleting outcome links and groups within a group
to refer to the outcome link rather than the outcome
Change-Id: I85d99f2634f7206332cb1f5d5ea575b428988d4b
Reviewed-on: https://gerrit.instructure.com/12590
Reviewed-by: Jacob Fugal <jacob@instructure.com>
Tested-by: Jacob Fugal <jacob@instructure.com>
2012-07-13 01:16:13 +08:00
|
|
|
return unless assignment
|
correctly maintain assignment/rubric <-> outcome links
There are a few old LearningOutcomeResults that have a nil artifact, and
many that have a Submission as an artifact. We want to get rid of these
because they come from bad data, and step 1 toward that goal is to stop
creating them and hide them in the UI.
The LORs with a nil artifact are very old and I believe came from a very
early incarnation of outcomes. The LORs with a Submission as an artifact
came from a combination of two code problems. The first was old code
that allowed an assignment that was aligned with an outcome but did not
have a rubric to create LORs directly based on it's submission. The
second was a bug that prevented the assignment <-> outcome link from
being destroyed when a rubric with an outcome was removed from an
assignment.
fixes CNVS-7495
fixes CNVS-7498
test plan:
- try different combinations of adding a rubric with an outcome to an
assignment.
- when you grade the assignment, the grade create a learning outcome result
(which can be seen on the outcome show page, or in the account outcome
report) if the rubric+outcome are currently attached to the assignment.
- so for example, add a rubric with an outcome, check, remove just the outcome
row, check, add a new outcome row, check, remove the whole rubric, check.
- be sure to check both the show page and the outcome report
TODO:
- datafix migration
Change-Id: I37700e3e5c08fc6cfb8fcf1cac42ea6693fcaba3
Reviewed-on: https://gerrit.instructure.com/23303
Tested-by: Jenkins <jenkins@instructure.com>
Reviewed-by: Cameron Matheson <cameron@instructure.com>
QA-Review: Amber Taniuchi <amber@instructure.com>
Product-Review: Simon Williams <simon@instructure.com>
2013-08-14 07:15:15 +08:00
|
|
|
outcome_ids = []
|
|
|
|
unless self.destroyed?
|
|
|
|
outcome_ids = rubric.learning_outcome_alignments.map(&:learning_outcome_id)
|
|
|
|
end
|
learning outcomes refactor
This list is *NOT* complete, some items may have snuck in that I forgot
to note, and/or some of the noted items may not be completely functional
yet.
Specs need to be written around a lot of this, other specs will no doubt
need to be fixed.
Some things, particularly around LearningOutcomeGroups will need data
migrations that aren't there yet.
* remove LearningOutcome.non_rubric_outcomes? and replace with false
where invoked
* remove LearningOutcome.enabled? and replace with true where invoked
* remove never-taken branches
* remove the shared/aligned_outcomes partial and it's supporting
javascript, since it's now empty
* remove js handler for add_outcome_alignment_link and supporting
method since it only occurred in never-taken branches
* mix LearningOutcomeContext into Course and Account
* replace LearningOutcomeGroup.default_for(context) with
LearningOutcomeContext#root_outcome_group
* rename LearningOutcome#content_tags to LearningOutcome#alignments
* rename LearningOutcomeGroup#content_tags to
LearningOutcomeGroup#child_links, and properly restrict
* remove ContentTag[Alignment]#rubric_association_id, add
ContentTag[Alignment]#has_rubric_association? that looks at the
presence of the content's rubric_association_id
* condition off the assignment having a rubric_association rather than
filtering tags by has_rubric_association (which just looks back at
the assignment). all or none of the assignment's alignments are
forced to have the association (via the assignment). this was true in
practice before, is now codified (and more efficient)
* rename AssessmentQuestionBank#learning_outcome_tags to
AssessmentQuestionBank#learning_outcome_alignments
* rename Assignment#learning_outcome_tags to
Assignment#learning_outcome_alignments
* rename Rubric#learning_outcome_tags to
Rubric#learning_outcome_alignments
* move/rename (Course|Account)#learning_outcome_tags to
LearningOutcomeContext#learning_outcome_links
* move/rename Account#learning_outcomes (corrected) and
Course#learning_outcomes to
LearningOutcomeContext#linked_learning_outcomes
* move/rename Account#created_learning_outcomes and
Course#created_learning_outcomes to
LearningOutcomeContext#created_learning_outcomes
* clarify and correct usage of linked_learning_outcomes vs.
created_learning_outcomes
* move/rename (Account|Account)#learning_outcome_groups to
LearningOutcomeContext#learning_outcome_groups
* remove unused Account#associated_learning_outcomes
* just remove one link to a learning outcome when deleting
* merge Account#has_outcomes?, Course#has_outcomes? and
Course#has_outcomes into LearningOutcomeContext#has_outcomes?, add a
use in Context#active_record_types
* kill LearningOutcomeGroup#root_learning_outcome_group (unused)
* rename LearningOutcomeResult#content_tag to
LearningOutcomeResult#alignment
* kill unused (and broken) OutcomesController#add_outcome_group
* kill unused OutcomesController#update_outcomes_for_asset
* kill unused OutcomesController#outcomes_for_asset
* remove unused (outside specs, correct specs)
AssessmentQuestionBank#outcomes=
* remove unused ContentTag#learning_outcome_content
* replace ContentTag.learning_outcome_tags_for(asset) (only ever called
with asset=an assignment) with call to
Assignment#learning_outcome_alignments
* remove unused ContentTag.not_rubric
* remove (now) unused ContentTag.include_outcome
* remove unused LearningOutcome#learning_outcome_group_associations
* avoid explicit use of ContentTag in outcome-related specs
* replace LearningOutcomeGroup#learning_outcome_tags with
LearningOutcomeGroup#child_outcome_links (and only use for outcome
links; not tags for child groups)
* split ContentTag#create_outcome_result into
Submission#create_outcome_result,
QuizSubmission#create_outcome_result, and
RubricAssessment#create_outcome_result. fix some bugs along the way
* refactor ContentTag.outcome_tags_for_banks and some code from
QuizSubmission#(track_outcomes|update_outcomes_for_assessment_questions)
into QuizSubmission#questions_and_alignments
* refactor RubricAssociation#update_outcome_relations and
Rubric#update_alignments into LearningOutcome.update_alignments
* don't use ContentTag#rubric_association with outcome alignments; use
the tag's content's rubric_association in its place (they should have
been equal anyways)
* refactor LearningOutcome.available_in_context and
@context.root_outcome_group.sorted_all_outcomes (only time
sorted_all_outcomes is used) into
LearningOutcomeContext#available_outcomes and
LearningOutcomeContext#available_outcome
* overhaul LearningOutcomeGroup#sorted_content and rename to
LearningOutcomeGroup#sorted_children. it not returns ContentTags
(outcome links) and LearningOutcomeGroups, vs. LearningOutcomes and
LearningOutcomeGroups; fix usages appropriately
* fix UI for arranging/deleting outcome links and groups within a group
to refer to the outcome link rather than the outcome
Change-Id: I85d99f2634f7206332cb1f5d5ea575b428988d4b
Reviewed-on: https://gerrit.instructure.com/12590
Reviewed-by: Jacob Fugal <jacob@instructure.com>
Tested-by: Jacob Fugal <jacob@instructure.com>
2012-07-13 01:16:13 +08:00
|
|
|
LearningOutcome.update_alignments(assignment, context, outcome_ids)
|
|
|
|
true
|
|
|
|
end
|
2011-02-01 09:57:29 +08:00
|
|
|
|
|
|
|
def update_old_rubric
|
|
|
|
if self.rubric_id_changed? && self.rubric_id_was && self.rubric_id_was != self.rubric_id
|
|
|
|
rubric = Rubric.find(self.rubric_id_was)
|
|
|
|
rubric.destroy if rubric.rubric_associations.count == 0 && rubric.rubric_assessments.count == 0
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
|
|
|
def context_name
|
|
|
|
@cached_context_name ||= Rails.cache.fetch(['short_name_lookup', self.context_code].cache_key) do
|
|
|
|
self.context.short_name rescue ""
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
|
|
|
def update_values
|
2011-03-04 08:23:40 +08:00
|
|
|
self.bookmarked = true if self.purpose == 'bookmark' || self.bookmarked.nil?
|
2011-02-01 09:57:29 +08:00
|
|
|
self.context_code ||= "#{self.context_type.underscore}_#{self.context_id}" rescue nil
|
2014-01-23 01:54:27 +08:00
|
|
|
self.title ||= (self.association_object.title rescue self.association_object.name) rescue nil
|
2011-02-01 09:57:29 +08:00
|
|
|
end
|
|
|
|
protected :update_values
|
|
|
|
|
|
|
|
attr_accessor :assessing_user_id
|
2012-05-01 05:57:13 +08:00
|
|
|
|
2011-02-01 09:57:29 +08:00
|
|
|
set_policy do
|
|
|
|
given {|user, session| self.cached_context_grants_right?(user, session, :manage) }
|
2011-07-14 00:24:17 +08:00
|
|
|
can :update and can :delete and can :manage and can :assess
|
2011-02-01 09:57:29 +08:00
|
|
|
|
|
|
|
given {|user, session| user && @assessing_user_id && self.assessment_requests.for_assessee(@assessing_user_id).map{|r| r.assessor_id}.include?(user.id) }
|
2011-07-14 00:24:17 +08:00
|
|
|
can :assess
|
2011-02-01 09:57:29 +08:00
|
|
|
|
|
|
|
given {|user, session| self.cached_context_grants_right?(user, session, :participate_as_student) }
|
2011-07-14 00:24:17 +08:00
|
|
|
can :submit
|
2011-02-01 09:57:29 +08:00
|
|
|
end
|
|
|
|
|
|
|
|
def update_assignment_points
|
2014-01-23 01:54:27 +08:00
|
|
|
if self.use_for_grading && !self.skip_updating_points_possible && self.association_object && self.association_object.respond_to?(:points_possible=) && self.rubric && self.rubric.points_possible && self.association_object.points_possible != self.rubric.points_possible
|
|
|
|
self.association_object.update_attribute(:points_possible, self.rubric.points_possible)
|
2011-02-01 09:57:29 +08:00
|
|
|
end
|
|
|
|
end
|
|
|
|
protected :update_assignment_points
|
clean up some rubric assessment requests stuff
refs CNVS-7414
first, start at RubricsController#assessments. there is no route for it,
so remove the action and it's view. The rubric_association partial was
only used from that view, so remove it as well. Then in
RubricAssessmentController and RubricAssociationsController #create,
note that nothing ever provides an invitations param, so remove that,
and cascade down to removing or simplifying a few other methods
(particularly RubricAssociation#invite_assessors, which created users
in a bad way, and RubricAssociation#invite_assessor, which never
assigned assessor_asset, which will shortly be non-null, and is
obviously never used cause that column is never null in production).
Finally, fix some specs to properly create rubric assessments since
the (bad) helper methods are now gone.
test plan:
* specs
* basic regression test around using rubrics for grading and
peer reviews
Change-Id: Ibd7713d9fc1f847d49c47b95d8c51ce28fa41e92
Reviewed-on: https://gerrit.instructure.com/23412
Tested-by: Jenkins <jenkins@instructure.com>
QA-Review: Clare Strong <clare@instructure.com>
Reviewed-by: Simon Williams <simon@instructure.com>
Product-Review: Cody Cutrer <cody@instructure.com>
2013-08-17 01:42:29 +08:00
|
|
|
|
2011-02-01 09:57:29 +08:00
|
|
|
def remind_user(assessee)
|
2011-05-14 00:49:23 +08:00
|
|
|
assessment_request = self.assessment_requests.find_by_user_id(assessee.id)
|
|
|
|
assessment_request ||= self.assessment_requests.build(:user => assessee)
|
2011-02-01 09:57:29 +08:00
|
|
|
assessment_request.send_reminder! if assessment_request.assigned?
|
|
|
|
assessment_request
|
|
|
|
end
|
|
|
|
|
|
|
|
def update_rubric
|
|
|
|
cnt = self.rubric.rubric_associations.for_grading.length rescue 0
|
|
|
|
if self.rubric
|
|
|
|
self.rubric.with_versioning(false) do
|
|
|
|
self.rubric.read_only = cnt > 1
|
|
|
|
self.rubric.association_count = cnt
|
|
|
|
self.rubric.save
|
|
|
|
|
|
|
|
self.rubric.destroy if cnt == 0 && self.rubric.rubric_associations.count == 0 && !self.rubric.public
|
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|
|
|
|
protected :update_rubric
|
2012-05-01 05:57:13 +08:00
|
|
|
|
|
|
|
# Link the rubric association to any existing assessment_requests (i.e. peer-reviews) that haven't been completed and
|
|
|
|
# aren't currently linked to a rubric association. This routine is needed when an assignment is completed and
|
|
|
|
# submissions were already sent when peer-review links and a *then* a rubric is created.
|
|
|
|
def link_to_assessments
|
|
|
|
# Go up to the assignment and loop through all submissions.
|
|
|
|
# Update each submission's assessment_requests with a link to this rubric association
|
|
|
|
# but only if not already associated and the assessment is incomplete.
|
2013-12-24 04:38:31 +08:00
|
|
|
if self.association_id && self.association_type == 'Assignment'
|
2014-01-23 01:54:27 +08:00
|
|
|
self.association_object.submissions.each do |sub|
|
2013-03-19 03:07:47 +08:00
|
|
|
sub.assessment_requests.incomplete.where(:rubric_association_id => nil).
|
|
|
|
update_all(:rubric_association_id => self)
|
2012-05-01 05:57:13 +08:00
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|
|
|
|
protected :link_to_assessments
|
|
|
|
|
2011-02-01 09:57:29 +08:00
|
|
|
def unsubmitted_users
|
|
|
|
self.context.students - self.rubric_assessments.map{|a| a.user} - self.assessment_requests.map{|a| a.user}
|
|
|
|
end
|
|
|
|
|
clean up some rubric assessment requests stuff
refs CNVS-7414
first, start at RubricsController#assessments. there is no route for it,
so remove the action and it's view. The rubric_association partial was
only used from that view, so remove it as well. Then in
RubricAssessmentController and RubricAssociationsController #create,
note that nothing ever provides an invitations param, so remove that,
and cascade down to removing or simplifying a few other methods
(particularly RubricAssociation#invite_assessors, which created users
in a bad way, and RubricAssociation#invite_assessor, which never
assigned assessor_asset, which will shortly be non-null, and is
obviously never used cause that column is never null in production).
Finally, fix some specs to properly create rubric assessments since
the (bad) helper methods are now gone.
test plan:
* specs
* basic regression test around using rubrics for grading and
peer reviews
Change-Id: Ibd7713d9fc1f847d49c47b95d8c51ce28fa41e92
Reviewed-on: https://gerrit.instructure.com/23412
Tested-by: Jenkins <jenkins@instructure.com>
QA-Review: Clare Strong <clare@instructure.com>
Reviewed-by: Simon Williams <simon@instructure.com>
Product-Review: Cody Cutrer <cody@instructure.com>
2013-08-17 01:42:29 +08:00
|
|
|
def self.generate(current_user, rubric, context, params)
|
2011-02-01 09:57:29 +08:00
|
|
|
raise "context required" unless context
|
2014-01-23 01:54:27 +08:00
|
|
|
association_object = params.delete :association_object
|
2011-04-27 11:55:24 +08:00
|
|
|
if (association_id = params.delete(:id)) && association_id.present?
|
|
|
|
association = RubricAssociation.find_by_id(association_id)
|
|
|
|
end
|
2014-01-23 01:54:27 +08:00
|
|
|
association = nil unless association && association.context == context && association.association_object == association_object
|
2011-02-01 09:57:29 +08:00
|
|
|
raise "association required" unless association || association_object
|
|
|
|
# Update/create the association -- this is what ties the rubric to an entity
|
|
|
|
update_if_existing = params.delete(:update_if_existing)
|
|
|
|
association ||= rubric.associate_with(association_object, context, :use_for_grading => params[:use_for_grading] == "1", :purpose => params[:purpose], :update_if_existing => update_if_existing)
|
|
|
|
association.rubric = rubric
|
|
|
|
association.context = context
|
2011-11-11 00:44:12 +08:00
|
|
|
association.skip_updating_points_possible = params.delete :skip_updating_points_possible
|
2011-02-01 09:57:29 +08:00
|
|
|
association.update_attributes(params)
|
2014-01-23 01:54:27 +08:00
|
|
|
association.association_object = association_object
|
2011-02-01 09:57:29 +08:00
|
|
|
association
|
|
|
|
end
|
|
|
|
|
|
|
|
def assessments_unique_per_asset?(assessment_type)
|
2014-01-23 01:54:27 +08:00
|
|
|
self.association_object.is_a?(Assignment) && self.purpose == "grading" && assessment_type == "grading"
|
2011-02-01 09:57:29 +08:00
|
|
|
end
|
|
|
|
|
|
|
|
def assess(opts={})
|
|
|
|
# TODO: what if this is for a group assignment? Seems like it should
|
|
|
|
# give all students for the group assignment the same rubric assessment
|
|
|
|
# results.
|
|
|
|
association = self
|
|
|
|
params = opts[:assessment]
|
|
|
|
raise "User required for assessing" unless opts[:user]
|
|
|
|
raise "Assessor required for assessing" unless opts[:assessor]
|
|
|
|
raise "Artifact required for assessing" unless opts[:artifact]
|
|
|
|
raise "Assessment type required for assessing" unless params[:assessment_type]
|
|
|
|
|
2014-01-23 01:54:27 +08:00
|
|
|
if self.association_object.is_a?(Assignment) && !self.association_object.grade_group_students_individually
|
|
|
|
students_to_assess = self.association_object.group_students(opts[:artifact].user).last
|
2011-02-01 09:57:29 +08:00
|
|
|
artifacts_to_assess = students_to_assess.map do |student|
|
2014-01-23 01:54:27 +08:00
|
|
|
self.association_object.find_asset_for_assessment(self, student).first
|
2011-02-01 09:57:29 +08:00
|
|
|
end
|
|
|
|
else
|
|
|
|
artifacts_to_assess = [opts[:artifact]]
|
|
|
|
end
|
|
|
|
|
|
|
|
ratings = []
|
|
|
|
score = 0
|
|
|
|
replace_ratings = false
|
|
|
|
self.rubric.criteria_object.each do |criterion|
|
|
|
|
data = params["criterion_#{criterion.id}".to_sym]
|
|
|
|
rating = {}
|
|
|
|
if data
|
|
|
|
replace_ratings = true
|
|
|
|
rating[:points] = [criterion.points, data[:points].to_f].min || 0
|
|
|
|
rating[:criterion_id] = criterion.id
|
|
|
|
rating[:learning_outcome_id] = criterion.learning_outcome_id
|
2012-01-25 05:22:14 +08:00
|
|
|
if criterion.ignore_for_scoring
|
|
|
|
rating[:ignore_for_scoring] = true
|
|
|
|
else
|
|
|
|
score += rating[:points]
|
|
|
|
end
|
2011-02-01 09:57:29 +08:00
|
|
|
rating[:description] = data[:description]
|
|
|
|
rating[:comments_enabled] = true
|
|
|
|
rating[:comments] = data[:comments]
|
|
|
|
rating[:above_threshold] = rating[:points] > criterion.mastery_points if criterion.mastery_points && rating[:points]
|
|
|
|
cached_description = nil
|
|
|
|
criterion.ratings.each do |r|
|
|
|
|
if r.points.to_f == rating[:points].to_f
|
|
|
|
cached_description = r.description
|
|
|
|
rating[:id] = r.id
|
|
|
|
end
|
|
|
|
end
|
|
|
|
if !rating[:description] || rating[:description].empty?
|
|
|
|
rating[:description] = cached_description
|
|
|
|
end
|
|
|
|
if rating[:comments] && !rating[:comments].empty? && data[:save_comment] == '1'
|
|
|
|
self.summary_data ||= {}
|
|
|
|
self.summary_data[:saved_comments] ||= {}
|
|
|
|
self.summary_data[:saved_comments][criterion.id.to_s] ||= []
|
|
|
|
self.summary_data[:saved_comments][criterion.id.to_s] << rating[:comments]
|
2011-07-01 04:36:59 +08:00
|
|
|
# TODO i18n
|
2011-02-01 09:57:29 +08:00
|
|
|
self.summary_data[:saved_comments][criterion.id.to_s] = self.summary_data[:saved_comments][criterion.id.to_s].select{|desc| desc && !desc.empty? && desc != "No Details"}.uniq.sort
|
|
|
|
self.save
|
|
|
|
end
|
2011-06-22 00:27:31 +08:00
|
|
|
rating[:description] = t('no_details', "No details") if !rating[:description] || rating[:description].empty?
|
2011-02-11 01:26:35 +08:00
|
|
|
ratings << rating
|
2011-02-01 09:57:29 +08:00
|
|
|
end
|
|
|
|
end
|
|
|
|
assessment_to_return = nil
|
|
|
|
artifacts_to_assess.each do |artifact|
|
|
|
|
assessment = nil
|
|
|
|
if assessments_unique_per_asset?(params[:assessment_type])
|
|
|
|
# Unless it's for grading, in which case assessments are unique per artifact (the assessor can change, depending on if the teacher/TA updates it)
|
|
|
|
assessment = association.rubric_assessments.find_by_artifact_id_and_artifact_type_and_assessment_type(artifact.id, artifact.class.to_s, params[:assessment_type])
|
|
|
|
else
|
|
|
|
# Assessments are unique per artifact/assessor/assessment_type.
|
|
|
|
assessment = association.rubric_assessments.find_by_artifact_id_and_artifact_type_and_assessor_id_and_assessment_type(artifact.id, artifact.class.to_s, opts[:assessor].id, params[:assessment_type])
|
|
|
|
end
|
|
|
|
assessment ||= association.rubric_assessments.build(:assessor => opts[:assessor], :artifact => artifact, :user => artifact.user, :rubric => self.rubric, :assessment_type => params[:assessment_type])
|
|
|
|
assessment.score = score if replace_ratings
|
|
|
|
assessment.data = ratings if replace_ratings
|
|
|
|
assessment.comments = params[:comments] if params[:comments]
|
|
|
|
|
|
|
|
assessment.save
|
|
|
|
assessment_to_return = assessment if assessment.artifact == opts[:artifact]
|
|
|
|
end
|
|
|
|
assessment_to_return
|
|
|
|
end
|
|
|
|
end
|