mumuki-domain 9.7.0 → 9.10.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (36) hide show
  1. checksums.yaml +4 -4
  2. data/app/models/application_record.rb +1 -1
  3. data/app/models/assignment.rb +8 -13
  4. data/app/models/concerns/onomastic.rb +37 -0
  5. data/app/models/concerns/with_messages.rb +1 -1
  6. data/app/models/concerns/with_reminders.rb +1 -1
  7. data/app/models/concerns/with_responsible_moderator.rb +1 -1
  8. data/app/models/concerns/with_soft_deletion.rb +1 -1
  9. data/app/models/concerns/with_terms_acceptance.rb +1 -2
  10. data/app/models/concerns/with_timed_enablement.rb +1 -1
  11. data/app/models/course.rb +2 -2
  12. data/app/models/discussion.rb +19 -5
  13. data/app/models/exam.rb +3 -3
  14. data/app/models/exam_authorization.rb +1 -1
  15. data/app/models/exam_registration.rb +1 -1
  16. data/app/models/exercise.rb +0 -8
  17. data/app/models/exercise/playground.rb +2 -1
  18. data/app/models/exercise/problem.rb +1 -1
  19. data/app/models/message.rb +42 -16
  20. data/app/models/organization.rb +1 -1
  21. data/app/models/user.rb +2 -13
  22. data/db/migrate/20210707143002_add_assignment_id_to_message.rb +5 -0
  23. data/lib/mumuki/domain/factories/exercise_factory.rb +9 -1
  24. data/lib/mumuki/domain/helpers/user.rb +0 -6
  25. data/lib/mumuki/domain/organization/profile.rb +1 -1
  26. data/lib/mumuki/domain/organization/settings.rb +2 -2
  27. data/lib/mumuki/domain/status/discussion/closed.rb +4 -0
  28. data/lib/mumuki/domain/status/discussion/opened.rb +4 -0
  29. data/lib/mumuki/domain/status/discussion/pending_review.rb +4 -0
  30. data/lib/mumuki/domain/status/discussion/solved.rb +4 -0
  31. data/lib/mumuki/domain/submission/persistent_submission.rb +1 -1
  32. data/lib/mumuki/domain/submission/query.rb +1 -1
  33. data/lib/mumuki/domain/submission/question.rb +0 -1
  34. data/lib/mumuki/domain/submission/try.rb +1 -0
  35. data/lib/mumuki/domain/version.rb +1 -1
  36. metadata +4 -2
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 5f0a85995ceefa3f9400d60e29b11c3907b1c42853c2d1517138bc7fa4532239
4
- data.tar.gz: d468a495d0c21ee1139b4087c7ce5653936d7b9289a5a06d2e7c338f443fe128
3
+ metadata.gz: 51a03f1d01bc567c0b91939577bd7fad54968380794122c8f93a6355b4d2fd87
4
+ data.tar.gz: e953f4fdca9d236bfef4e9ab6d9543fec286229b668cf071830d6c98f38bfa39
5
5
  SHA512:
6
- metadata.gz: f5ddf066cff9cf215e1ad83041b418cf615dcf3f5674b97cc569725d53f2107f2fc4c33b5d75fc3ae36e9a16694eeac90318062a65b3b1f1c003f97924359119
7
- data.tar.gz: 0200b8bf90e1e7c08797fd2f3c417b744be4c455ff40cff1063fd7f8bf9a28f143f7d272a85e765ef02b663f10957b1ee5fa647b32331ea953bb6b7d8cbf4e0c
6
+ metadata.gz: 46ef5320c51569aab17dda636d81fcba3cc27cbbf7e9f22f78c96a67b97aa1f7f3d25127c9cd7bded347a5764a91b970c1ec5809c84bb904930d61212cd81cda
7
+ data.tar.gz: c3ffff05f15964f1bac7ea31adc0e5c78e09ce7ccc47dee8f95347205b692aa93be2c0f79ed9162fbf27a664eb60e205eeaf7f078e5456b5356a2e73b4db7f2f
@@ -152,7 +152,7 @@ class ApplicationRecord < ActiveRecord::Base
152
152
  def self.active_between(start_date_field, end_date_field, **options)
153
153
  define_singleton_method(:active) do |actually_filter=true|
154
154
  if actually_filter
155
- self.where("(#{start_date_field} IS NULL OR #{start_date_field} < :now) AND (#{end_date_field} IS NULL OR #{end_date_field} > :now)", now: Time.now)
155
+ self.where("(#{start_date_field} IS NULL OR #{start_date_field} < :now) AND (#{end_date_field} IS NULL OR #{end_date_field} > :now)", now: Time.current)
156
156
  else
157
157
  all
158
158
  end
@@ -7,11 +7,7 @@ class Assignment < Progress
7
7
 
8
8
  belongs_to :exercise
9
9
  has_one :guide, through: :exercise
10
- has_many :messages,
11
- -> { where.not(submission_id: nil).order(date: :desc) },
12
- foreign_key: :submission_id,
13
- primary_key: :submission_id,
14
- dependent: :destroy
10
+ has_many :messages, -> { order(date: :desc) }, dependent: :destroy
15
11
 
16
12
  belongs_to :organization
17
13
  belongs_to :submitter, class_name: 'User'
@@ -28,13 +24,13 @@ class Assignment < Progress
28
24
  alias_attribute :status, :submission_status
29
25
  alias_attribute :attempts_count, :attemps_count
30
26
 
31
- scope :by_exercise_ids, -> (exercise_ids) {
27
+ scope :by_exercise_ids, -> (exercise_ids) do
32
28
  where(exercise_id: exercise_ids) if exercise_ids
33
- }
29
+ end
34
30
 
35
- scope :by_usernames, -> (usernames) {
31
+ scope :by_usernames, -> (usernames) do
36
32
  joins(:submitter).where('users.name' => usernames) if usernames
37
- }
33
+ end
38
34
 
39
35
  defaults do
40
36
  self.query_results = []
@@ -86,11 +82,10 @@ class Assignment < Progress
86
82
  end
87
83
  end
88
84
 
89
- def persist_submission!(submission)
85
+ def save_submission!(submission)
90
86
  transaction do
91
- messages.destroy_all if submission_id.present?
92
87
  update! submission_id: submission.id
93
- update! submitted_at: DateTime.current
88
+ update! submitted_at: Time.current
94
89
  update_submissions_count!
95
90
  update_last_submission!
96
91
  end
@@ -286,6 +281,6 @@ class Assignment < Progress
286
281
  end
287
282
 
288
283
  def update_last_submission!
289
- submitter.update!(last_submission_date: DateTime.current, last_exercise: exercise)
284
+ submitter.update!(last_submission_date: Time.current, last_exercise: exercise)
290
285
  end
291
286
  end
@@ -0,0 +1,37 @@
1
+ module Onomastic
2
+ extend ActiveSupport::Concern
3
+
4
+ included do
5
+ alias_method :name, :full_name
6
+ end
7
+
8
+ def formal_first_name
9
+ verified_first_name.presence || first_name
10
+ end
11
+
12
+ def formal_last_name
13
+ verified_last_name.presence || last_name
14
+ end
15
+
16
+ def has_verified_full_name?
17
+ verified_first_name? && verified_last_name?
18
+ end
19
+
20
+ def formal_full_name
21
+ join_names formal_first_name, formal_last_name
22
+ end
23
+
24
+ def full_name
25
+ join_names first_name, last_name
26
+ end
27
+
28
+ def verified_full_name
29
+ join_names verified_first_name, verified_last_name
30
+ end
31
+
32
+ private
33
+
34
+ def join_names(first, last)
35
+ "#{first} #{last}".strip
36
+ end
37
+ end
@@ -9,7 +9,7 @@ module WithMessages
9
9
  end
10
10
 
11
11
  def build_message(body)
12
- messages.build({date: DateTime.current}.merge(body))
12
+ messages.build({date: Time.current, submission_id: submission_id}.merge(body))
13
13
  end
14
14
 
15
15
  def has_messages?
@@ -11,7 +11,7 @@ module WithReminders
11
11
 
12
12
  def remind!
13
13
  build_reminder.deliver_now
14
- update! last_reminded_date: Time.now
14
+ update! last_reminded_date: Time.current
15
15
  end
16
16
 
17
17
  def should_remind?
@@ -34,7 +34,7 @@ module WithResponsibleModerator
34
34
  private
35
35
 
36
36
  def responsible!(moderator)
37
- update! responsible_moderator_at: Time.now, responsible_moderator_by: moderator
37
+ update! responsible_moderator_at: Time.current, responsible_moderator_by: moderator
38
38
  end
39
39
 
40
40
  def no_responsible!
@@ -7,7 +7,7 @@ module WithSoftDeletion
7
7
  end
8
8
 
9
9
  def soft_delete!(motive, deleter)
10
- update! deletion_motive: motive, deleted_by: deleter, deleted_at: Time.now
10
+ update! deletion_motive: motive, deleted_by: deleter, deleted_at: Time.current
11
11
  end
12
12
 
13
13
  def deleted?
@@ -58,8 +58,7 @@ module WithTermsAcceptance
58
58
  end
59
59
 
60
60
  def accept_terms!(terms)
61
- update! unaccepted_terms_scopes_in(terms).to_h { |scope| [term_acceptance_field_for(scope), Time.now] }
61
+ update! unaccepted_terms_scopes_in(terms).to_h { |scope| [term_acceptance_field_for(scope), Time.current] }
62
62
  end
63
63
 
64
64
  end
65
-
@@ -2,7 +2,7 @@ module WithTimedEnablement
2
2
  extend ActiveSupport::Concern
3
3
 
4
4
  def enabled?
5
- enabled_range.cover? DateTime.current
5
+ enabled_range.cover? Time.current
6
6
  end
7
7
 
8
8
  def enabled_range
data/app/models/course.rb CHANGED
@@ -14,7 +14,7 @@ class Course < ApplicationRecord
14
14
  resource_fields :slug, :shifts, :code, :days, :period, :description, :period_start, :period_end
15
15
 
16
16
  def current_invitation
17
- invitations.where('expiration_date > ?', Time.now).first
17
+ invitations.where('expiration_date > ?', Time.current).first
18
18
  end
19
19
 
20
20
  def import_from_resource_h!(resource_h)
@@ -49,7 +49,7 @@ class Course < ApplicationRecord
49
49
  period =~ /^(\d{4})?/
50
50
  year = $1.to_i
51
51
 
52
- return nil unless year.between? 2014, (DateTime.now.year + 1)
52
+ return nil unless year.between? 2014, (Time.current.year + 1)
53
53
 
54
54
  self.period_start = DateTime.new(year).beginning_of_year
55
55
  self.period_end = DateTime.new(year).end_of_year
@@ -15,14 +15,20 @@ class Discussion < ApplicationRecord
15
15
 
16
16
  scope :by_language, -> (language) { includes(:exercise).joins(exercise: :language).where(languages: {name: language}) }
17
17
  scope :order_by_responses_count, -> (direction) { reorder(validated_messages_count: direction, messages_count: opposite(direction)) }
18
- scope :by_requires_moderator_response, -> (boolean) { where(requires_moderator_response: boolean.to_boolean) }
18
+ scope :by_requires_attention, -> (boolean) { opened_and_requires_moderator_response(boolean).or(pending_review).no_responsible_moderator }
19
+ scope :opened_and_requires_moderator_response, -> (boolean) { where(requires_moderator_response: boolean.to_boolean)
20
+ .where(status: :opened) }
21
+ scope :no_responsible_moderator, -> { where('responsible_moderator_at < ?', Time.now - MODERATOR_MAX_RESPONSIBLE_TIME)
22
+ .or(where(responsible_moderator_at: nil)) }
23
+ scope :pending_review, -> { where(status: :pending_review) }
24
+ scope :unread_first, -> { (includes(:subscriptions).reorder('subscriptions.read')) }
19
25
 
20
26
  after_create :subscribe_initiator!
21
27
 
22
28
  markdown_on :description
23
29
 
24
30
  sortable :responses_count, :upvotes_count, :created_at, default: :created_at_desc
25
- filterable :status, :language, :requires_moderator_response
31
+ filterable :status, :language, :requires_attention
26
32
  pageable
27
33
 
28
34
  delegate :language, to: :item
@@ -37,7 +43,7 @@ class Discussion < ApplicationRecord
37
43
  end
38
44
 
39
45
  def visible_messages
40
- messages.where.not(deletion_motive: :self_deleted).or(messages.where(deletion_motive: nil))
46
+ messages.visible
41
47
  end
42
48
 
43
49
  def try_solve!
@@ -49,7 +55,7 @@ class Discussion < ApplicationRecord
49
55
  def navigable_content_in(_)
50
56
  nil
51
57
  end
52
-
58
+
53
59
  def target
54
60
  self
55
61
  end
@@ -123,7 +129,7 @@ class Discussion < ApplicationRecord
123
129
  if reachable_status_for?(user, status)
124
130
  update! status: status,
125
131
  status_updated_by: user,
126
- status_updated_at: Time.now
132
+ status_updated_at: Time.current
127
133
 
128
134
  no_responsible! if responsible?(user)
129
135
  end
@@ -145,6 +151,14 @@ class Discussion < ApplicationRecord
145
151
  validated_messages_count > 0
146
152
  end
147
153
 
154
+ def requires_attention_for?(user)
155
+ user&.moderator_here? && requires_attention?
156
+ end
157
+
158
+ def requires_attention?
159
+ no_current_responsible? && status.requires_attention_for?(self)
160
+ end
161
+
148
162
  def subscribe_initiator!
149
163
  initiator.subscribe_to! self
150
164
  end
data/app/models/exam.rb CHANGED
@@ -32,7 +32,7 @@ class Exam < ApplicationRecord
32
32
  end
33
33
 
34
34
  def enabled_for?(user)
35
- enabled_range_for(user).cover? DateTime.current
35
+ enabled_range_for(user).cover? Time.current
36
36
  end
37
37
 
38
38
  def in_progress_for?(user)
@@ -179,8 +179,8 @@ class Exam < ApplicationRecord
179
179
  exam[:organization_id] = Organization.current.id
180
180
  exam[:course_id] = Course.locate!(exam[:course].to_s).id
181
181
  exam[:users] = User.where(uid: exam[:uids])
182
- exam[:start_time] = exam[:start_time].to_time
183
- exam[:end_time] = exam[:end_time].to_time
182
+ exam[:start_time] = exam[:start_time].in_time_zone
183
+ exam[:end_time] = exam[:end_time].in_time_zone
184
184
  exam[:classroom_id] = exam[:eid] if exam[:eid].present?
185
185
  end
186
186
 
@@ -4,7 +4,7 @@ class ExamAuthorization < ApplicationRecord
4
4
  belongs_to :exam
5
5
 
6
6
  def start!
7
- update!(started: true, started_at: Time.now) unless started?
7
+ update!(started: true, started_at: Time.current) unless started?
8
8
  end
9
9
 
10
10
  end
@@ -17,7 +17,7 @@ class ExamRegistration < ApplicationRecord
17
17
 
18
18
  alias_attribute :name, :description
19
19
 
20
- scope :should_process, -> { where(processed: false).where(arel_table[:end_time].lt(Time.now)) }
20
+ scope :should_process, -> { where(processed: false).where(arel_table[:end_time].lt(Time.current)) }
21
21
 
22
22
  def authorization_criterion
23
23
  @authorization_criterion ||= ExamRegistration::AuthorizationCriterion.parse(authorization_criterion_type, authorization_criterion_value)
@@ -168,14 +168,6 @@ class Exercise < ApplicationRecord
168
168
  Exercise.find(id)
169
169
  end
170
170
 
171
- def messages_path_for(user)
172
- "api/guides/#{guide.slug}/#{bibliotheca_id}/student/#{URI.escape user.uid}/messages?language=#{language}"
173
- end
174
-
175
- def messages_url_for(user)
176
- Mumukit::Platform.classroom_api.organic_url_for(Organization.current, messages_path_for(user))
177
- end
178
-
179
171
  def description_context
180
172
  splitted_description.first.markdownified
181
173
  end
@@ -3,8 +3,9 @@ class Playground < QueriableChallenge
3
3
 
4
4
  name_model_as Exercise
5
5
 
6
- def setup_query_assignment!(assignment)
6
+ def save_query_submission!(assignment, submission)
7
7
  assignment.running!
8
+ assignment.save_submission! submission
8
9
  end
9
10
 
10
11
  def save_query_results!(assignment)
@@ -9,7 +9,7 @@ class Problem < QueriableChallenge
9
9
 
10
10
  name_model_as Exercise
11
11
 
12
- def setup_query_assignment!(assignment)
12
+ def save_query_submission!(_assignment, _submission)
13
13
  end
14
14
 
15
15
  def save_query_results!(assignment)
@@ -2,18 +2,48 @@ class Message < ApplicationRecord
2
2
  include WithSoftDeletion
3
3
 
4
4
  belongs_to :discussion, optional: true
5
- belongs_to :assignment, foreign_key: :submission_id, primary_key: :submission_id, optional: true
5
+ belongs_to :assignment, optional: true
6
6
  belongs_to :approved_by, class_name: 'User', optional: true
7
7
 
8
8
  has_one :exercise, through: :assignment
9
9
 
10
10
  validates_presence_of :content, :sender
11
- validates_presence_of :submission_id, :unless => :discussion_id?
11
+ validate :ensure_contextualized
12
12
 
13
13
  after_save :update_counters_cache!
14
14
 
15
15
  markdown_on :content
16
16
 
17
+ # Visible messages are those that can be publicly seen
18
+ # in forums. non-direct messages are never visible.
19
+ scope :visible, -> () do
20
+ where.not(deletion_motive: :self_deleted)
21
+ .or(where(deletion_motive: nil))
22
+ .where(assignment_id: nil)
23
+ end
24
+
25
+ def contextualization
26
+ direct? ? assignment : discussion
27
+ end
28
+
29
+ def contextualized?
30
+ assignment_id.present? ^ discussion_id.present?
31
+ end
32
+
33
+ # Whether this message is stale, that is, it
34
+ # targets a submission that is not the latest one.
35
+ #
36
+ # Only direct messages may become stale.
37
+ def stale?
38
+ direct? && assignment.submission_id != submission_id
39
+ end
40
+
41
+ # Whether this message is direct, that is, whether it comes from rise-hand feature.
42
+ # Forum messages are non-direct.
43
+ def direct?
44
+ submission_id.present?
45
+ end
46
+
17
47
  def notify!
18
48
  Mumukit::Nuntius.notify! 'student-messages', to_resource_h unless Organization.silenced?
19
49
  end
@@ -85,33 +115,29 @@ class Message < ApplicationRecord
85
115
  self
86
116
  end
87
117
 
88
- def self.parse_json(json)
89
- message = json.delete 'message'
90
- json
91
- .except('uid', 'exercise_id')
92
- .merge(message)
93
- end
94
-
95
118
  def self.read_all!
96
119
  update_all read: true
97
120
  end
98
121
 
99
- def self.import_from_resource_h!(json)
100
- message_data = parse_json json
101
- Organization.find_by!(name: message_data.delete('organization')).switch!
102
-
103
- if message_data['submission_id'].present?
104
- Assignment.find_by(submission_id: message_data.delete('submission_id'))&.receive_answer! message_data
122
+ def self.import_from_resource_h!(resource_h)
123
+ if resource_h['submission_id'].present?
124
+ assignment = Assignment.find_by(submission_id: resource_h['submission_id'])
125
+ assignment&.receive_answer! sender: resource_h['message']['sender'],
126
+ content: resource_h['message']['content']
105
127
  end
106
128
  end
107
129
 
108
130
  private
109
131
 
110
132
  def approve!(user)
111
- update! approved: true, approved_at: Time.now, approved_by: user
133
+ update! approved: true, approved_at: Time.current, approved_by: user
112
134
  end
113
135
 
114
136
  def disapprove!
115
137
  update! approved: false, approved_at: nil, approved_by: nil
116
138
  end
139
+
140
+ def ensure_contextualized
141
+ errors.add(:base, :not_properly_contextualized) unless contextualized?
142
+ end
117
143
  end
@@ -23,7 +23,7 @@ class Organization < ApplicationRecord
23
23
 
24
24
  has_many :certificate_programs
25
25
 
26
- validates_presence_of :contact_email, :locale
26
+ validates_presence_of :contact_email, :locale, :time_zone
27
27
  validates_presence_of :welcome_email_template, if: :greet_new_users?
28
28
  validates :name, uniqueness: true,
29
29
  presence: true,
data/app/models/user.rb CHANGED
@@ -9,6 +9,7 @@ class User < ApplicationRecord
9
9
  Disabling,
10
10
  WithTermsAcceptance,
11
11
  WithPreferences,
12
+ Onomastic,
12
13
  Mumuki::Domain::Helpers::User
13
14
 
14
15
  serialize :permissions, Mumukit::Auth::Permissions
@@ -251,7 +252,7 @@ class User < ApplicationRecord
251
252
 
252
253
  def age
253
254
  if birthdate.present?
254
- @age ||= Time.now.round_years_since(birthdate.to_time)
255
+ @age ||= Time.current.round_years_since(birthdate.in_time_zone)
255
256
  end
256
257
  end
257
258
 
@@ -288,18 +289,6 @@ class User < ApplicationRecord
288
289
  end
289
290
  end
290
291
 
291
- def formal_first_name
292
- verified_first_name.presence || first_name
293
- end
294
-
295
- def formal_last_name
296
- verified_last_name.presence || last_name
297
- end
298
-
299
- def formal_full_name
300
- "#{formal_first_name} #{formal_last_name}"
301
- end
302
-
303
292
  def certificates_in_organization(organization = Organization.current)
304
293
  certificates.where certificate_program: CertificateProgram.where(organization: organization)
305
294
  end
@@ -0,0 +1,5 @@
1
+ class AddAssignmentIdToMessage < ActiveRecord::Migration[5.1]
2
+ def change
3
+ add_reference :messages, :assignment, index: true
4
+ end
5
+ end
@@ -28,12 +28,20 @@ FactoryBot.define do
28
28
  end
29
29
 
30
30
  factory :exercise_base do
31
+ transient do
32
+ indexed { false }
33
+ end
34
+
31
35
  language { guide ? guide.language : create(:language) }
32
36
  sequence(:bibliotheca_id) { |n| n }
33
37
  sequence(:number) { |n| n }
34
38
 
35
39
  locale { :en }
36
40
  guide
41
+
42
+ after(:build) do |exercise, evaluator|
43
+ exercise.guide = create(:indexed_guide) if evaluator.indexed
44
+ end
37
45
  end
38
46
 
39
47
  factory :challenge, parent: :exercise_base do
@@ -73,7 +81,7 @@ FactoryBot.define do
73
81
  factory :exercise, parent: :problem
74
82
 
75
83
  factory :indexed_exercise, parent: :exercise do
76
- guide { create(:indexed_guide) }
84
+ indexed { true }
77
85
  end
78
86
 
79
87
  factory :x_equal_5_exercise, parent: :exercise do
@@ -61,12 +61,6 @@ module Mumuki::Domain::Helpers::User
61
61
 
62
62
  ## Profile
63
63
 
64
- def full_name
65
- "#{first_name} #{last_name}".strip
66
- end
67
-
68
- alias_method :name, :full_name
69
-
70
64
  def profile_completed?
71
65
  self.class.profile_fields.map { |it| self[it] }.all? &:present?
72
66
  end
@@ -41,7 +41,7 @@ class Mumuki::Domain::Organization::Profile < Mumukit::Platform::Model
41
41
  end
42
42
 
43
43
  def time_zone
44
- @time_zone || 'Buenos Aires'
44
+ @time_zone
45
45
  end
46
46
 
47
47
  end
@@ -32,11 +32,11 @@ class Mumuki::Domain::Organization::Settings < Mumukit::Platform::Model
32
32
  end
33
33
 
34
34
  def disabled_from=(disabled_from)
35
- @disabled_from = disabled_from&.to_time
35
+ @disabled_from = disabled_from&.in_time_zone
36
36
  end
37
37
 
38
38
  def in_preparation_until=(in_preparation_until)
39
- @in_preparation_until = in_preparation_until&.to_time
39
+ @in_preparation_until = in_preparation_until&.in_time_zone
40
40
  end
41
41
 
42
42
  def disabled?
@@ -12,4 +12,8 @@ module Mumuki::Domain::Status::Discussion::Closed
12
12
  def self.iconize
13
13
  {class: :danger, type: 'times-circle'}
14
14
  end
15
+
16
+ def self.requires_attention_for?(_)
17
+ false
18
+ end
15
19
  end
@@ -28,4 +28,8 @@ module Mumuki::Domain::Status::Discussion::Opened
28
28
  def self.should_be_shown?(*)
29
29
  true
30
30
  end
31
+
32
+ def self.requires_attention_for?(discussion)
33
+ discussion.requires_moderator_response?
34
+ end
31
35
  end
@@ -12,4 +12,8 @@ module Mumuki::Domain::Status::Discussion::PendingReview
12
12
  def self.iconize
13
13
  {class: :info, type: 'hourglass'}
14
14
  end
15
+
16
+ def self.requires_attention_for?(_)
17
+ true
18
+ end
15
19
  end
@@ -16,4 +16,8 @@ module Mumuki::Domain::Status::Discussion::Solved
16
16
  def self.should_be_shown?(*)
17
17
  true
18
18
  end
19
+
20
+ def self.requires_attention_for?(_)
21
+ false
22
+ end
19
23
  end
@@ -2,6 +2,6 @@ class Mumuki::Domain::Submission::PersistentSubmission < Mumuki::Domain::Submiss
2
2
  def save_submission!(assignment)
3
3
  assignment.running!
4
4
  super
5
- assignment.persist_submission! self
5
+ assignment.save_submission! self
6
6
  end
7
7
  end
@@ -6,7 +6,7 @@ class Mumuki::Domain::Submission::Query < Mumuki::Domain::Submission::ConsoleSub
6
6
  end
7
7
 
8
8
  def save_submission!(assignment)
9
- assignment.exercise.setup_query_assignment!(assignment)
9
+ assignment.exercise.save_query_submission!(assignment, self)
10
10
  super
11
11
  end
12
12
 
@@ -5,7 +5,6 @@ class Mumuki::Domain::Submission::Question < Mumuki::Domain::Submission::Base
5
5
  end
6
6
 
7
7
  def save_submission!(assignment)
8
- assignment.persist_submission! self
9
8
  end
10
9
 
11
10
  def try_evaluate!(*)
@@ -8,6 +8,7 @@ class Mumuki::Domain::Submission::Try < Mumuki::Domain::Submission::ConsoleSubmi
8
8
  def save_submission!(assignment)
9
9
  assignment.query_results = [] if cookie.blank?
10
10
  assignment.queries = cookie.insert_last(query)
11
+ assignment.save_submission! self
11
12
  assignment.save!
12
13
  end
13
14
 
@@ -1,5 +1,5 @@
1
1
  module Mumuki
2
2
  module Domain
3
- VERSION = '9.7.0'
3
+ VERSION = '9.10.0'
4
4
  end
5
5
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: mumuki-domain
3
3
  version: !ruby/object:Gem::Version
4
- version: 9.7.0
4
+ version: 9.10.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Franco Leonardo Bulgarelli
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2021-06-17 00:00:00.000000000 Z
11
+ date: 2021-07-29 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rails
@@ -264,6 +264,7 @@ files:
264
264
  - app/models/concerns/navigation/parent_navigation.rb
265
265
  - app/models/concerns/navigation/siblings_navigation.rb
266
266
  - app/models/concerns/navigation/terminal_navigation.rb
267
+ - app/models/concerns/onomastic.rb
267
268
  - app/models/concerns/submittable/confirmable.rb
268
269
  - app/models/concerns/submittable/queriable.rb
269
270
  - app/models/concerns/submittable/questionable.rb
@@ -670,6 +671,7 @@ files:
670
671
  - db/migrate/20210330175706_create_exam_registration_user_join_table.rb
671
672
  - db/migrate/20210512200453_add_processed_flag_to_exam_registration.rb
672
673
  - db/migrate/20210518100153_rename_last_moderator_access.rb
674
+ - db/migrate/20210707143002_add_assignment_id_to_message.rb
673
675
  - lib/mumuki/domain.rb
674
676
  - lib/mumuki/domain/area.rb
675
677
  - lib/mumuki/domain/engine.rb