moodle2cc 0.2.41 → 0.2.43
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/lib/moodle2cc/canvas/assessment.rb +0 -0
- data/lib/moodle2cc/canvas/assignment.rb +0 -0
- data/lib/moodle2cc/canvas/converter.rb +0 -0
- data/lib/moodle2cc/canvas/discussion_topic.rb +0 -0
- data/lib/moodle2cc/canvas/label.rb +0 -0
- data/lib/moodle2cc/canvas/question.rb +3 -3
- data/lib/moodle2cc/canvas/question_bank.rb +0 -0
- data/lib/moodle2cc/canvas/question_group.rb +0 -0
- data/lib/moodle2cc/canvas/resource.rb +0 -0
- data/lib/moodle2cc/canvas/templates/assignment.html.erb +0 -0
- data/lib/moodle2cc/canvas/templates/syllabus.html.erb +0 -0
- data/lib/moodle2cc/canvas/templates/wiki_content.html.erb +0 -0
- data/lib/moodle2cc/canvas/web_content.rb +0 -0
- data/lib/moodle2cc/canvas/web_link.rb +0 -0
- data/lib/moodle2cc/canvas/wiki.rb +0 -0
- data/lib/moodle2cc/canvas_cc/models/assessment.rb +27 -17
- data/lib/moodle2cc/canvas_cc/models/question.rb +21 -15
- data/lib/moodle2cc/cc/assessment.rb +0 -0
- data/lib/moodle2cc/cc/assignment.rb +0 -0
- data/lib/moodle2cc/cc/course.rb +0 -0
- data/lib/moodle2cc/cc/discussion_topic.rb +0 -0
- data/lib/moodle2cc/cc/label.rb +0 -0
- data/lib/moodle2cc/cc/question.rb +0 -0
- data/lib/moodle2cc/cc/resource.rb +0 -0
- data/lib/moodle2cc/cc/templates/assignment.html.erb +0 -0
- data/lib/moodle2cc/cc/templates/syllabus.html.erb +0 -0
- data/lib/moodle2cc/cc/templates/wiki_content.html.erb +0 -0
- data/lib/moodle2cc/cc/web_link.rb +0 -0
- data/lib/moodle2cc/cc/wiki.rb +0 -0
- data/lib/moodle2cc/error.rb +0 -0
- data/lib/moodle2cc/logger.rb +0 -0
- data/lib/moodle2cc/moodle/course.rb +0 -0
- data/lib/moodle2cc/moodle/grade_item.rb +0 -0
- data/lib/moodle2cc/moodle/info.rb +0 -0
- data/lib/moodle2cc/moodle/question_category.rb +0 -0
- data/lib/moodle2cc/moodle/section.rb +0 -0
- data/lib/moodle2cc/moodle2/models/quizzes/question.rb +23 -7
- data/lib/moodle2cc/moodle2/parsers/forum_parser.rb +2 -2
- data/lib/moodle2cc/moodle2/parsers/question_category_parser.rb +31 -21
- data/lib/moodle2cc/moodle2/parsers/question_parsers/question_parser.rb +30 -31
- data/lib/moodle2cc/moodle2/parsers/quiz_parser.rb +54 -52
- data/lib/moodle2cc/moodle2converter/question_converters/question_converter.rb +16 -12
- data/lib/moodle2cc/version.rb +1 -1
- metadata +6 -7
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 00f4e9ab98639c0cfad6a74817e7658bcd09b6e8c7e5f6d344000321f3f226ae
|
4
|
+
data.tar.gz: f6ed3c60d489fc0949022feecf030cc8733b43294263da35844c866c63b3777c
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 90961bcb581bbb15314bce622dac900fca05a840e9c80f73602341759f69a00ce644299a9348015387067335d467549920f02d63ca147db503b6d3cbe441fba7
|
7
|
+
data.tar.gz: 3b8a6392926134b26847a2ada520eaff43698e27f9dcbd724acbd260a632c770775d15fea37786cf427527b1b81c65370e28aaebcc3038b74118e1f6eb6fc660
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
@@ -148,9 +148,9 @@ module Moodle2CC::Canvas
|
|
148
148
|
end
|
149
149
|
end
|
150
150
|
|
151
|
-
if question.instance_id
|
152
|
-
|
153
|
-
end
|
151
|
+
# if question.instance_id
|
152
|
+
@assessment_question_identifierref = create_key(question.instance_id || question.id, "#{@identifier_prefix}question_")
|
153
|
+
# end
|
154
154
|
end
|
155
155
|
|
156
156
|
def create_item_xml(section_node)
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
@@ -1,12 +1,21 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
module Moodle2CC::CanvasCC::Models
|
2
4
|
class Assessment
|
3
|
-
META_ATTRIBUTES = [
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
5
|
+
META_ATTRIBUTES = %i[title
|
6
|
+
description
|
7
|
+
allowed_attempts
|
8
|
+
scoring_policy
|
9
|
+
access_code
|
10
|
+
ip_filter
|
11
|
+
shuffle_answers
|
12
|
+
time_limit
|
13
|
+
quiz_type].freeze
|
14
|
+
DATETIME_ATTRIBUTES = [:lock_at, :unlock_at].freeze
|
15
|
+
|
16
|
+
ASSESSMENT_TYPE = "imsqti_xmlv1p2/imscc_xmlv1p1/assessment"
|
17
|
+
LAR_TYPE = "associatedcontent/imscc_xmlv1p1/learning-application-resource"
|
18
|
+
ASSESSMENT_NON_CC_FOLDER = "non_cc_assessments"
|
10
19
|
|
11
20
|
attr_accessor :identifier, :workflow_state, :question_references, :items, *META_ATTRIBUTES, *DATETIME_ATTRIBUTES
|
12
21
|
|
@@ -54,14 +63,15 @@ module Moodle2CC::CanvasCC::Models
|
|
54
63
|
question = nil
|
55
64
|
group = nil
|
56
65
|
question_banks.each do |bank|
|
57
|
-
break if (question = bank.questions.detect{|q| q.original_identifier.to_s == ref[:question]})
|
58
|
-
|
66
|
+
break if (question = bank.questions.detect { |q| q.original_identifier.to_s == ref[:question] })
|
67
|
+
break if (question = bank.questions.detect { |q| q.bank_entry_id.to_s == ref[:bank_entry_id] })
|
68
|
+
break if (group = bank.question_groups.detect { |g| g.identifier.to_s == ref[:question] })
|
59
69
|
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
70
|
+
next unless bank.random_question_references.any? { |r| r.to_s == ref[:question] }
|
71
|
+
|
72
|
+
random_bank_counts[bank] ||= 0
|
73
|
+
random_bank_counts[bank] += 1
|
74
|
+
break
|
65
75
|
end
|
66
76
|
|
67
77
|
if question
|
@@ -93,11 +103,11 @@ module Moodle2CC::CanvasCC::Models
|
|
93
103
|
@items << new_group
|
94
104
|
end
|
95
105
|
|
96
|
-
@items.select{|i| i.is_a?(Moodle2CC::CanvasCC::Models::QuestionGroup)}.each do |group|
|
106
|
+
@items.select { |i| i.is_a?(Moodle2CC::CanvasCC::Models::QuestionGroup) }.each do |group|
|
97
107
|
group.questions.each do |q|
|
98
|
-
@items.delete_if{|i| i.respond_to?(:original_identifier) && i.original_identifier == q.original_identifier}
|
108
|
+
@items.delete_if { |i| i.respond_to?(:original_identifier) && i.original_identifier == q.original_identifier }
|
99
109
|
end
|
100
110
|
end
|
101
111
|
end
|
102
112
|
end
|
103
|
-
end
|
113
|
+
end
|
@@ -1,22 +1,28 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
module Moodle2CC::CanvasCC::Models
|
2
4
|
class Question
|
3
|
-
QTI_META_ATTRIBUTES = [
|
4
|
-
STANDARD_QUESTION_TYPES = [
|
5
|
-
|
6
|
-
|
5
|
+
QTI_META_ATTRIBUTES = %i[question_type points_possible assessment_question_identifierref].freeze
|
6
|
+
STANDARD_QUESTION_TYPES = %w[essay_question
|
7
|
+
fill_in_multiple_blanks_question
|
8
|
+
multiple_choice_question
|
9
|
+
multiple_answers_question
|
10
|
+
short_answer_question
|
11
|
+
text_only_question
|
12
|
+
true_false_question].freeze
|
7
13
|
|
8
|
-
attr_accessor :identifier, :original_identifier, :title, :material, :answers, :general_feedback, *QTI_META_ATTRIBUTES
|
14
|
+
attr_accessor :identifier, :original_identifier, :bank_entry_id, :title, :material, :answers, :general_feedback, *QTI_META_ATTRIBUTES
|
9
15
|
|
10
16
|
@@subclasses = {}
|
11
17
|
|
12
18
|
def self.create(type)
|
13
19
|
q = if STANDARD_QUESTION_TYPES.include?(type)
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
+
new
|
21
|
+
elsif (c = @@subclasses[type])
|
22
|
+
c.new
|
23
|
+
else
|
24
|
+
raise "Unknown question type: #{type}"
|
25
|
+
end
|
20
26
|
q.question_type = type
|
21
27
|
q
|
22
28
|
end
|
@@ -31,7 +37,7 @@ module Moodle2CC::CanvasCC::Models
|
|
31
37
|
end
|
32
38
|
end
|
33
39
|
|
34
|
-
require_relative
|
35
|
-
require_relative
|
36
|
-
require_relative
|
37
|
-
require_relative
|
40
|
+
require_relative "calculated_question"
|
41
|
+
require_relative "matching_question"
|
42
|
+
require_relative "multiple_dropdowns_question"
|
43
|
+
require_relative "numerical_question"
|
File without changes
|
File without changes
|
data/lib/moodle2cc/cc/course.rb
CHANGED
File without changes
|
File without changes
|
data/lib/moodle2cc/cc/label.rb
CHANGED
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
data/lib/moodle2cc/cc/wiki.rb
CHANGED
File without changes
|
data/lib/moodle2cc/error.rb
CHANGED
File without changes
|
data/lib/moodle2cc/logger.rb
CHANGED
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
@@ -1,17 +1,18 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
module Moodle2CC::Moodle2::Models::Quizzes
|
2
4
|
class Question
|
3
|
-
|
4
5
|
@@subclasses = {}
|
5
6
|
|
6
|
-
STANDARD_TYPES = [
|
7
|
+
STANDARD_TYPES = %w[description essay random shortanswer].freeze
|
7
8
|
|
8
9
|
def self.create(type)
|
9
|
-
if c = @@subclasses[type]
|
10
|
+
if (c = @@subclasses[type])
|
10
11
|
q = c.new
|
11
12
|
q.type = type
|
12
13
|
q
|
13
14
|
elsif STANDARD_TYPES.include?(type)
|
14
|
-
q =
|
15
|
+
q = new
|
15
16
|
q.type = type
|
16
17
|
q
|
17
18
|
else
|
@@ -23,11 +24,26 @@ module Moodle2CC::Moodle2::Models::Quizzes
|
|
23
24
|
@@subclasses[name] = self
|
24
25
|
end
|
25
26
|
|
26
|
-
attr_accessor :id,
|
27
|
-
:
|
27
|
+
attr_accessor :id,
|
28
|
+
:bank_entry_id,
|
29
|
+
:parent,
|
30
|
+
:name,
|
31
|
+
:question_text,
|
32
|
+
:question_text_format,
|
33
|
+
:general_feedback,
|
34
|
+
:default_mark,
|
35
|
+
:max_mark,
|
36
|
+
:penalty,
|
37
|
+
:qtype,
|
38
|
+
:length,
|
39
|
+
:stamp,
|
40
|
+
:version,
|
41
|
+
:hidden,
|
42
|
+
:answers,
|
43
|
+
:type
|
28
44
|
|
29
45
|
def initialize
|
30
46
|
@answers = []
|
31
47
|
end
|
32
48
|
end
|
33
|
-
end
|
49
|
+
end
|
@@ -22,8 +22,8 @@ module Moodle2CC::Moodle2::Parsers
|
|
22
22
|
activity_dir = File.join(@backup_dir, forum_dir)
|
23
23
|
File.open(File.join(activity_dir, xml_file)) do |f|
|
24
24
|
forum_xml = Nokogiri::XML(f)
|
25
|
-
forum.id = forum_xml.at_xpath("/activity/#{module_name}/@id")
|
26
|
-
forum.module_id = forum_xml.at_xpath("/activity/@moduleid")
|
25
|
+
forum.id = forum_xml.at_xpath("/activity/#{module_name}/@id")&.value
|
26
|
+
forum.module_id = forum_xml.at_xpath("/activity/@moduleid")&.value
|
27
27
|
forum.name = parse_text(forum_xml, "/activity/#{module_name}/name")
|
28
28
|
forum.type = parse_text(forum_xml, "/activity/#{module_name}/type")
|
29
29
|
forum.intro = parse_text(forum_xml, "/activity/#{module_name}/intro")
|
@@ -1,8 +1,10 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
module Moodle2CC::Moodle2
|
2
4
|
class Parsers::QuestionCategoryParser
|
3
5
|
include Parsers::ParserHelper
|
4
6
|
|
5
|
-
QUESTIONS_XML =
|
7
|
+
QUESTIONS_XML = "questions.xml"
|
6
8
|
|
7
9
|
def initialize(backup_dir)
|
8
10
|
@backup_dir = backup_dir
|
@@ -11,7 +13,7 @@ module Moodle2CC::Moodle2
|
|
11
13
|
def parse
|
12
14
|
File.open(File.join(@backup_dir, QUESTIONS_XML)) do |f|
|
13
15
|
root_xml = Nokogiri::XML(f)
|
14
|
-
root_xml.search(
|
16
|
+
root_xml.search("/question_categories/question_category").map { |node| question_category_parser(node) }
|
15
17
|
end
|
16
18
|
end
|
17
19
|
|
@@ -19,30 +21,38 @@ module Moodle2CC::Moodle2
|
|
19
21
|
|
20
22
|
def question_category_parser(node)
|
21
23
|
category = Models::Quizzes::QuestionCategory.new
|
22
|
-
category.id = node.at_xpath(
|
23
|
-
category.name = parse_text(node,
|
24
|
-
category.context_id = parse_text(node,
|
25
|
-
category.context_level = parse_text(node,
|
26
|
-
category.context_instance_id = parse_text(node,
|
27
|
-
category.info = parse_text(node,
|
28
|
-
category.info_format = parse_text(node,
|
29
|
-
category.stamp = parse_text(node,
|
30
|
-
category.parent = parse_text(node,
|
31
|
-
category.sort_order = parse_text(node,
|
32
|
-
|
33
|
-
category.questions += node.search(
|
24
|
+
category.id = node.at_xpath("@id").value
|
25
|
+
category.name = parse_text(node, "name")
|
26
|
+
category.context_id = parse_text(node, "contextid")
|
27
|
+
category.context_level = parse_text(node, "contextlevel")
|
28
|
+
category.context_instance_id = parse_text(node, "contextinstanceid")
|
29
|
+
category.info = parse_text(node, "info")
|
30
|
+
category.info_format = parse_text(node, "infoformat")
|
31
|
+
category.stamp = parse_text(node, "stamp")
|
32
|
+
category.parent = parse_text(node, "parent")
|
33
|
+
category.sort_order = parse_text(node, "sortorder")
|
34
|
+
|
35
|
+
category.questions += node.search("questions/question").filter_map { |question_node| question_parser(question_node) }
|
36
|
+
category.questions += node.search("question_bank_entries/question_bank_entry").map do |question_bank_entry|
|
37
|
+
question_bank_entry.search("question_version/question_versions").map do |question_versions|
|
38
|
+
question_versions.search("questions/question").map do |question_node|
|
39
|
+
bank_entry_reference = Nokogiri::XML::DocumentFragment.parse("<bank_entry_id>#{question_bank_entry.at_xpath("@id").value}</bank_entry_id>")
|
40
|
+
question_node.add_child(bank_entry_reference)
|
41
|
+
question_parser(question_node)
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end.flatten.compact
|
45
|
+
|
46
|
+
category.questions = category.questions.flatten
|
34
47
|
|
35
48
|
category
|
36
49
|
end
|
37
50
|
|
38
51
|
def question_parser(node)
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
nil
|
44
|
-
end
|
52
|
+
Parsers::QuestionParsers::QuestionParser.parse(node)
|
53
|
+
rescue Exception => e
|
54
|
+
Moodle2CC::OutputLogger.logger.info e.message
|
55
|
+
nil
|
45
56
|
end
|
46
|
-
|
47
57
|
end
|
48
58
|
end
|
@@ -1,3 +1,5 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
module Moodle2CC::Moodle2
|
2
4
|
class Parsers::QuestionParsers::QuestionParser
|
3
5
|
include Parsers::ParserHelper
|
@@ -5,8 +7,8 @@ module Moodle2CC::Moodle2
|
|
5
7
|
@@subclasses = {}
|
6
8
|
|
7
9
|
def self.parse(node)
|
8
|
-
type = node.%(
|
9
|
-
if c = @@subclasses[type]
|
10
|
+
type = node.%("qtype").text
|
11
|
+
if (c = @@subclasses[type])
|
10
12
|
c.new.parse_question(node)
|
11
13
|
else
|
12
14
|
raise "Unknown parser type: #{type}"
|
@@ -18,37 +20,34 @@ module Moodle2CC::Moodle2
|
|
18
20
|
end
|
19
21
|
|
20
22
|
# simple question types
|
21
|
-
register_parser_type(
|
22
|
-
register_parser_type(
|
23
|
-
register_parser_type(
|
23
|
+
register_parser_type("description")
|
24
|
+
register_parser_type("essay")
|
25
|
+
register_parser_type("random")
|
24
26
|
|
25
27
|
def parse_question(node, question_type = nil)
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
end
|
28
|
+
question_type ||= parse_text(node, "qtype")
|
29
|
+
question = Models::Quizzes::Question.create question_type
|
30
|
+
|
31
|
+
question.id = node.at_xpath("@id").value
|
32
|
+
question.bank_entry_id = parse_text(node, "bank_entry_id")
|
33
|
+
question.parent = parse_text(node, "parent")
|
34
|
+
question.name = parse_text(node, "name")
|
35
|
+
question.question_text = parse_text(node, "questiontext")
|
36
|
+
question.question_text_format = parse_text(node, "questiontextformat")
|
37
|
+
question.general_feedback = parse_text(node, "generalfeedback")
|
38
|
+
question.default_mark = parse_text(node, "defaultmark")
|
39
|
+
question.max_mark = parse_text(node, "maxmark")
|
40
|
+
question.penalty = parse_text(node, "penalty")
|
41
|
+
question.qtype = parse_text(node, "qtype")
|
42
|
+
question.length = parse_text(node, "length")
|
43
|
+
question.stamp = parse_text(node, "stamp")
|
44
|
+
question.version = parse_text(node, "version")
|
45
|
+
question.hidden = parse_boolean(node, "hidden")
|
46
|
+
|
47
|
+
question
|
48
|
+
rescue Exception => e
|
49
|
+
Moodle2CC::OutputLogger.logger.info e.message
|
50
|
+
nil
|
50
51
|
end
|
51
|
-
|
52
|
-
|
53
52
|
end
|
54
53
|
end
|
@@ -1,9 +1,11 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
module Moodle2CC::Moodle2::Parsers
|
2
4
|
class QuizParser
|
3
5
|
include ParserHelper
|
4
6
|
|
5
|
-
QUIZ_XML =
|
6
|
-
QUIZ_MODULE_NAME =
|
7
|
+
QUIZ_XML = "quiz.xml"
|
8
|
+
QUIZ_MODULE_NAME = "quiz"
|
7
9
|
|
8
10
|
def initialize(backup_dir)
|
9
11
|
@backup_dir = backup_dir
|
@@ -21,65 +23,66 @@ module Moodle2CC::Moodle2::Parsers
|
|
21
23
|
activity_dir = File.join(@backup_dir, dir)
|
22
24
|
File.open(File.join(activity_dir, QUIZ_XML)) do |f|
|
23
25
|
xml = Nokogiri::XML(f)
|
24
|
-
quiz.id = xml.at_xpath(
|
25
|
-
quiz.module_id = xml.at_xpath(
|
26
|
-
quiz.name = parse_text(xml,
|
27
|
-
quiz.intro = parse_text(xml,
|
28
|
-
quiz.intro_format = parse_text(xml,
|
29
|
-
quiz.time_open = parse_text(xml,
|
30
|
-
quiz.time_close = parse_text(xml,
|
31
|
-
quiz.time_limit = parse_text(xml,
|
32
|
-
quiz.overdue_handling = parse_text(xml,
|
33
|
-
quiz.grace_period = parse_text(xml,
|
34
|
-
quiz.preferred_behavior = parse_text(xml,
|
35
|
-
quiz.attempts_number = parse_text(xml,
|
36
|
-
quiz.attempt_on_last = parse_text(xml,
|
37
|
-
quiz.grade_method = parse_text(xml,
|
38
|
-
quiz.decimal_points = parse_text(xml,
|
39
|
-
quiz.question_decimal_points = parse_text(xml,
|
40
|
-
quiz.review_attempt = parse_text(xml,
|
41
|
-
quiz.review_correctness = parse_text(xml,
|
42
|
-
quiz.review_marks = parse_text(xml,
|
43
|
-
quiz.review_specific_feedback = parse_text(xml,
|
44
|
-
quiz.review_general_feedback = parse_text(xml,
|
45
|
-
quiz.review_right_answer = parse_text(xml,
|
46
|
-
quiz.review_overall_feedback = parse_text(xml,
|
47
|
-
quiz.questions_per_page = parse_text(xml,
|
48
|
-
quiz.nav_method = parse_text(xml,
|
26
|
+
quiz.id = xml.at_xpath("/activity/quiz/@id").value
|
27
|
+
quiz.module_id = xml.at_xpath("/activity/@moduleid").value
|
28
|
+
quiz.name = parse_text(xml, "/activity/quiz/name")
|
29
|
+
quiz.intro = parse_text(xml, "/activity/quiz/intro")
|
30
|
+
quiz.intro_format = parse_text(xml, "/activity/quiz/introformat")
|
31
|
+
quiz.time_open = parse_text(xml, "/activity/quiz/timeopen")
|
32
|
+
quiz.time_close = parse_text(xml, "/activity/quiz/timeclose")
|
33
|
+
quiz.time_limit = parse_text(xml, "/activity/quiz/timelimit")
|
34
|
+
quiz.overdue_handling = parse_text(xml, "/activity/quiz/overduehandling")
|
35
|
+
quiz.grace_period = parse_text(xml, "/activity/quiz/graceperiod")
|
36
|
+
quiz.preferred_behavior = parse_text(xml, "/activity/quiz/preferredbehaviour")
|
37
|
+
quiz.attempts_number = parse_text(xml, "/activity/quiz/attempts_number")
|
38
|
+
quiz.attempt_on_last = parse_text(xml, "/activity/quiz/attemptonlast")
|
39
|
+
quiz.grade_method = parse_text(xml, "/activity/quiz/grademethod")
|
40
|
+
quiz.decimal_points = parse_text(xml, "/activity/quiz/decimalpoints")
|
41
|
+
quiz.question_decimal_points = parse_text(xml, "/activity/quiz/questiondecimalpoints")
|
42
|
+
quiz.review_attempt = parse_text(xml, "/activity/quiz/reviewattempt")
|
43
|
+
quiz.review_correctness = parse_text(xml, "/activity/quiz/reviewcorrectness")
|
44
|
+
quiz.review_marks = parse_text(xml, "/activity/quiz/reviewmarks")
|
45
|
+
quiz.review_specific_feedback = parse_text(xml, "/activity/quiz/reviewspecificfeedback")
|
46
|
+
quiz.review_general_feedback = parse_text(xml, "/activity/quiz/reviewgeneralfeedback")
|
47
|
+
quiz.review_right_answer = parse_text(xml, "/activity/quiz/reviewrightanswer")
|
48
|
+
quiz.review_overall_feedback = parse_text(xml, "/activity/quiz/reviewoverallfeedback")
|
49
|
+
quiz.questions_per_page = parse_text(xml, "/activity/quiz/questionsperpage")
|
50
|
+
quiz.nav_method = parse_text(xml, "/activity/quiz/navmethod")
|
49
51
|
|
50
|
-
quiz.shuffle_questions = parse_boolean(xml,
|
51
|
-
quiz.shuffle_answers = parse_boolean(xml,
|
52
|
+
quiz.shuffle_questions = parse_boolean(xml, "/activity/quiz/shufflequestions")
|
53
|
+
quiz.shuffle_answers = parse_boolean(xml, "/activity/quiz/shuffleanswers")
|
52
54
|
|
53
|
-
quiz.sum_grades = parse_text(xml,
|
54
|
-
quiz.grade = parse_text(xml,
|
55
|
-
quiz.time_created = parse_text(xml,
|
56
|
-
quiz.time_modified = parse_text(xml,
|
57
|
-
quiz.password = parse_text(xml,
|
58
|
-
quiz.subnet = parse_text(xml,
|
59
|
-
quiz.browser_security = parse_text(xml,
|
60
|
-
quiz.delay1 = parse_text(xml,
|
61
|
-
quiz.delay2 = parse_text(xml,
|
62
|
-
quiz.show_user_picture = parse_text(xml,
|
63
|
-
quiz.show_blocks = parse_text(xml,
|
55
|
+
quiz.sum_grades = parse_text(xml, "/activity/quiz/sumgrades")
|
56
|
+
quiz.grade = parse_text(xml, "/activity/quiz/grade")
|
57
|
+
quiz.time_created = parse_text(xml, "/activity/quiz/timecreated")
|
58
|
+
quiz.time_modified = parse_text(xml, "/activity/quiz/timemodified")
|
59
|
+
quiz.password = parse_text(xml, "/activity/quiz/password")
|
60
|
+
quiz.subnet = parse_text(xml, "/activity/quiz/subnet")
|
61
|
+
quiz.browser_security = parse_text(xml, "/activity/quiz/browsersecurity")
|
62
|
+
quiz.delay1 = parse_text(xml, "/activity/quiz/delay1")
|
63
|
+
quiz.delay2 = parse_text(xml, "/activity/quiz/delay2")
|
64
|
+
quiz.show_user_picture = parse_text(xml, "/activity/quiz/showuserpicture")
|
65
|
+
quiz.show_blocks = parse_text(xml, "/activity/quiz/showblocks")
|
64
66
|
|
65
|
-
xml.search(
|
67
|
+
xml.search("/activity/quiz/question_instances/question_instance").each do |node|
|
66
68
|
quiz.question_instances << {
|
67
|
-
:
|
68
|
-
:
|
69
|
+
question: parse_text(node, "question") || parse_text(node, "questionid"),
|
70
|
+
bank_entry_id: parse_text(node, "question_reference/questionbankentryid"),
|
71
|
+
grade: parse_text(node, "grade") || parse_text(node, "maxmark")
|
69
72
|
}
|
70
73
|
end
|
71
74
|
|
72
|
-
question_order = parse_text(xml,
|
75
|
+
question_order = parse_text(xml, "/activity/quiz/questions").to_s.split(",")
|
73
76
|
unless question_order.empty?
|
74
|
-
quiz.question_instances.sort_by!{|qi| question_order.index(qi[:question])}
|
77
|
+
quiz.question_instances.sort_by! { |qi| question_order.index(qi[:question]) || 0 }
|
75
78
|
end
|
76
79
|
|
77
|
-
xml.search(
|
80
|
+
xml.search("/activity/quiz/feedbacks/feedback").each do |node|
|
78
81
|
quiz.feedbacks << {
|
79
|
-
:
|
80
|
-
:
|
81
|
-
:
|
82
|
-
:
|
82
|
+
text: parse_text(node, "feedbacktext"),
|
83
|
+
format: parse_text(node, "feedbacktextformat"),
|
84
|
+
min_grade: parse_text(node, "mingrade"),
|
85
|
+
max_grade: parse_text(node, "maxgrade")
|
83
86
|
}
|
84
87
|
end
|
85
88
|
end
|
@@ -87,6 +90,5 @@ module Moodle2CC::Moodle2::Parsers
|
|
87
90
|
|
88
91
|
quiz
|
89
92
|
end
|
90
|
-
|
91
93
|
end
|
92
|
-
end
|
94
|
+
end
|
@@ -1,3 +1,5 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
module Moodle2CC::Moodle2Converter
|
2
4
|
module QuestionConverters
|
3
5
|
class QuestionConverter
|
@@ -13,17 +15,17 @@ module Moodle2CC::Moodle2Converter
|
|
13
15
|
end
|
14
16
|
|
15
17
|
STANDARD_CONVERSIONS = {
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
}
|
18
|
+
"description" => "text_only_question",
|
19
|
+
"essay" => "essay_question",
|
20
|
+
"shortanswer" => "short_answer_question"
|
21
|
+
}.freeze
|
20
22
|
|
21
23
|
def convert(moodle_question)
|
22
24
|
type = moodle_question.type
|
23
|
-
if type && c = @@subclasses[type]
|
25
|
+
if type && (c = @@subclasses[type])
|
24
26
|
c.new.convert_question(moodle_question)
|
25
|
-
elsif type && question_type = STANDARD_CONVERSIONS[type]
|
26
|
-
|
27
|
+
elsif type && (question_type = STANDARD_CONVERSIONS[type])
|
28
|
+
convert_question(moodle_question, question_type)
|
27
29
|
else
|
28
30
|
raise "Unknown converter type: #{type}"
|
29
31
|
end
|
@@ -31,29 +33,31 @@ module Moodle2CC::Moodle2Converter
|
|
31
33
|
|
32
34
|
def convert_question(moodle_question, question_type = nil)
|
33
35
|
canvas_question = create_canvas_question(question_type, moodle_question)
|
34
|
-
canvas_question.identifier = generate_unique_identifier_for(moodle_question.id,
|
36
|
+
canvas_question.identifier = generate_unique_identifier_for(moodle_question.id, "_quiz_question")
|
35
37
|
canvas_question.original_identifier = moodle_question.id
|
38
|
+
canvas_question.bank_entry_id = moodle_question.bank_entry_id
|
36
39
|
canvas_question.title = truncate_text(moodle_question.name)
|
37
40
|
canvas_question.points_possible = moodle_question.max_mark
|
38
41
|
canvas_question.general_feedback = moodle_question.general_feedback
|
39
42
|
canvas_question.answers = moodle_question.answers.map do |moodle_answer|
|
40
|
-
|
43
|
+
Moodle2CC::CanvasCC::Models::Answer.new(moodle_answer)
|
41
44
|
end
|
42
45
|
canvas_question.material = convert_question_text(moodle_question)
|
43
46
|
canvas_question
|
44
47
|
end
|
45
48
|
|
46
49
|
def convert_question_text(moodle_question)
|
47
|
-
material = moodle_question.question_text ||
|
50
|
+
material = moodle_question.question_text || ""
|
48
51
|
material = RDiscount.new(material).to_html if moodle_question.question_text_format.to_i == 4 # markdown
|
49
52
|
material
|
50
53
|
end
|
51
54
|
|
52
55
|
def create_canvas_question(question_type = nil, question = nil)
|
53
56
|
question_type ||= self.class.canvas_question_type
|
54
|
-
raise
|
57
|
+
raise "set canvas_question_type in question converter subclasses" unless question_type
|
58
|
+
|
55
59
|
Moodle2CC::CanvasCC::Models::Question.create(question_type)
|
56
60
|
end
|
57
61
|
end
|
58
62
|
end
|
59
|
-
end
|
63
|
+
end
|
data/lib/moodle2cc/version.rb
CHANGED
metadata
CHANGED
@@ -1,16 +1,16 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: moodle2cc
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.2.
|
4
|
+
version: 0.2.43
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Christopher Durtschi
|
8
8
|
- Kevin Carter
|
9
9
|
- Instructure
|
10
|
-
autorequire:
|
10
|
+
autorequire:
|
11
11
|
bindir: bin
|
12
12
|
cert_chain: []
|
13
|
-
date:
|
13
|
+
date: 2024-01-25 00:00:00.000000000 Z
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
16
16
|
name: rubyzip
|
@@ -409,7 +409,7 @@ homepage: https://github.com/instructure/moodle2cc
|
|
409
409
|
licenses:
|
410
410
|
- AGPLv3
|
411
411
|
metadata: {}
|
412
|
-
post_install_message:
|
412
|
+
post_install_message:
|
413
413
|
rdoc_options: []
|
414
414
|
require_paths:
|
415
415
|
- lib
|
@@ -424,9 +424,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
424
424
|
- !ruby/object:Gem::Version
|
425
425
|
version: '0'
|
426
426
|
requirements: []
|
427
|
-
|
428
|
-
|
429
|
-
signing_key:
|
427
|
+
rubygems_version: 3.3.3
|
428
|
+
signing_key:
|
430
429
|
specification_version: 4
|
431
430
|
summary: Migrates Moodle backup ZIP to IMS Common Cartridge package
|
432
431
|
test_files: []
|