census 0.1.0

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.
Files changed (79) hide show
  1. data/LICENSE +20 -0
  2. data/README.rdoc +5 -0
  3. data/Rakefile +70 -0
  4. data/VERSION +1 -0
  5. data/app/controllers/census/data_groups_controller.rb +44 -0
  6. data/app/helpers/census_helper.rb +15 -0
  7. data/app/models/answer.rb +43 -0
  8. data/app/models/choice.rb +9 -0
  9. data/app/models/data_group.rb +10 -0
  10. data/app/models/question.rb +54 -0
  11. data/app/views/census/_question_fields.html.erb +40 -0
  12. data/app/views/census/_user_answers.html.erb +10 -0
  13. data/app/views/census/_user_questions.html.erb +10 -0
  14. data/app/views/census/data_groups/_choice_fields.html.erb +4 -0
  15. data/app/views/census/data_groups/_form.html.erb +11 -0
  16. data/app/views/census/data_groups/_question_fields.html.erb +22 -0
  17. data/app/views/census/data_groups/edit.html.erb +7 -0
  18. data/app/views/census/data_groups/index.html.erb +10 -0
  19. data/app/views/census/data_groups/new.html.erb +7 -0
  20. data/config/routes.rb +8 -0
  21. data/generators/census/USAGE +1 -0
  22. data/generators/census/census_generator.rb +39 -0
  23. data/generators/census/lib/insert_commands.rb +33 -0
  24. data/generators/census/lib/rake_commands.rb +22 -0
  25. data/generators/census/templates/README +29 -0
  26. data/generators/census/templates/census.js +10 -0
  27. data/generators/census/templates/census.rb +14 -0
  28. data/generators/census/templates/factories.rb +24 -0
  29. data/generators/census/templates/migrations/with_users.rb +60 -0
  30. data/generators/census/templates/migrations/without_users.rb +54 -0
  31. data/generators/census/templates/user.rb +3 -0
  32. data/lib/census/data_type.rb +33 -0
  33. data/lib/census/user.rb +85 -0
  34. data/lib/census.rb +1 -0
  35. data/rails/init.rb +7 -0
  36. data/shoulda_macros/census.rb +35 -0
  37. data/test/controllers/data_groups_controller_test.rb +165 -0
  38. data/test/models/answer_test.rb +44 -0
  39. data/test/models/choice_test.rb +24 -0
  40. data/test/models/data_group_test.rb +12 -0
  41. data/test/models/question_test.rb +213 -0
  42. data/test/models/user_test.rb +9 -0
  43. data/test/rails_root/app/controllers/application_controller.rb +10 -0
  44. data/test/rails_root/app/helpers/application_helper.rb +3 -0
  45. data/test/rails_root/app/models/user.rb +3 -0
  46. data/test/rails_root/config/boot.rb +110 -0
  47. data/test/rails_root/config/environment.rb +8 -0
  48. data/test/rails_root/config/environments/development.rb +17 -0
  49. data/test/rails_root/config/environments/production.rb +28 -0
  50. data/test/rails_root/config/environments/test.rb +32 -0
  51. data/test/rails_root/config/initializers/backtrace_silencers.rb +7 -0
  52. data/test/rails_root/config/initializers/census.rb +14 -0
  53. data/test/rails_root/config/initializers/inflections.rb +10 -0
  54. data/test/rails_root/config/initializers/mime_types.rb +5 -0
  55. data/test/rails_root/config/initializers/new_rails_defaults.rb +21 -0
  56. data/test/rails_root/config/initializers/session_store.rb +15 -0
  57. data/test/rails_root/config/routes.rb +43 -0
  58. data/test/rails_root/db/migrate/20100406160306_create_census_tables.rb +60 -0
  59. data/test/rails_root/db/schema.rb +58 -0
  60. data/test/rails_root/test/factories/census.rb +24 -0
  61. data/test/rails_root/test/performance/browsing_test.rb +9 -0
  62. data/test/rails_root/test/test_helper.rb +38 -0
  63. data/test/rails_root/vendor/gems/acts_as_list-0.1.2/lib/acts_as_list.rb +254 -0
  64. data/test/rails_root/vendor/gems/acts_as_list-0.1.2/test/list_test.rb +369 -0
  65. data/test/rails_root/vendor/gems/inverse_of-0.0.1/install.rb +1 -0
  66. data/test/rails_root/vendor/gems/inverse_of-0.0.1/lib/inverse_of.rb +293 -0
  67. data/test/rails_root/vendor/gems/inverse_of-0.0.1/rails/init.rb +1 -0
  68. data/test/rails_root/vendor/gems/inverse_of-0.0.1/test/cases/helper.rb +28 -0
  69. data/test/rails_root/vendor/gems/inverse_of-0.0.1/test/cases/inverse_associations_test.rb +567 -0
  70. data/test/rails_root/vendor/gems/inverse_of-0.0.1/test/models/club.rb +13 -0
  71. data/test/rails_root/vendor/gems/inverse_of-0.0.1/test/models/face.rb +7 -0
  72. data/test/rails_root/vendor/gems/inverse_of-0.0.1/test/models/interest.rb +5 -0
  73. data/test/rails_root/vendor/gems/inverse_of-0.0.1/test/models/man.rb +9 -0
  74. data/test/rails_root/vendor/gems/inverse_of-0.0.1/test/models/sponsor.rb +4 -0
  75. data/test/rails_root/vendor/gems/inverse_of-0.0.1/test/models/zine.rb +3 -0
  76. data/test/rails_root/vendor/gems/inverse_of-0.0.1/test/schema/schema.rb +32 -0
  77. data/test/rails_root/vendor/gems/inverse_of-0.0.1/uninstall.rb +1 -0
  78. data/test/test_helper.rb +19 -0
  79. metadata +190 -0
@@ -0,0 +1,54 @@
1
+ class CreateCensusTables < ActiveRecord::Migration
2
+ def self.up
3
+ create_table :data_groups do |t|
4
+ t.string :name
5
+ t.integer :position
6
+ t.timestamps
7
+ end
8
+
9
+ create_table :questions do |t|
10
+ t.integer :data_group_id
11
+ t.string :data_type
12
+ t.string :prompt
13
+ t.boolean :multiple
14
+ t.boolean :other
15
+ t.integer :position
16
+ t.timestamps
17
+ end
18
+
19
+ add_index :questions, :data_group_id
20
+
21
+ create_table :choices do |t|
22
+ t.integer :question_id
23
+ t.string :value
24
+ t.integer :position
25
+ t.timestamps
26
+ end
27
+
28
+ add_index :choices, :question_id
29
+
30
+ create_table :answers do |t|
31
+ t.integer :question_id
32
+ t.integer :user_id
33
+ t.string :data
34
+ end
35
+
36
+ add_index :answers, :question_id
37
+ add_index :answers, :user_id
38
+
39
+ end
40
+
41
+ def self.down
42
+ remove_index :answers, :question_id
43
+ remove_index :answers, :user_id
44
+ drop_table :answers
45
+
46
+ remove_index :choices, :question_id
47
+ drop_table :choices
48
+
49
+ remove_index :questions, :data_group_id
50
+ drop_table :questions
51
+
52
+ drop_table :data_groups
53
+ end
54
+ end
@@ -0,0 +1,3 @@
1
+ class User < ActiveRecord::Base
2
+ include Census::User
3
+ end
@@ -0,0 +1,33 @@
1
+ module Census
2
+ class DataType
3
+ attr_accessor :name
4
+ attr_accessor :sql_transform
5
+ attr_accessor :format_data
6
+ attr_accessor :validate_data
7
+
8
+ @@data_types = []
9
+
10
+ def self.all
11
+ @@data_types
12
+ end
13
+
14
+ def self.define(name, options = {})
15
+ @@data_types << DataType.new(name, options)
16
+ end
17
+
18
+ def self.find(name)
19
+ @@data_types.select {|dt| dt.name == name}.try(:first)
20
+ end
21
+
22
+ def initialize(name, options)
23
+ @name = name
24
+ @sql_transform = options[:sql_transform] || lambda {|column_name| "#{column_name}"}
25
+ @format_data = options[:format_data] || lambda {|data| data}
26
+ @validate_data = options[:validate_data] || lambda {|data| nil}
27
+ end
28
+
29
+ def to_s
30
+ @name
31
+ end
32
+ end
33
+ end
@@ -0,0 +1,85 @@
1
+ module Census
2
+ module User
3
+
4
+ # Hook for all Census::User modules.
5
+ #
6
+ # If you need to override parts of Census::User,
7
+ # extend and include à la carte.
8
+ #
9
+ # @example
10
+ # extend ClassMethods
11
+ # include InstanceMethods
12
+ # include Callbacks
13
+ #
14
+ # @see ClassMethods
15
+ # @see InstanceMethods
16
+ # @see Callbacks
17
+ def self.included(model)
18
+ model.extend(ClassMethods)
19
+
20
+ model.send(:include, InstanceMethods)
21
+ model.send(:include, Associations)
22
+ model.send(:include, Callbacks)
23
+ end
24
+
25
+ module Associations
26
+ # Hook for defining associations.
27
+ def self.included(model)
28
+ model.class_eval do
29
+ has_many :answers, :dependent => :destroy
30
+ accepts_nested_attributes_for :answers, :reject_if => lambda { |a| a[:data].blank? }
31
+ end
32
+ end
33
+ end
34
+
35
+ module Callbacks
36
+ # Hook for callbacks.
37
+ #
38
+ # empty answers are removed after_save.
39
+ def self.included(model)
40
+ model.class_eval do
41
+ after_save :remove_empty_answers
42
+ end
43
+ end
44
+ end
45
+
46
+ module InstanceMethods
47
+ #
48
+ # Returns this user's first answer for the given question, or a new empty
49
+ # answer if the user has not answered the question.
50
+ #
51
+ def first_answer_for(question)
52
+ answers.select {|a| a.question == question}.first || answers.build(:question => question, :data => '')
53
+ end
54
+
55
+ #
56
+ # Returns an array of this user's answers for the given question. The returned
57
+ # array will be empty if the user has not answered this question.
58
+ #
59
+ def all_answers_for(question)
60
+ answers.select {|a| a.question == question}
61
+ end
62
+
63
+ #
64
+ # Returns this user's answer for a specific choice under a multiple-choice
65
+ # question, or a new empty answer if the user did not select the given choice.
66
+ #
67
+ def answer_for_choice(choice)
68
+ answers.select {|a| a.question == choice.question && a.data == choice.value}.first || answers.build(:question => choice.question, :data => '')
69
+ end
70
+
71
+ private
72
+
73
+ #
74
+ # After save callback, used to remove blank answers
75
+ #
76
+ def remove_empty_answers
77
+ answers.each {|answer| answer.destroy if answer.data.blank? }
78
+ end
79
+ end
80
+
81
+ module ClassMethods
82
+ end
83
+
84
+ end
85
+ end
data/lib/census.rb ADDED
@@ -0,0 +1 @@
1
+ require 'census/user'
data/rails/init.rb ADDED
@@ -0,0 +1,7 @@
1
+ require 'acts_as_list'
2
+ require 'inverse_of'
3
+ require 'census'
4
+
5
+ config.to_prepare do
6
+ ApplicationController.helper(CensusHelper)
7
+ end
@@ -0,0 +1,35 @@
1
+ module Census
2
+ module Shoulda
3
+
4
+ def should_accept_nested_attributes_for(*attr_names)
5
+ klass = self.name.gsub(/Test$/, '').constantize
6
+
7
+ context "#{klass}" do
8
+ attr_names.each do |association_name|
9
+ should "accept nested attrs for #{association_name}" do
10
+ meth = "#{association_name}_attributes="
11
+ assert ([meth,meth.to_sym].any?{ |m| klass.instance_methods.include?(m) }),
12
+ "#{klass} does not accept nested attributes for #{association_name}"
13
+ end
14
+ end
15
+ end
16
+ end
17
+
18
+ def should_act_as_list
19
+ klass = self.name.gsub(/Test$/, '').constantize
20
+
21
+ context "To support acts_as_list" do
22
+ should_have_db_column('position', :type => :integer)
23
+ end
24
+
25
+ should "include ActsAsList methods" do
26
+ assert klass.include?(ActsAsList::InstanceMethods)
27
+ end
28
+
29
+ should_have_instance_methods :acts_as_list_class, :position_column, :scope_condition
30
+ end
31
+
32
+ end
33
+ end
34
+
35
+ Test::Unit::TestCase.extend(Census::Shoulda)
@@ -0,0 +1,165 @@
1
+ require 'test_helper'
2
+
3
+ class DataGroupsControllerTest < ActionController::TestCase
4
+
5
+ tests Census::DataGroupsController
6
+
7
+ should_route :get, '/census/admin',
8
+ :controller => 'census/data_groups', :action => 'index'
9
+
10
+ should_route :get, '/census/data_groups/new',
11
+ :controller => 'census/data_groups', :action => 'new'
12
+
13
+ should_route :post, '/census/data_groups',
14
+ :controller => 'census/data_groups', :action => 'create'
15
+
16
+ should_route :get, '/census/data_groups/1/edit',
17
+ :controller => 'census/data_groups', :action => 'edit', :id => '1'
18
+
19
+ should_route :put, '/census/data_groups/1',
20
+ :controller => 'census/data_groups', :action => 'update', :id => '1'
21
+
22
+ should_route :delete, '/census/data_groups/1',
23
+ :controller => 'census/data_groups', :action => 'destroy', :id => '1'
24
+
25
+ context 'The Census::DataGroupsController' do
26
+
27
+ context 'using GET to index' do
28
+
29
+ setup do
30
+ @group = Factory(:data_group)
31
+ get :index
32
+ end
33
+
34
+ should_respond_with :success
35
+ should_respond_with_content_type :html
36
+ should_render_template :index
37
+ should_assign_to :data_groups
38
+
39
+ end
40
+
41
+ context 'using GET to new' do
42
+
43
+ setup do
44
+ get :new
45
+ end
46
+
47
+ should_respond_with :success
48
+ should_respond_with_content_type :html
49
+ should_render_template :new
50
+ should_assign_to :data_group
51
+
52
+ should 'have a new data group record' do
53
+ assert assigns(:data_group).new_record?
54
+ end
55
+
56
+ end
57
+
58
+ context 'using POST to create' do
59
+
60
+ context 'with invalid attributes' do
61
+
62
+ setup do
63
+ DataGroup.any_instance.stubs(:valid?).returns(false)
64
+ post :create, :data_group => Factory.attributes_for(:data_group)
65
+ end
66
+
67
+ should_respond_with :unprocessable_entity
68
+ should_respond_with_content_type :html
69
+ should_render_template :new
70
+ should_assign_to :data_group
71
+
72
+ should 'not create the data group' do
73
+ assert assigns(:data_group).new_record?
74
+ end
75
+
76
+ end
77
+
78
+ context 'with valid attributes' do
79
+
80
+ setup do
81
+ post :create, :data_group => Factory.attributes_for(:data_group)
82
+ end
83
+
84
+ should_respond_with :redirect
85
+ should_assign_to :data_group
86
+ should_redirect_to('census admin page') { census_admin_url }
87
+
88
+ should 'create the data group' do
89
+ assert !assigns(:data_group).new_record?
90
+ end
91
+
92
+ end
93
+
94
+ end
95
+
96
+ context 'using GET to edit' do
97
+
98
+ setup do
99
+ @group = Factory(:data_group)
100
+ get :edit, :id => @group.to_param
101
+ end
102
+
103
+ should_respond_with :success
104
+ should_respond_with_content_type :html
105
+ should_render_template :edit
106
+ should_assign_to(:data_group) { @group }
107
+
108
+ end
109
+
110
+ context 'using PUT to update' do
111
+
112
+ context 'with valid attributes' do
113
+
114
+ setup do
115
+ @group = Factory(:data_group)
116
+ put :update, :id => @group.to_param, :data_group => {:name => 'CHANGED'}
117
+ end
118
+
119
+ should_respond_with :redirect
120
+ should_assign_to(:data_group) { @group }
121
+ should_redirect_to('census admin page') { census_admin_url }
122
+
123
+ should 'update the data group' do
124
+ assert_equal('CHANGED', @group.reload.name)
125
+ end
126
+
127
+ end
128
+
129
+ context 'with invalid attributes' do
130
+
131
+ setup do
132
+ @group = Factory(:data_group)
133
+ DataGroup.any_instance.stubs(:valid? => false)
134
+ put :update, :id => @group.to_param, :data_group => {:name => 'CHANGED'}
135
+ end
136
+
137
+ should_respond_with :unprocessable_entity
138
+ should_respond_with_content_type :html
139
+ should_assign_to(:data_group) { @group }
140
+ should_render_template :edit
141
+
142
+ end
143
+
144
+ end
145
+
146
+ context 'using DELETE to destroy' do
147
+
148
+ setup do
149
+ @group = Factory(:data_group)
150
+ delete :destroy, :id => @group.to_param
151
+ end
152
+
153
+ should_respond_with :redirect
154
+ should_assign_to(:data_group) { @group }
155
+ should_redirect_to('census admin page') { census_admin_url }
156
+
157
+ should 'destroy the data group' do
158
+ assert_nil(DataGroup.find_by_id(@group.id))
159
+ end
160
+
161
+ end
162
+
163
+ end
164
+
165
+ end
@@ -0,0 +1,44 @@
1
+ require 'test_helper'
2
+
3
+ class AnswerTest < ActiveSupport::TestCase
4
+
5
+ context "An Answer" do
6
+
7
+ setup do
8
+ @answer = Factory(:answer)
9
+ end
10
+
11
+ subject { @answer }
12
+
13
+ should_belong_to :question
14
+ should_belong_to :user
15
+
16
+ should_validate_presence_of :question,
17
+ :user
18
+
19
+ should_allow_mass_assignment_of :data
20
+
21
+ context "getting formatted data" do
22
+
23
+ should "format strings" do
24
+ a = Factory(:answer, :question => Factory(:question, :data_type => 'String'), :data => 'abc123')
25
+ assert_equal 'abc123', a.formatted_data
26
+ end
27
+
28
+ should "format numbers" do
29
+ a = Factory(:answer, :question => Factory(:question, :data_type => 'Number'), :data => '5389')
30
+ assert_equal 5389, a.formatted_data
31
+ end
32
+
33
+ should "format booleans" do
34
+ a = Factory(:answer, :question => Factory(:question, :data_type => 'Yes/No'), :data => '0')
35
+ assert_equal false, a.formatted_data
36
+ a.data = '1'
37
+ assert_equal true, a.formatted_data
38
+ end
39
+
40
+ end
41
+
42
+ end
43
+
44
+ end
@@ -0,0 +1,24 @@
1
+ require 'test_helper'
2
+
3
+ class ChoiceTest < ActiveSupport::TestCase
4
+
5
+ context "A Choice" do
6
+
7
+ setup do
8
+ @choice = Factory(:choice)
9
+ end
10
+
11
+ subject { @choice }
12
+
13
+ should_belong_to :question
14
+
15
+ should_act_as_list
16
+
17
+ should_validate_presence_of :value,
18
+ :question
19
+
20
+ should_allow_mass_assignment_of :value
21
+
22
+ end
23
+
24
+ end
@@ -0,0 +1,12 @@
1
+ require 'test_helper'
2
+
3
+ class DataGroupTest < ActiveSupport::TestCase
4
+
5
+ should_have_many :questions, :dependent => :destroy
6
+ should_accept_nested_attributes_for :questions
7
+
8
+ should_validate_presence_of :name
9
+
10
+ should_act_as_list
11
+
12
+ end
@@ -0,0 +1,213 @@
1
+ require 'test_helper'
2
+
3
+ class QuestionTest < ActiveSupport::TestCase
4
+
5
+ context "A Question" do
6
+
7
+ setup do
8
+ @question = Factory(:question)
9
+ end
10
+
11
+ subject { @question }
12
+
13
+ should_belong_to :data_group
14
+ should_have_many :choices, :dependent => :destroy
15
+ should_have_many :answers, :dependent => :destroy
16
+
17
+ should_act_as_list
18
+
19
+ should_validate_presence_of :prompt,
20
+ :data_group
21
+
22
+ should_allow_mass_assignment_of :data_type,
23
+ :prompt,
24
+ :multiple,
25
+ :other
26
+
27
+ should_accept_nested_attributes_for :choices
28
+
29
+ should "return a default sql transform" do
30
+ assert '"?"', @question.sql_transform
31
+ end
32
+
33
+ context "with choices" do
34
+
35
+ setup do
36
+ @choice1 = Factory(:choice, :value => 'Choice 1', :question => @question)
37
+ @choice2 = Factory(:choice, :value => 'Choice 2', :question => @question)
38
+ @choice3 = Factory(:choice, :value => 'Choice 3', :question => @question)
39
+ end
40
+
41
+ should "allow answers that match the choices" do
42
+ assert Factory.build(:answer, :question => @question, :data => 'Choice 1').valid?
43
+ assert Factory.build(:answer, :question => @question, :data => 'Choice 3').valid?
44
+ end
45
+
46
+ should "not allow answers that don't match the choices" do
47
+ assert !Factory.build(:answer, :question => @question, :data => 'Blah').valid?
48
+ end
49
+
50
+ context "that allows user-supplied 'other' answer" do
51
+
52
+ setup do
53
+ @question.update_attribute(:other, true)
54
+ end
55
+
56
+ should "allow answers that don't match the choices" do
57
+ assert Factory.build(:answer, :question => @question, :data => 'Blah').valid?
58
+ end
59
+
60
+ end
61
+
62
+ end
63
+
64
+ context "that can't have multiple answers" do
65
+
66
+ setup do
67
+ @question.update_attribute(:multiple, false)
68
+ @user = Factory(:user)
69
+ end
70
+
71
+ should "not be able to create multiple answers" do
72
+ assert @question.answers.create(:data => 'Answer 1', :user => @user)
73
+ assert !Factory.build(:answer, :question => @question, :data => 'Answer 2', :user => @user).valid?
74
+ end
75
+
76
+ end
77
+
78
+ context "that can have multiple answers" do
79
+
80
+ setup do
81
+ @question.update_attribute(:multiple, true)
82
+ end
83
+
84
+ should "be able to create multiple answers" do
85
+ assert @question.answers.create(:data => 'Answer 1')
86
+ assert @question.answers.create(:data => 'Answer 2')
87
+ end
88
+
89
+ end
90
+
91
+ context "with String data type" do
92
+
93
+ setup do
94
+ @question.data_type = 'String'
95
+ end
96
+
97
+ should "return a default sql transform" do
98
+ assert_equal "?", @question.sql_transform
99
+ end
100
+
101
+ context "with answers" do
102
+
103
+ setup do
104
+ @answer1 = Factory(:answer, :question => @question, :data => 'findme')
105
+ @answer2 = Factory(:answer, :question => @question, :data => 'dont_findme')
106
+ @answer3 = Factory(:answer, :question => @question, :data => 'findme_too')
107
+ end
108
+
109
+ should "find answers matching a given string" do
110
+ assert @question.find_answers_matching('findme').include?(@answer1)
111
+ end
112
+
113
+ should "not find answers not matching the given string" do
114
+ assert !@question.find_answers_matching('findme').include?(@answer2)
115
+ end
116
+
117
+ should "find answers matching an array of strings" do
118
+ result = @question.find_answers_matching(['findme', 'findme_too'])
119
+ assert result.include?(@answer1)
120
+ assert result.include?(@answer3)
121
+ assert !result.include?(@answer2)
122
+ end
123
+
124
+ end
125
+
126
+ end
127
+
128
+ context "with Number data type" do
129
+
130
+ setup do
131
+ @question.data_type = 'Number'
132
+ end
133
+
134
+ should "return an integer sql transform" do
135
+ assert_equal "CAST(? AS SIGNED INTEGER)", @question.sql_transform
136
+ end
137
+
138
+ context "with answers" do
139
+
140
+ setup do
141
+ @answer1 = Factory(:answer, :question => @question, :data => '123')
142
+ @answer2 = Factory(:answer, :question => @question, :data => '125')
143
+ @answer3 = Factory(:answer, :question => @question, :data => '127')
144
+ end
145
+
146
+ should "find answers matching a given string" do
147
+ assert @question.find_answers_matching('123').include?(@answer1)
148
+ end
149
+
150
+ should "not find answers not matching the given string" do
151
+ assert !@question.find_answers_matching('123').include?(@answer2)
152
+ end
153
+
154
+ should "find answers matching a given number" do
155
+ assert @question.find_answers_matching(123).include?(@answer1)
156
+ end
157
+
158
+ should "not find answers not matching the given number" do
159
+ assert !@question.find_answers_matching(123).include?(@answer2)
160
+ end
161
+
162
+ should "find answers in a given range" do
163
+ result = @question.find_answers_matching(123..126)
164
+ assert result.include?(@answer1)
165
+ assert result.include?(@answer2)
166
+ assert !result.include?(@answer3)
167
+ end
168
+
169
+ end
170
+
171
+ end
172
+
173
+ context "with Yes/No data type" do
174
+
175
+ setup do
176
+ @question.data_type = 'Yes/No'
177
+ end
178
+
179
+ should "return a boolean sql transform" do
180
+ assert_equal "CAST(? AS CHAR)", @question.sql_transform
181
+ end
182
+
183
+ context "with answers" do
184
+
185
+ setup do
186
+ @answer1 = Factory(:answer, :question => @question)
187
+ @answer1.update_attribute(:data, false)
188
+ @answer2 = Factory(:answer, :question => @question, :data => true)
189
+ end
190
+
191
+ should "find answers matching true" do
192
+ assert @question.find_answers_matching(true).include?(@answer2)
193
+ end
194
+
195
+ should "not find answers not matching true" do
196
+ assert !@question.find_answers_matching(true).include?(@answer1)
197
+ end
198
+
199
+ should "find answers matching false" do
200
+ assert @question.find_answers_matching(false).include?(@answer1)
201
+ end
202
+
203
+ should "not find answers not matching false" do
204
+ assert !@question.find_answers_matching(false).include?(@answer2)
205
+ end
206
+
207
+ end
208
+
209
+ end
210
+
211
+ end
212
+
213
+ end
@@ -0,0 +1,9 @@
1
+ require 'test_helper'
2
+
3
+ class UserTest < ActiveSupport::TestCase
4
+
5
+ should_have_many :answers, :dependent => :destroy
6
+ should_accept_nested_attributes_for :answers
7
+ should_allow_mass_assignment_of :answers_attributes
8
+
9
+ end