active_record_survey 0.1.39 → 0.1.40
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/lib/active_record_survey/instance_node.rb +24 -19
- data/lib/active_record_survey/node.rb +8 -1
- data/lib/active_record_survey/version.rb +1 -1
- data/spec/active_record_survey/instance_node_spec.rb +5 -0
- data/spec/active_record_survey/instance_spec.rb +93 -0
- data/spec/active_record_survey/node/answer_spec.rb +15 -0
- data/spec/factories/active_record_survey/survey.rb +75 -0
- metadata +6 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 0ec49942bdb8de3f5ea1c79c524a7756c0c23ca5
|
4
|
+
data.tar.gz: 4a951bb87e0f5b9990eb1b6648fe41652a18426e
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 4095f4b2118338abeed4e6a9c69f134479491ff45af9b997a8389b7f6562df34318c0b0ce842217599c1b43128e108c083ca57421de52723e5d4fe360554bba1
|
7
|
+
data.tar.gz: 57dcd1b8f5c50ccfcb43d551fb6d6ae0414f6f39cfd1527418dfe761ddc4ba50721c26e0ff257ff83bc1744c2d4e20ce8e881a9f0358ab95315a2579838c0edf
|
@@ -7,28 +7,33 @@ module ActiveRecordSurvey
|
|
7
7
|
validates_presence_of :instance
|
8
8
|
|
9
9
|
validate do |instance_node|
|
10
|
-
#
|
11
|
-
if
|
12
|
-
instance_node.errors[:base] << "
|
13
|
-
|
10
|
+
# No node to begin with!
|
11
|
+
if self.node.nil?
|
12
|
+
instance_node.errors[:base] << "INVALID_NODE"
|
13
|
+
else
|
14
|
+
# This instance_node has no valid path to the root node
|
15
|
+
if !self.node.instance_node_path_to_root?(self)
|
16
|
+
instance_node.errors[:base] << "INVALID_PATH"
|
17
|
+
end
|
14
18
|
|
15
|
-
|
19
|
+
parent_nodes = self.node.survey.node_maps.select { |i| i.node == self.node }.collect { |j| j.parent }
|
16
20
|
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
21
|
+
# Two instance_nodes on the same node for this instance
|
22
|
+
if self.instance.instance_nodes.select { |i|
|
23
|
+
# We don't care about paths that are going to be deleted
|
24
|
+
!i.marked_for_destruction?
|
25
|
+
}.select { |i|
|
26
|
+
# And the two arrays
|
27
|
+
# Two votes share a parent (this means a question has two answers for this instance)
|
28
|
+
(i.node.survey.node_maps.select { |j| i.node == j.node }.collect { |j| j.parent } & parent_nodes).length > 0
|
29
|
+
}.length > 1
|
30
|
+
instance_node.errors[:base] << "DUPLICATE_PATH"
|
31
|
+
end
|
28
32
|
|
29
|
-
|
30
|
-
|
31
|
-
|
33
|
+
# Validate against the associated node
|
34
|
+
if !self.node.validate_instance_node(self)
|
35
|
+
instance_node.errors[:base] << "INVALID"
|
36
|
+
end
|
32
37
|
end
|
33
38
|
end
|
34
39
|
end
|
@@ -92,7 +92,7 @@ module ActiveRecordSurvey
|
|
92
92
|
|
93
93
|
# Whether there is a valid answer path from this node to the root node for the instance
|
94
94
|
def instance_node_path_to_root?(instance_node)
|
95
|
-
instance_nodes = instance_node.instance.instance_nodes.select { |i| i.node
|
95
|
+
instance_nodes = instance_node.instance.instance_nodes.select { |i| i.node == self }
|
96
96
|
|
97
97
|
# if ::ActiveRecordSurvey::Node::Answer but no votes, not a valid path
|
98
98
|
if self.class.ancestors.include?(::ActiveRecordSurvey::Node::Answer) &&
|
@@ -100,6 +100,13 @@ module ActiveRecordSurvey
|
|
100
100
|
return false
|
101
101
|
end
|
102
102
|
|
103
|
+
# if ::ActiveRecordSurvey::Node::Question but no answers, so needs at least one vote directly on itself
|
104
|
+
if self.class.ancestors.include?(::ActiveRecordSurvey::Node::Question) &&
|
105
|
+
(self.answers.length === 0) &&
|
106
|
+
(instance_nodes.length === 0)
|
107
|
+
return false
|
108
|
+
end
|
109
|
+
|
103
110
|
# Start at each node_map of this node
|
104
111
|
# Find the parent node ma
|
105
112
|
paths = self.survey.node_maps.select { |i| i.node == self }.collect { |node_map|
|
@@ -0,0 +1,93 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe ActiveRecordSurvey::Instance, :instance_spec => true do
|
4
|
+
before(:each) do
|
5
|
+
@survey = FactoryGirl.build(:boolean_survey)
|
6
|
+
@survey.save
|
7
|
+
|
8
|
+
@survey.questions.each { |q|
|
9
|
+
@q1 = q if q.text == "Q1"
|
10
|
+
@q2 = q if q.text == "Q2"
|
11
|
+
@q3 = q if q.text == "Q3"
|
12
|
+
@q4 = q if q.text == "Q4"
|
13
|
+
@q5 = q if q.text == "Q5"
|
14
|
+
}
|
15
|
+
|
16
|
+
@q1.answers.each { |a|
|
17
|
+
@q1_a1 = a if a.text == "Q1 A1"
|
18
|
+
@q1_a2 = a if a.text == "Q1 A2"
|
19
|
+
}
|
20
|
+
@q2.answers.each { |a|
|
21
|
+
@q2_a1 = a if a.text == "Q2 A1"
|
22
|
+
@q2_a2 = a if a.text == "Q2 A2"
|
23
|
+
}
|
24
|
+
@q3.answers.each { |a|
|
25
|
+
@q3_a1 = a if a.text == "Q3 A1"
|
26
|
+
@q3_a2 = a if a.text == "Q3 A2"
|
27
|
+
}
|
28
|
+
@q4.answers.each { |a|
|
29
|
+
@q4_a1 = a if a.text == "Q4 A1"
|
30
|
+
@q4_a2 = a if a.text == "Q4 A2"
|
31
|
+
}
|
32
|
+
@instance = ActiveRecordSurvey::Instance.new(:survey => @survey)
|
33
|
+
end
|
34
|
+
|
35
|
+
describe "#invalid?" do
|
36
|
+
it 'should not allow not starting from the root' do
|
37
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q3_a1)
|
38
|
+
|
39
|
+
expect(@instance.invalid?).to eq(true)
|
40
|
+
end
|
41
|
+
|
42
|
+
it 'should not allow impossible answers' do
|
43
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q1_a1)
|
44
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q3_a1)
|
45
|
+
|
46
|
+
expect(@instance.invalid?).to eq(true)
|
47
|
+
end
|
48
|
+
|
49
|
+
it 'should fail when boolean answer is not passed an value of [0,1]' do
|
50
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q1_a1)
|
51
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q2_a1)
|
52
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q2_a2)
|
53
|
+
|
54
|
+
expect(@instance.invalid?).to eq(true)
|
55
|
+
end
|
56
|
+
|
57
|
+
it 'should allow an incompleted survey, even if a missing part is a question node only' do
|
58
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q1_a1)
|
59
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q2_a1, :value => 1)
|
60
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q2_a2, :value => 0)
|
61
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q3_a1)
|
62
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q5)
|
63
|
+
|
64
|
+
expect(@instance.invalid?).to eq(true)
|
65
|
+
end
|
66
|
+
end
|
67
|
+
|
68
|
+
describe "#valid?" do
|
69
|
+
it 'should allow a single answer' do
|
70
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q1_a1)
|
71
|
+
|
72
|
+
expect(@instance.valid?).to eq(true)
|
73
|
+
end
|
74
|
+
|
75
|
+
it 'should allow multiple answers' do
|
76
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q1_a1)
|
77
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q2_a1, :value => 0)
|
78
|
+
|
79
|
+
expect(@instance.valid?).to eq(true)
|
80
|
+
end
|
81
|
+
|
82
|
+
it 'should allow a completed survey' do
|
83
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q1_a1)
|
84
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q2_a1, :value => 1)
|
85
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q2_a2, :value => 0)
|
86
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q3_a1)
|
87
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q4)
|
88
|
+
@instance.instance_nodes << ActiveRecordSurvey::InstanceNode.new(:instance => @instance, :node => @q5)
|
89
|
+
|
90
|
+
expect(@instance.valid?).to eq(true)
|
91
|
+
end
|
92
|
+
end
|
93
|
+
end
|
@@ -345,6 +345,21 @@ describe ActiveRecordSurvey::Node::Answer, :answer_spec => true do
|
|
345
345
|
end
|
346
346
|
|
347
347
|
describe '#next_question' do
|
348
|
+
it 'should not have a next question if not linked anywhere' do
|
349
|
+
survey = FactoryGirl.build(:survey1)
|
350
|
+
survey.save
|
351
|
+
|
352
|
+
q2 = survey.questions.select { |i|
|
353
|
+
i.text == "Question #2"
|
354
|
+
}.first
|
355
|
+
|
356
|
+
q2_a1 = q2.answers.select { |i|
|
357
|
+
i.text == "Q2 Answer #1"
|
358
|
+
}.first
|
359
|
+
|
360
|
+
expect(q2_a1.next_question).to be(nil)
|
361
|
+
end
|
362
|
+
|
348
363
|
it 'should get the next question' do
|
349
364
|
expected = {
|
350
365
|
"Q1" => {
|
@@ -1,5 +1,72 @@
|
|
1
1
|
module FactoryGirlSurveyHelpers
|
2
2
|
extend self
|
3
|
+
def build_survey1(survey)
|
4
|
+
q1 = survey.questions.build(:type => "ActiveRecordSurvey::Node::Question", :text => "Question #1", :survey => survey)
|
5
|
+
q1_a1 = ActiveRecordSurvey::Node::Answer.new(:text => "Q1 Answer #1")
|
6
|
+
q1_a2 = ActiveRecordSurvey::Node::Answer.new(:text => "Q1 Answer #2")
|
7
|
+
q1.build_answer(q1_a1)
|
8
|
+
q1.build_answer(q1_a2)
|
9
|
+
|
10
|
+
q2 = survey.questions.build(:type => "ActiveRecordSurvey::Node::Question", :text => "Question #2", :survey => survey)
|
11
|
+
q2_a1 = ActiveRecordSurvey::Node::Answer.new(:text => "Q2 Answer #1")
|
12
|
+
q2_a2 = ActiveRecordSurvey::Node::Answer.new(:text => "Q2 Answer #2")
|
13
|
+
q2.build_answer(q2_a1)
|
14
|
+
q2.build_answer(q2_a2)
|
15
|
+
|
16
|
+
q3 = survey.questions.build(:type => "ActiveRecordSurvey::Node::Question", :text => "Question #3", :survey => survey)
|
17
|
+
q3_a1 = ActiveRecordSurvey::Node::Answer.new(:text => "Q3 Answer #1")
|
18
|
+
q3_a2 = ActiveRecordSurvey::Node::Answer.new(:text => "Q3 Answer #2")
|
19
|
+
q3.build_answer(q3_a1)
|
20
|
+
q3.build_answer(q3_a2)
|
21
|
+
|
22
|
+
q4 = survey.questions.build(:type => "ActiveRecordSurvey::Node::Question", :text => "Question #4", :survey => survey)
|
23
|
+
|
24
|
+
q5 = survey.questions.build(:type => "ActiveRecordSurvey::Node::Question", :text => "Question #5", :survey => survey)
|
25
|
+
|
26
|
+
q1_a1.build_link(q2)
|
27
|
+
q1_a2.build_link(q3)
|
28
|
+
q2_a2.build_link(q3)
|
29
|
+
|
30
|
+
q3_a1.build_link(q4)
|
31
|
+
q3_a2.build_link(q4)
|
32
|
+
|
33
|
+
q4.build_link(q5)
|
34
|
+
end
|
35
|
+
|
36
|
+
def build_boolean_survey(survey)
|
37
|
+
q1 = survey.questions.build(:type => "ActiveRecordSurvey::Node::Question", :text => "Q1", :survey => survey)
|
38
|
+
q1_a1 = ActiveRecordSurvey::Node::Answer.new(:text => "Q1 A1")
|
39
|
+
q1_a2 = ActiveRecordSurvey::Node::Answer.new(:text => "Q1 A2")
|
40
|
+
q1.build_answer(q1_a1)
|
41
|
+
q1.build_answer(q1_a2)
|
42
|
+
|
43
|
+
q2 = survey.questions.build(:type => "ActiveRecordSurvey::Node::Question", :text => "Q2", :survey => survey)
|
44
|
+
q2_a1 = ActiveRecordSurvey::Node::Answer::Boolean.new(:text => "Q2 A1")
|
45
|
+
q2_a2 = ActiveRecordSurvey::Node::Answer::Boolean.new(:text => "Q2 A2")
|
46
|
+
q2.build_answer(q2_a1)
|
47
|
+
q2.build_answer(q2_a2)
|
48
|
+
|
49
|
+
q3 = survey.questions.build(:type => "ActiveRecordSurvey::Node::Question", :text => "Q3", :survey => survey)
|
50
|
+
q3_a1 = ActiveRecordSurvey::Node::Answer.new(:text => "Q3 A1")
|
51
|
+
q3_a2 = ActiveRecordSurvey::Node::Answer.new(:text => "Q3 A2")
|
52
|
+
q3.build_answer(q3_a1)
|
53
|
+
q3.build_answer(q3_a2)
|
54
|
+
|
55
|
+
q4 = survey.questions.build(:type => "ActiveRecordSurvey::Node::Question", :text => "Q4", :survey => survey)
|
56
|
+
|
57
|
+
q5 = survey.questions.build(:type => "ActiveRecordSurvey::Node::Question", :text => "Q5", :survey => survey)
|
58
|
+
|
59
|
+
q1_a1.build_link(q2)
|
60
|
+
q1_a2.build_link(q3)
|
61
|
+
|
62
|
+
q2_a2.build_link(q3)
|
63
|
+
|
64
|
+
q3_a1.build_link(q4)
|
65
|
+
q3_a2.build_link(q4)
|
66
|
+
|
67
|
+
q4.build_link(q5)
|
68
|
+
end
|
69
|
+
|
3
70
|
def build_simple_survey(survey)
|
4
71
|
q1 = survey.questions.build(:type => "ActiveRecordSurvey::Node::Question", :text => "Question #1", :survey => survey)
|
5
72
|
q1_a1 = ActiveRecordSurvey::Node::Answer.new(:text => "Q1 Answer #1")
|
@@ -106,6 +173,10 @@ FactoryGirl.define do
|
|
106
173
|
|
107
174
|
end
|
108
175
|
|
176
|
+
factory :survey1, parent: :survey do |f|
|
177
|
+
after(:build) { |survey| FactoryGirlSurveyHelpers.build_survey1(survey) }
|
178
|
+
end
|
179
|
+
|
109
180
|
factory :simple_survey, parent: :survey do |f|
|
110
181
|
after(:build) { |survey| FactoryGirlSurveyHelpers.build_simple_survey(survey) }
|
111
182
|
end
|
@@ -113,4 +184,8 @@ FactoryGirl.define do
|
|
113
184
|
factory :basic_survey, parent: :survey do |f|
|
114
185
|
after(:build) { |survey| FactoryGirlSurveyHelpers.build_basic_survey(survey) }
|
115
186
|
end
|
187
|
+
|
188
|
+
factory :boolean_survey, parent: :survey do |f|
|
189
|
+
after(:build) { |survey| FactoryGirlSurveyHelpers.build_boolean_survey(survey) }
|
190
|
+
end
|
116
191
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: active_record_survey
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.
|
4
|
+
version: 0.1.40
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Butch Marshall
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2016-08-
|
11
|
+
date: 2016-08-28 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: activerecord
|
@@ -163,6 +163,8 @@ files:
|
|
163
163
|
- lib/generators/active_record_survey/templates/migration_0.1.0.rb
|
164
164
|
- lib/generators/active_record_survey/templates/migration_0.1.26.rb
|
165
165
|
- rspec_rvm
|
166
|
+
- spec/active_record_survey/instance_node_spec.rb
|
167
|
+
- spec/active_record_survey/instance_spec.rb
|
166
168
|
- spec/active_record_survey/node/answer/boolean_spec.rb
|
167
169
|
- spec/active_record_survey/node/answer/rank_spec.rb
|
168
170
|
- spec/active_record_survey/node/answer/scale_spec.rb
|
@@ -199,6 +201,8 @@ signing_key:
|
|
199
201
|
specification_version: 4
|
200
202
|
summary: Surveys using activerecord
|
201
203
|
test_files:
|
204
|
+
- spec/active_record_survey/instance_node_spec.rb
|
205
|
+
- spec/active_record_survey/instance_spec.rb
|
202
206
|
- spec/active_record_survey/node/answer/boolean_spec.rb
|
203
207
|
- spec/active_record_survey/node/answer/rank_spec.rb
|
204
208
|
- spec/active_record_survey/node/answer/scale_spec.rb
|