-
-
Notifications
You must be signed in to change notification settings - Fork 26
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #1072 from mumuki/feature-generalized-tips
Feature generalized tips
- Loading branch information
Showing
34 changed files
with
746 additions
and
36 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,17 @@ | ||
module Assistable | ||
extend ActiveSupport::Concern | ||
|
||
included do | ||
serialize :assistance_rules, Array | ||
end | ||
|
||
def assistant | ||
Mumukit::Assistant.parse(assistance_rules) | ||
end | ||
|
||
def assist_with(assignment) | ||
# not strictly necessary, but avoid going through | ||
# all the assistence process when there are no rules | ||
assistance_rules.blank? ? [] : assistant.assist_with(assignment) | ||
end | ||
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -11,7 +11,7 @@ def passed? | |
end | ||
|
||
def aborted? | ||
status == :aborted | ||
status.aborted? | ||
end | ||
|
||
def run_update! | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
5 changes: 5 additions & 0 deletions
5
db/migrate/20180307150148_add_failed_submissions_count_to_assignments.rb
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,5 @@ | ||
class AddFailedSubmissionsCountToAssignments < ActiveRecord::Migration[5.1] | ||
def change | ||
add_column :assignments, :attemps_count, :integer, default: 0 | ||
end | ||
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,5 @@ | ||
class AddTipsRulesToExercise < ActiveRecord::Migration[5.1] | ||
def change | ||
add_column :exercises, :assistance_rules, :text | ||
end | ||
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,14 @@ | ||
en: | ||
narrator: | ||
retry_0: Let's try again! | ||
retry_1: Keep on! | ||
retry_2: Let's fix it! | ||
introduction_0: "Oops, it didn't work :frowning:." | ||
introduction_1: "Oops, it didn't work :frowning:." | ||
introduction_2: "Oops, it didn't work :frowning:." | ||
middle_0: Also, %{tip}. | ||
middle_1: Also, %{tip}. | ||
middle_2: Also, %{tip}. | ||
ending_0: Finally, %{tip}. | ||
ending_1: Finally, %{tip}. | ||
ending_2: Finally, %{tip}. |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,14 @@ | ||
es: | ||
narrator: | ||
retry_0: ¡Intentemos de nuevo! | ||
retry_1: 'Pero a no desesperar, intentemos otra vez :muscle:' | ||
retry_2: ¡Corrijamos el problema! | ||
introduction_0: 'Parece que algo no funcionó :see_no_evil:.' | ||
introduction_1: 'Eh, ¿qué pasó acá :frowning:?' | ||
introduction_2: 'Parece que algo no anduvo bien :sweat_smile:' | ||
middle_0: "Además, %{tip}." | ||
middle_1: "También %{tip}." | ||
middle_2: "Por otro lado, %{tip}." | ||
ending_0: "Por último, %{tip}." | ||
ending_1: "Ah, algo más: %{tip}." | ||
ending_2: "Y para cerrar, %{tip}." |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,14 @@ | ||
pt: | ||
narrator: | ||
retry_0: Vamos tentar de novo! | ||
retry_1: 'Mas não se desespere, vamos tentar novamente :muscle:' | ||
retry_2: Corrigimos o problema! | ||
introduction_0: 'Parece que algo não funcionou :see_no_evil:.' | ||
introduction_1: 'Ei, o que aconteceu aqui :frowning:?' | ||
introduction_2: 'Parece que algo não correu bem :sweat_smile:' | ||
middle_0: "Além disso, %{tip}." | ||
middle_1: "Também %{tip}." | ||
middle_2: "Por outro lado, %{tip}." | ||
ending_0: "Finalmente, %{tip}." | ||
ending_1: "Oh, algo mais: %{tip}." | ||
ending_2: "E para fechar, %{tip}." |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -8,8 +8,4 @@ def self.to_i | |
def self.iconize | ||
{class: :muted, type: :circle} | ||
end | ||
|
||
def self.should_retry? | ||
false | ||
end | ||
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,30 @@ | ||
module Mumukit | ||
# An assistant is used to generate dynamic feedback | ||
# over a student's submission, based on rules. | ||
# | ||
# This feedback is composed of a list of markdown messages called _tips_, | ||
# and the whole processes of creating this feedback is called _assistance_. | ||
class Assistant | ||
attr_accessor :rules | ||
|
||
def initialize(rules) | ||
@rules = rules | ||
end | ||
|
||
# Provides tips for the student for the given submission, | ||
# based on the `rules`. | ||
def assist_with(submission) | ||
@rules | ||
.select { |it| it.matches?(submission) } | ||
.map { |it| it.message_for(submission.attemps_count) } | ||
end | ||
|
||
def self.parse(rules) | ||
new rules.map { |it| Mumukit::Assistant::Rule.parse it } | ||
end | ||
end | ||
end | ||
|
||
require_relative './assistant/rule' | ||
require_relative './assistant/message' | ||
require_relative './assistant/narrator' |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,45 @@ | ||
module Mumukit::Assistant::Message | ||
# Fixed messages are independent of the number | ||
# of attemps | ||
class Fixed | ||
def initialize(text) | ||
@text = text | ||
end | ||
|
||
def call(_) | ||
@text | ||
end | ||
end | ||
|
||
# Progressive messages depend on the number of attemps | ||
# They work with exactly two or three messages: | ||
# | ||
# * the first message will be displayed in the first three attemps | ||
# * the second message will be displayed in the fourth, fifth and sixth attemps | ||
# * the third message will be displayed starting at the seventh attemp | ||
# | ||
class Progressive | ||
def initialize(alternatives) | ||
raise 'You need two or three alternatives' unless alternatives.size.between?(2, 3) | ||
@alternatives = alternatives | ||
end | ||
|
||
def call(attemps_count) | ||
case attemps_count | ||
when (1..3) then @alternatives.first | ||
when (4..6) then @alternatives.second | ||
else @alternatives.last | ||
end | ||
end | ||
end | ||
|
||
def self.parse(text_or_alternatives) | ||
if text_or_alternatives.is_a? String | ||
Fixed.new text_or_alternatives | ||
elsif text_or_alternatives.is_a? Array | ||
Progressive.new text_or_alternatives | ||
else | ||
raise "Wrong message format #{text_or_alternatives}" | ||
end | ||
end | ||
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,67 @@ | ||
# A narrator can turn tips - generated by `Mumukit::Assistant` - | ||
# into a humanized text with the same information but | ||
# a bit more friendly. This text is called _explanation_. | ||
# | ||
# The narrator uses some internationalized random phrases, and it does provide | ||
# a seed as a construction argument to allow its testing. | ||
class Mumukit::Assistant::Narrator | ||
def initialize(seed) | ||
@seed = seed | ||
end | ||
|
||
# Generated a markdown explanation using the seeded phrases. Uses `I18n` to get | ||
# the appropriate locale. | ||
def compose_explanation(tips) | ||
"#{explanation_introduction_phrase}\n\n#{explanation_paragraphs(tips).join("\n\n")}\n\n#{retry_phrase}\n" | ||
end | ||
|
||
# Generates an html explantion. | ||
# See `compose_explanation` | ||
def compose_explanation_html(tips) | ||
Mumukit::ContentType::Markdown.to_html compose_explanation(tips) | ||
end | ||
|
||
def retry_phrase | ||
t :retry | ||
end | ||
|
||
def explanation_introduction_phrase | ||
t :introduction | ||
end | ||
|
||
def explanation_paragraphs(tips) | ||
tips.take(3).zip([:opening, :middle, :ending]).map do |tip, selector| | ||
send "explanation_#{selector}_paragraph", tip | ||
end | ||
end | ||
|
||
def explanation_opening_paragraph(tip) | ||
"#{tip.capitalize}." | ||
end | ||
|
||
def explanation_middle_paragraph(tip) | ||
t :middle, tip: tip | ||
end | ||
|
||
def explanation_ending_paragraph(tip) | ||
t :ending, tip: tip | ||
end | ||
|
||
def self.random | ||
new seed(*5.times.map { random_index }) | ||
end | ||
|
||
def self.seed(r, i, o, m, e) | ||
{ retry: r, introduction: i, opening: o, middle: m, ending: e } | ||
end | ||
|
||
private | ||
|
||
def t(key, args={}) | ||
I18n.t "narrator.#{key}_#{@seed[key]}", args | ||
end | ||
|
||
def self.random_index | ||
(0..2).to_a.sample | ||
end | ||
end |
Oops, something went wrong.