couchrest_model 2.1.0.rc1 → 2.2.0.beta1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (56) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +1 -1
  3. data/.travis.yml +15 -4
  4. data/Gemfile.activesupport-4.x +4 -0
  5. data/Gemfile.activesupport-5.x +4 -0
  6. data/README.md +2 -0
  7. data/VERSION +1 -1
  8. data/couchrest_model.gemspec +3 -2
  9. data/history.md +14 -1
  10. data/lib/couchrest/model/associations.rb +3 -8
  11. data/lib/couchrest/model/base.rb +15 -7
  12. data/lib/couchrest/model/casted_array.rb +22 -34
  13. data/lib/couchrest/model/configuration.rb +2 -0
  14. data/lib/couchrest/model/design.rb +4 -3
  15. data/lib/couchrest/model/designs/view.rb +37 -32
  16. data/lib/couchrest/model/dirty.rb +93 -19
  17. data/lib/couchrest/model/embeddable.rb +2 -14
  18. data/lib/couchrest/model/extended_attachments.rb +2 -4
  19. data/lib/couchrest/model/persistence.rb +14 -17
  20. data/lib/couchrest/model/properties.rb +46 -54
  21. data/lib/couchrest/model/property.rb +0 -3
  22. data/lib/couchrest/model/proxyable.rb +20 -4
  23. data/lib/couchrest/model/validations/uniqueness.rb +4 -1
  24. data/lib/couchrest_model.rb +2 -2
  25. data/spec/fixtures/models/article.rb +1 -1
  26. data/spec/fixtures/models/card.rb +2 -1
  27. data/spec/fixtures/models/person.rb +1 -0
  28. data/spec/fixtures/models/project.rb +3 -0
  29. data/spec/unit/assocations_spec.rb +73 -73
  30. data/spec/unit/attachment_spec.rb +34 -34
  31. data/spec/unit/base_spec.rb +102 -102
  32. data/spec/unit/casted_array_spec.rb +7 -7
  33. data/spec/unit/casted_spec.rb +7 -7
  34. data/spec/unit/configuration_spec.rb +11 -11
  35. data/spec/unit/connection_spec.rb +30 -30
  36. data/spec/unit/core_extensions/{time_parsing.rb → time_parsing_spec.rb} +21 -21
  37. data/spec/unit/design_spec.rb +38 -38
  38. data/spec/unit/designs/design_mapper_spec.rb +26 -26
  39. data/spec/unit/designs/migrations_spec.rb +13 -13
  40. data/spec/unit/designs/view_spec.rb +319 -274
  41. data/spec/unit/designs_spec.rb +39 -39
  42. data/spec/unit/dirty_spec.rb +188 -103
  43. data/spec/unit/embeddable_spec.rb +119 -117
  44. data/spec/unit/inherited_spec.rb +4 -4
  45. data/spec/unit/persistence_spec.rb +122 -122
  46. data/spec/unit/properties_spec.rb +466 -16
  47. data/spec/unit/property_protection_spec.rb +32 -32
  48. data/spec/unit/property_spec.rb +45 -436
  49. data/spec/unit/proxyable_spec.rb +140 -82
  50. data/spec/unit/subclass_spec.rb +14 -14
  51. data/spec/unit/translations_spec.rb +5 -5
  52. data/spec/unit/typecast_spec.rb +131 -131
  53. data/spec/unit/utils/migrate_spec.rb +2 -2
  54. data/spec/unit/validations_spec.rb +31 -31
  55. metadata +27 -12
  56. data/lib/couchrest/model/casted_hash.rb +0 -84
@@ -31,11 +31,11 @@ describe CouchRest::Model::Design do
31
31
 
32
32
  describe ".method_name" do
33
33
  it "should return standard method name" do
34
- @klass.method_name.should eql('design_doc')
34
+ expect(@klass.method_name).to eql('design_doc')
35
35
  end
36
36
 
37
37
  it "should add prefix to standard method name" do
38
- @klass.method_name('stats').should eql('stats_design_doc')
38
+ expect(@klass.method_name('stats')).to eql('stats_design_doc')
39
39
  end
40
40
  end
41
41
 
@@ -45,23 +45,23 @@ describe CouchRest::Model::Design do
45
45
 
46
46
  before :each do
47
47
  @model = double("ModelExample")
48
- @model.stub(:to_s).and_return("ModelExample")
48
+ allow(@model).to receive(:to_s).and_return("ModelExample")
49
49
  @obj = CouchRest::Model::Design.new(@model)
50
50
  end
51
51
 
52
52
 
53
53
  describe "initialisation without prefix" do
54
54
  it "should associate model and set method name" do
55
- @obj.model.should eql(@model)
56
- @obj.method_name.should eql("design_doc")
55
+ expect(@obj.model).to eql(@model)
56
+ expect(@obj.method_name).to eql("design_doc")
57
57
  end
58
58
 
59
59
  it "should generate correct id" do
60
- @obj['_id'].should eql("_design/ModelExample")
60
+ expect(@obj['_id']).to eql("_design/ModelExample")
61
61
  end
62
62
 
63
63
  it "should apply defaults" do
64
- @obj['language'].should eql('javascript')
64
+ expect(@obj['language']).to eql('javascript')
65
65
  end
66
66
  end
67
67
 
@@ -69,13 +69,13 @@ describe CouchRest::Model::Design do
69
69
 
70
70
  it "should associate model and set method name" do
71
71
  @obj = CouchRest::Model::Design.new(@model, 'stats')
72
- @obj.model.should eql(@model)
73
- @obj.method_name.should eql("stats_design_doc")
72
+ expect(@obj.model).to eql(@model)
73
+ expect(@obj.method_name).to eql("stats_design_doc")
74
74
  end
75
75
 
76
76
  it "should generate correct id with prefix" do
77
77
  @obj = CouchRest::Model::Design.new(@model, 'stats')
78
- @obj['_id'].should eql("_design/ModelExample_stats")
78
+ expect(@obj['_id']).to eql("_design/ModelExample_stats")
79
79
  end
80
80
 
81
81
  end
@@ -86,7 +86,7 @@ describe CouchRest::Model::Design do
86
86
 
87
87
  it "should skip if auto update disabled" do
88
88
  @obj.auto_update = false
89
- @obj.should_not_receive(:sync!)
89
+ expect(@obj).not_to receive(:sync!)
90
90
  @obj.sync
91
91
  end
92
92
 
@@ -110,28 +110,28 @@ describe CouchRest::Model::Design do
110
110
  # This would fail if changes were not detected!
111
111
  @doc.sync
112
112
  doc = @db.get(@doc['_id'])
113
- doc['views']['all']['map'].should eql(@doc['views']['all']['map'])
113
+ expect(doc['views']['all']['map']).to eql(@doc['views']['all']['map'])
114
114
  end
115
115
 
116
116
  it "should not save a design that is not in cache and has not changed" do
117
117
  @doc.sync # put doc in cache
118
118
  @doc.send(:set_cache_checksum, @doc.database, nil)
119
119
 
120
- @db.should_not_receive(:save_doc)
121
- @doc.should_receive(:set_cache_checksum)
120
+ expect(@db).not_to receive(:save_doc)
121
+ expect(@doc).to receive(:set_cache_checksum)
122
122
  @doc.sync
123
123
  end
124
124
 
125
125
  it "should not reload a design that is in cache and has not changed" do
126
126
  @doc.sync
127
- @doc.should_not_receive(:load_from_database)
127
+ expect(@doc).not_to receive(:load_from_database)
128
128
  @doc.sync
129
129
  end
130
130
 
131
131
  it "should be re-created if database destroyed" do
132
132
  @doc.sync # saved
133
133
  reset_test_db!
134
- @db.should_receive(:save_doc).with(@doc)
134
+ expect(@db).to receive(:save_doc).with(@doc)
135
135
  @doc.sync
136
136
  end
137
137
 
@@ -142,8 +142,8 @@ describe CouchRest::Model::Design do
142
142
  @db.save_doc(doc)
143
143
  @doc.send(:set_cache_checksum, @doc.database, nil)
144
144
  @doc.sync
145
- @doc['views'].should_not have_key('test')
146
- @doc['_rev'].should be_nil
145
+ expect(@doc['views']).not_to have_key('test')
146
+ expect(@doc['_rev']).to be_nil
147
147
  end
148
148
 
149
149
  it "should save a non existant design" do
@@ -155,8 +155,8 @@ describe CouchRest::Model::Design do
155
155
  @db.delete_doc(doc) if doc
156
156
  @doc.sync!
157
157
  doc = @db.get(@doc['_id'])
158
- doc.should_not be_nil
159
- doc['views']['all'].should eql(@doc['views']['all'])
158
+ expect(doc).not_to be_nil
159
+ expect(doc['views']['all']).to eql(@doc['views']['all'])
160
160
  end
161
161
 
162
162
  end
@@ -172,19 +172,19 @@ describe CouchRest::Model::Design do
172
172
  end
173
173
 
174
174
  it "should return fresh checksum when not calculated earlier" do
175
- @doc.checksum.should_not be_blank
175
+ expect(@doc.checksum).not_to be_blank
176
176
  end
177
177
 
178
178
  it "should provide same checksum without refresh on re-request" do
179
179
  chk = @doc.checksum
180
- @doc.should_not_receive(:checksum!)
181
- @doc.checksum.should eql(chk)
180
+ expect(@doc).not_to receive(:checksum!)
181
+ expect(@doc.checksum).to eql(chk)
182
182
  end
183
183
 
184
184
  it "should provide new checksum if the design has changed" do
185
185
  chk = @doc.checksum
186
186
  @doc['views']['all']['map'] += '// comment'
187
- @doc.checksum.should_not eql(chk)
187
+ expect(@doc.checksum).not_to eql(chk)
188
188
  end
189
189
 
190
190
  end
@@ -193,7 +193,7 @@ describe CouchRest::Model::Design do
193
193
  it "should provide model's database" do
194
194
  @mod = DesignSampleModel
195
195
  @doc = @mod.design_doc
196
- @mod.should_receive(:database)
196
+ expect(@mod).to receive(:database)
197
197
  @doc.database
198
198
  end
199
199
  end
@@ -202,13 +202,13 @@ describe CouchRest::Model::Design do
202
202
  describe "#uri" do
203
203
  it "should provide complete url" do
204
204
  @doc = DesignSampleModel.design_doc
205
- @doc.uri.should eql("#{DesignSampleModel.database.root}/_design/DesignSampleModel")
205
+ expect(@doc.uri).to eql("#{DesignSampleModel.database.root}/_design/DesignSampleModel")
206
206
  end
207
207
  end
208
208
 
209
209
  describe "#view" do
210
210
  it "should instantiate a new view and pass options" do
211
- CouchRest::Model::Designs::View.should_receive(:new).with(@obj, @model, {}, 'by_test')
211
+ expect(CouchRest::Model::Designs::View).to receive(:new).with(@obj, @model, {}, 'by_test')
212
212
  @obj.view('by_test', {})
213
213
  end
214
214
  end
@@ -216,7 +216,7 @@ describe CouchRest::Model::Design do
216
216
  describe "#view_names" do
217
217
  it "should provide a list of all the views available" do
218
218
  @doc = DesignSampleModel.design_doc
219
- @doc.view_names.should eql(['by_name', 'all'])
219
+ expect(@doc.view_names).to eql(['by_name', 'all'])
220
220
  end
221
221
  end
222
222
 
@@ -226,15 +226,15 @@ describe CouchRest::Model::Design do
226
226
  end
227
227
 
228
228
  it "should tell us if a view exists" do
229
- @doc.has_view?('by_name').should be_true
229
+ expect(@doc.has_view?('by_name')).to be_truthy
230
230
  end
231
231
 
232
232
  it "should tell us if a view exists as symbol" do
233
- @doc.has_view?(:by_name).should be_true
233
+ expect(@doc.has_view?(:by_name)).to be_truthy
234
234
  end
235
235
 
236
236
  it "should tell us if a view does not exist" do
237
- @doc.has_view?(:by_foobar).should be_false
237
+ expect(@doc.has_view?(:by_foobar)).to be_falsey
238
238
  end
239
239
  end
240
240
 
@@ -245,12 +245,12 @@ describe CouchRest::Model::Design do
245
245
  end
246
246
 
247
247
  it "should forward view creation to View model" do
248
- CouchRest::Model::Designs::View.should_receive(:define_and_create).with(@doc, 'by_other_name', {})
248
+ expect(CouchRest::Model::Designs::View).to receive(:define_and_create).with(@doc, 'by_other_name', {})
249
249
  @doc.create_view('by_other_name')
250
250
  end
251
251
 
252
252
  it "should forward view creation to View model with opts" do
253
- CouchRest::Model::Designs::View.should_receive(:define_and_create).with(@doc, 'by_other_name', {:by => 'name'})
253
+ expect(CouchRest::Model::Designs::View).to receive(:define_and_create).with(@doc, 'by_other_name', {:by => 'name'})
254
254
  @doc.create_view('by_other_name', :by => 'name')
255
255
  end
256
256
  end
@@ -263,7 +263,7 @@ describe CouchRest::Model::Design do
263
263
 
264
264
  it "should add simple filter" do
265
265
  @doc.create_filter('test', 'foobar')
266
- @doc['filters']['test'].should eql('foobar')
266
+ expect(@doc['filters']['test']).to eql('foobar')
267
267
  @doc['filters'] = nil # cleanup
268
268
  end
269
269
  end
@@ -275,7 +275,7 @@ describe CouchRest::Model::Design do
275
275
 
276
276
  it "should add simple view lib" do
277
277
  @doc.create_view_lib('test', 'foobar')
278
- @doc['views']['lib']['test'].should eql('foobar')
278
+ expect(@doc['views']['lib']['test']).to eql('foobar')
279
279
  @doc['views']['lib'] = nil # cleanup
280
280
  end
281
281
  end
@@ -286,17 +286,17 @@ describe CouchRest::Model::Design do
286
286
 
287
287
  it "should calculate a consistent checksum for model" do
288
288
  #WithTemplateAndUniqueID.design_doc.checksum.should eql('caa2b4c27abb82b4e37421de76d96ffc')
289
- WithTemplateAndUniqueID.design_doc.checksum.should eql('7f44e88afbce06204010c49b76f31bcf')
289
+ expect(WithTemplateAndUniqueID.design_doc.checksum).to eql('7f44e88afbce06204010c49b76f31bcf')
290
290
  end
291
291
 
292
292
  it "should calculate checksum for complex model" do
293
293
  #Article.design_doc.checksum.should eql('70dff8caea143bf40fad09adf0701104')
294
- Article.design_doc.checksum.should eql('81f6553c44ecc3fe12a39331b0cdee46')
294
+ expect(Article.design_doc.checksum).to eql('81f6553c44ecc3fe12a39331b0cdee46')
295
295
  end
296
296
 
297
297
  it "should cache the generated checksum value" do
298
298
  Article.design_doc.checksum
299
- Article.design_doc['couchrest-hash'].should_not be_blank
299
+ expect(Article.design_doc['couchrest-hash']).not_to be_blank
300
300
  Article.first
301
301
  end
302
302
 
@@ -15,22 +15,22 @@ describe CouchRest::Model::Designs::DesignMapper do
15
15
  end
16
16
 
17
17
  it "should set basic variables" do
18
- @object.send(:model).should eql(DesignModel)
19
- @object.send(:prefix).should be_nil
20
- @object.send(:method).should eql('design_doc')
18
+ expect(@object.send(:model)).to eql(DesignModel)
19
+ expect(@object.send(:prefix)).to be_nil
20
+ expect(@object.send(:method)).to eql('design_doc')
21
21
  end
22
22
 
23
23
  it "should add design doc to list" do
24
- @object.model.design_docs.should include(@object.model.design_doc)
24
+ expect(@object.model.design_docs).to include(@object.model.design_doc)
25
25
  end
26
26
 
27
27
  it "should create a design doc method" do
28
- @object.model.should respond_to('design_doc')
29
- @object.design_doc.should eql(@object.model.design_doc)
28
+ expect(@object.model).to respond_to('design_doc')
29
+ expect(@object.design_doc).to eql(@object.model.design_doc)
30
30
  end
31
31
 
32
32
  it "should use default for autoupdate" do
33
- @object.design_doc.auto_update.should be_true
33
+ expect(@object.design_doc.auto_update).to be_truthy
34
34
  end
35
35
 
36
36
  end
@@ -41,22 +41,22 @@ describe CouchRest::Model::Designs::DesignMapper do
41
41
  end
42
42
 
43
43
  it "should set basics" do
44
- @object.send(:model).should eql(DesignModel)
45
- @object.send(:prefix).should eql('stats')
46
- @object.send(:method).should eql('stats_design_doc')
44
+ expect(@object.send(:model)).to eql(DesignModel)
45
+ expect(@object.send(:prefix)).to eql('stats')
46
+ expect(@object.send(:method)).to eql('stats_design_doc')
47
47
  end
48
48
 
49
49
  it "should add design doc to list" do
50
- @object.model.design_docs.should include(@object.model.stats_design_doc)
50
+ expect(@object.model.design_docs).to include(@object.model.stats_design_doc)
51
51
  end
52
52
 
53
53
  it "should not create an all method" do
54
- @object.model.should_not respond_to('all')
54
+ expect(@object.model).not_to respond_to('all')
55
55
  end
56
56
 
57
57
  it "should create a design doc method" do
58
- @object.model.should respond_to('stats_design_doc')
59
- @object.design_doc.should eql(@object.model.stats_design_doc)
58
+ expect(@object.model).to respond_to('stats_design_doc')
59
+ expect(@object.design_doc).to eql(@object.model.stats_design_doc)
60
60
  end
61
61
 
62
62
  end
@@ -65,7 +65,7 @@ describe CouchRest::Model::Designs::DesignMapper do
65
65
  it "should disable auto updates" do
66
66
  @object = @klass.new(DesignModel)
67
67
  @object.disable_auto_update
68
- @object.design_doc.auto_update.should be_false
68
+ expect(@object.design_doc.auto_update).to be_falsey
69
69
  end
70
70
  end
71
71
 
@@ -73,14 +73,14 @@ describe CouchRest::Model::Designs::DesignMapper do
73
73
  it "should enable auto updates" do
74
74
  @object = @klass.new(DesignModel)
75
75
  @object.enable_auto_update
76
- @object.design_doc.auto_update.should be_true
76
+ expect(@object.design_doc.auto_update).to be_truthy
77
77
  end
78
78
  end
79
79
 
80
80
  describe "#model_type_key" do
81
81
  it "should return models type key" do
82
82
  @object = @klass.new(DesignModel)
83
- @object.model_type_key.should eql(@object.model.model_type_key)
83
+ expect(@object.model_type_key).to eql(@object.model.model_type_key)
84
84
  end
85
85
  end
86
86
 
@@ -91,18 +91,18 @@ describe CouchRest::Model::Designs::DesignMapper do
91
91
  end
92
92
 
93
93
  it "should call create method on view" do
94
- CouchRest::Model::Designs::View.should_receive(:define).with(@object.design_doc, 'test', {})
94
+ expect(CouchRest::Model::Designs::View).to receive(:define).with(@object.design_doc, 'test', {})
95
95
  @object.view('test')
96
96
  end
97
97
 
98
98
  it "should create a method on parent model" do
99
- CouchRest::Model::Designs::View.stub(:define)
99
+ allow(CouchRest::Model::Designs::View).to receive(:define)
100
100
  @object.view('test_view')
101
- DesignModel.should respond_to(:test_view)
101
+ expect(DesignModel).to respond_to(:test_view)
102
102
  end
103
103
 
104
104
  it "should create a method for view instance" do
105
- @object.design_doc.should_receive(:create_view).with('test', {})
105
+ expect(@object.design_doc).to receive(:create_view).with('test', {})
106
106
  @object.view('test')
107
107
  end
108
108
  end
@@ -115,8 +115,8 @@ describe CouchRest::Model::Designs::DesignMapper do
115
115
 
116
116
  it "should add the provided function to the design doc" do
117
117
  @object.filter(:important, "function(doc, req) { return doc.priority == 'high'; }")
118
- DesignModel.design_doc['filters'].should_not be_empty
119
- DesignModel.design_doc['filters']['important'].should_not be_blank
118
+ expect(DesignModel.design_doc['filters']).not_to be_empty
119
+ expect(DesignModel.design_doc['filters']['important']).not_to be_blank
120
120
  end
121
121
  end
122
122
 
@@ -128,9 +128,9 @@ describe CouchRest::Model::Designs::DesignMapper do
128
128
  it "should add the #view_lib function to the design doc" do
129
129
  val = "exports.bar = 42;"
130
130
  @object.view_lib(:foo, val)
131
- DesignModel.design_doc['views']['lib'].should_not be_empty
132
- DesignModel.design_doc['views']['lib'].should_not be_blank
133
- DesignModel.design_doc['views']['lib']['foo'].should eql(val)
131
+ expect(DesignModel.design_doc['views']['lib']).not_to be_empty
132
+ expect(DesignModel.design_doc['views']['lib']).not_to be_blank
133
+ expect(DesignModel.design_doc['views']['lib']['foo']).to eql(val)
134
134
  end
135
135
  end
136
136
 
@@ -34,24 +34,24 @@ describe CouchRest::Model::Designs::Migrations do
34
34
  end
35
35
 
36
36
  it "should create new design if non exists" do
37
- @db.should_receive(:view).with("#{@doc.name}/#{@doc['views'].keys.first}", {
37
+ expect(@db).to receive(:view).with("#{@doc.name}/#{@doc['views'].keys.first}", {
38
38
  :limit => 1, :stale => 'update_after', :reduce => false
39
39
  })
40
40
  callback = @doc.migrate do |res|
41
- res.should eql(:created)
41
+ expect(res).to eql(:created)
42
42
  end
43
43
  doc = @db.get(@doc['_id'])
44
- doc['views']['all'].should eql(@doc['views']['all'])
45
- callback.should be_nil
44
+ expect(doc['views']['all']).to eql(@doc['views']['all'])
45
+ expect(callback).to be_nil
46
46
  end
47
47
 
48
48
  it "should not change anything if design is up to date" do
49
49
  @doc.sync
50
- @db.should_not_receive(:view)
50
+ expect(@db).not_to receive(:view)
51
51
  callback = @doc.migrate do |res|
52
- res.should eql(:no_change)
52
+ expect(res).to eql(:no_change)
53
53
  end
54
- callback.should be_nil
54
+ expect(callback).to be_nil
55
55
  end
56
56
 
57
57
  end
@@ -72,28 +72,28 @@ describe CouchRest::Model::Designs::Migrations do
72
72
  end
73
73
 
74
74
  it "should save new migration design doc" do
75
- @db.should_receive(:view).with("#{@doc.name}_migration/by_name", {
75
+ expect(@db).to receive(:view).with("#{@doc.name}_migration/by_name", {
76
76
  :limit => 1, :reduce => false, :stale => 'update_after'
77
77
  })
78
78
  @callback = @doc.migrate do |res|
79
- res.should eql(:migrated)
79
+ expect(res).to eql(:migrated)
80
80
  end
81
- @callback.should_not be_nil
81
+ expect(@callback).not_to be_nil
82
82
 
83
83
  # should not have updated original view until cleanup
84
84
  doc = @db.get(@doc['_id'])
85
- doc['views'].should_not have_key('by_name_and_surname')
85
+ expect(doc['views']).not_to have_key('by_name_and_surname')
86
86
 
87
87
  # Should have created the migration
88
88
  new_doc = @db.get(@doc_id)
89
- new_doc.should_not be_nil
89
+ expect(new_doc).not_to be_nil
90
90
 
91
91
  # should be possible to perform cleanup
92
92
  @callback.call
93
93
  expect(@db.get(@doc_id)).to be_nil
94
94
 
95
95
  doc = @db.get(@doc['_id'])
96
- doc['views'].should have_key('by_name_and_surname')
96
+ expect(doc['views']).to have_key('by_name_and_surname')
97
97
  end
98
98
 
99
99
  end
@@ -24,7 +24,7 @@ describe "Design View" do
24
24
 
25
25
  describe "with invalid parent model" do
26
26
  it "should burn" do
27
- lambda { @klass.new(String) }.should raise_exception
27
+ expect { @klass.new(String, nil) }.to raise_error(/View cannot be initialized without a parent Model/)
28
28
  end
29
29
  end
30
30
 
@@ -32,14 +32,14 @@ describe "Design View" do
32
32
 
33
33
  it "should setup attributes" do
34
34
  @obj = @klass.new(@mod.design_doc, @mod, {}, 'test_view')
35
- @obj.design_doc.should eql(@mod.design_doc)
36
- @obj.model.should eql(@mod)
37
- @obj.name.should eql('test_view')
38
- @obj.query.should be_empty
35
+ expect(@obj.design_doc).to eql(@mod.design_doc)
36
+ expect(@obj.model).to eql(@mod)
37
+ expect(@obj.name).to eql('test_view')
38
+ expect(@obj.query).to be_empty
39
39
  end
40
40
 
41
41
  it "should complain if there is no name" do
42
- lambda { @klass.new(@mod.design_doc, @mod, {}, nil) }.should raise_error(/Name must be provided/)
42
+ expect { @klass.new(@mod.design_doc, @mod, {}, nil) }.to raise_error(/Name must be provided/)
43
43
  end
44
44
 
45
45
  end
@@ -52,14 +52,14 @@ describe "Design View" do
52
52
  end
53
53
 
54
54
  it "should copy attributes" do
55
- @obj.model.should eql(@mod)
56
- @obj.name.should eql('test_view')
57
- @obj.query.should eql({:foo => :bar})
55
+ expect(@obj.model).to eql(@mod)
56
+ expect(@obj.name).to eql('test_view')
57
+ expect(@obj.query).to eql({:foo => :bar})
58
58
  end
59
59
 
60
60
  it "should delete query keys if :delete defined" do
61
61
  @obj2 = @klass.new(@mod.design_doc, @obj, {:delete => [:foo]})
62
- @obj2.query.should_not include(:foo)
62
+ expect(@obj2.query).not_to include(:foo)
63
63
  end
64
64
 
65
65
  end
@@ -68,7 +68,7 @@ describe "Design View" do
68
68
  it "should set model to proxy object and remove from query" do
69
69
  proxy = double("Proxy")
70
70
  @obj = @klass.new(@mod.design_doc, @mod, {:proxy => proxy}, 'test_view')
71
- @obj.model.should eql(proxy)
71
+ expect(@obj.model).to eql(proxy)
72
72
  end
73
73
  end
74
74
 
@@ -76,9 +76,9 @@ describe "Design View" do
76
76
  it "should set the model to proxy object instead of parents model" do
77
77
  proxy = double("Proxy")
78
78
  @obj = @klass.new(@mod.design_doc, @mod, {}, 'test_view')
79
- @obj.model.should eql(@mod)
79
+ expect(@obj.model).to eql(@mod)
80
80
  @obj = @obj.proxy(proxy)
81
- @obj.model.should eql(proxy)
81
+ expect(@obj.model).to eql(proxy)
82
82
  end
83
83
  end
84
84
 
@@ -90,14 +90,14 @@ describe "Design View" do
90
90
  end
91
91
 
92
92
  it "should call define and create_model_methods method" do
93
- @klass.should_receive(:define).with(@design_doc, 'test', {}).and_return(nil)
94
- @klass.should_receive(:create_model_methods).with(@design_doc, 'test', {}).and_return(nil)
93
+ expect(@klass).to receive(:define).with(@design_doc, 'test', {}).and_return(nil)
94
+ expect(@klass).to receive(:create_model_methods).with(@design_doc, 'test', {}).and_return(nil)
95
95
  @klass.define_and_create(@design_doc, 'test')
96
96
  end
97
97
 
98
98
  it "should call define and create_model_methods method with opts" do
99
- @klass.should_receive(:define).with(@design_doc, 'test', {:foo => :bar}).and_return(nil)
100
- @klass.should_receive(:create_model_methods).with(@design_doc, 'test', {:foo => :bar}).and_return(nil)
99
+ expect(@klass).to receive(:define).with(@design_doc, 'test', {:foo => :bar}).and_return(nil)
100
+ expect(@klass).to receive(:create_model_methods).with(@design_doc, 'test', {:foo => :bar}).and_return(nil)
101
101
  @klass.define_and_create(@design_doc, 'test', {:foo => :bar})
102
102
  end
103
103
 
@@ -109,53 +109,71 @@ describe "Design View" do
109
109
 
110
110
  before :each do
111
111
  @design_doc = { }
112
- @design_doc.stub(:model).and_return(DesignViewModel)
112
+ allow(@design_doc).to receive(:model).and_return(DesignViewModel)
113
113
  end
114
114
 
115
115
  it "should add a basic view" do
116
116
  @klass.define(@design_doc, 'test_view', :map => 'foo')
117
- @design_doc['views']['test_view'].should_not be_nil
117
+ expect(@design_doc['views']['test_view']).not_to be_nil
118
118
  end
119
119
 
120
120
  it "should not overwrite reduce if set" do
121
121
  @klass.define(@design_doc, 'by_title', :reduce => true)
122
- @design_doc['views']['by_title']['map'].should_not be_blank
123
- @design_doc['views']['by_title']['reduce'].should eql(true)
122
+ expect(@design_doc['views']['by_title']['map']).not_to be_blank
123
+ expect(@design_doc['views']['by_title']['reduce']).to eql(true)
124
124
  end
125
125
 
126
126
  it "should replace reduce symbol with string name" do
127
127
  @klass.define(@design_doc, 'by_title', :reduce => :sum)
128
- @design_doc['views']['by_title']['map'].should_not be_blank
129
- @design_doc['views']['by_title']['reduce'].should eql('_sum')
128
+ expect(@design_doc['views']['by_title']['map']).not_to be_blank
129
+ expect(@design_doc['views']['by_title']['reduce']).to eql('_sum')
130
130
  end
131
131
 
132
132
  it "should replace reduce symbol with string if map function present" do
133
133
  @klass.define(@design_doc, 'by_title', :map => "function(d) { }", :reduce => :sum)
134
- @design_doc['views']['by_title']['map'].should_not be_blank
135
- @design_doc['views']['by_title']['reduce'].should eql('_sum')
134
+ expect(@design_doc['views']['by_title']['map']).not_to be_blank
135
+ expect(@design_doc['views']['by_title']['reduce']).to eql('_sum')
136
136
  end
137
137
 
138
138
  it "should auto generate mapping from name" do
139
- lambda { @klass.define(@design_doc, 'by_title') }.should_not raise_error
139
+ expect { @klass.define(@design_doc, 'by_title') }.not_to raise_error
140
140
  str = @design_doc['views']['by_title']['map']
141
- str.should include("((doc['#{DesignViewModel.model_type_key}'] == 'DesignViewModel') && (doc['title'] != null))")
142
- str.should include("emit(doc['title'], 1);")
141
+ expect(str).to include("((doc['#{DesignViewModel.model_type_key}'] == 'DesignViewModel') && (doc['title'] != null))")
142
+ expect(str).to include("emit(doc['title'], 1);")
143
143
  str = @design_doc['views']['by_title']['reduce']
144
- str.should include("_sum")
144
+ expect(str).to include("_sum")
145
145
  end
146
146
 
147
147
  it "should auto generate mapping from name with and" do
148
148
  @klass.define(@design_doc, 'by_title_and_name')
149
149
  str = @design_doc['views']['by_title_and_name']['map']
150
- str.should include("(doc['title'] != null) && (doc['name'] != null)")
151
- str.should include("emit([doc['title'], doc['name']], 1);")
150
+ expect(str).to include("(doc['title'] != null) && (doc['name'] != null)")
151
+ expect(str).to include("emit([doc['title'], doc['name']], 1);")
152
152
  str = @design_doc['views']['by_title_and_name']['reduce']
153
- str.should include("_sum")
153
+ expect(str).to include("_sum")
154
154
  end
155
155
 
156
156
  it "should allow reduce methods as symbols" do
157
157
  @klass.define(@design_doc, 'by_title', :reduce => :stats)
158
- @design_doc['views']['by_title']['reduce'].should eql('_stats')
158
+ expect(@design_doc['views']['by_title']['reduce']).to eql('_stats')
159
+ end
160
+
161
+ it "should allow the emit value to be overridden" do
162
+ @klass.define(@design_doc, 'by_title', :emit => :name)
163
+ str = @design_doc['views']['by_title']['map']
164
+ expect(str).to include("emit(doc['title'], doc['name']);")
165
+ end
166
+
167
+ it "should forward a non-symbol emit value straight into the view" do
168
+ @klass.define(@design_doc, 'by_title', :emit => 3)
169
+ str = @design_doc['views']['by_title']['map']
170
+ expect(str).to include("emit(doc['title'], 3);")
171
+ end
172
+
173
+ it "should support emitting an array" do
174
+ @klass.define(@design_doc, 'by_title', :emit => [1, :name])
175
+ str = @design_doc['views']['by_title']['map']
176
+ expect(str).to include("emit(doc['title'], [1, doc['name']]);")
159
177
  end
160
178
  end
161
179
 
@@ -163,42 +181,42 @@ describe "Design View" do
163
181
  before :each do
164
182
  @model = DesignViewModel
165
183
  @design_doc = { }
166
- @design_doc.stub(:model).and_return(@model)
167
- @design_doc.stub(:method_name).and_return("design_doc")
168
- @model.stub('design_doc').and_return(@design_doc)
184
+ allow(@design_doc).to receive(:model).and_return(@model)
185
+ allow(@design_doc).to receive(:method_name).and_return("design_doc")
186
+ allow(@model).to receive('design_doc').and_return(@design_doc)
169
187
  end
170
188
  it "should create standard view method" do
171
189
  @klass.create_model_methods(@design_doc, 'by_name')
172
- @model.should respond_to('by_name')
173
- @design_doc.should_receive('view').with('by_name', {})
190
+ expect(@model).to respond_to('by_name')
191
+ expect(@design_doc).to receive('view').with('by_name', {})
174
192
  @model.by_name
175
193
  end
176
194
  it "should create find_ view method" do
177
195
  @klass.create_model_methods(@design_doc, 'by_name')
178
- @model.should respond_to('find_by_name')
196
+ expect(@model).to respond_to('find_by_name')
179
197
  view = double("View")
180
- view.should_receive('key').with('fred').and_return(view)
181
- view.should_receive('first').and_return(nil)
182
- @design_doc.should_receive('view').and_return(view)
198
+ expect(view).to receive('key').with('fred').and_return(view)
199
+ expect(view).to receive('first').and_return(nil)
200
+ expect(@design_doc).to receive('view').and_return(view)
183
201
  @model.find_by_name('fred')
184
202
  end
185
203
  it "should create find_! view method" do
186
204
  @klass.create_model_methods(@design_doc, 'by_name')
187
- @model.should respond_to('find_by_name!')
205
+ expect(@model).to respond_to('find_by_name!')
188
206
  obj = double("SomeKlass")
189
207
  view = double("View")
190
- view.should_receive('key').with('fred').and_return(view)
191
- view.should_receive('first').and_return(obj)
192
- @design_doc.should_receive('view').and_return(view)
193
- @model.find_by_name!('fred').should eql(obj)
208
+ expect(view).to receive('key').with('fred').and_return(view)
209
+ expect(view).to receive('first').and_return(obj)
210
+ expect(@design_doc).to receive('view').and_return(view)
211
+ expect(@model.find_by_name!('fred')).to eql(obj)
194
212
  end
195
213
  it "should create find_! view method and raise error when nil" do
196
214
  @klass.create_model_methods(@design_doc, 'by_name')
197
215
  view = double("View")
198
- view.should_receive('key').with('fred').and_return(view)
199
- view.should_receive('first').and_return(nil)
200
- @design_doc.should_receive('view').and_return(view)
201
- lambda { @model.find_by_name!('fred') }.should raise_error(CouchRest::Model::DocumentNotFound)
216
+ expect(view).to receive('key').with('fred').and_return(view)
217
+ expect(view).to receive('first').and_return(nil)
218
+ expect(@design_doc).to receive('view').and_return(view)
219
+ expect { @model.find_by_name!('fred') }.to raise_error(CouchRest::Model::DocumentNotFound)
202
220
  end
203
221
 
204
222
  end
@@ -213,15 +231,15 @@ describe "Design View" do
213
231
 
214
232
  describe "#rows" do
215
233
  it "should execute query" do
216
- @obj.should_receive(:execute).and_return(true)
217
- @obj.should_receive(:result).twice.and_return({'rows' => []})
218
- @obj.rows.should be_empty
234
+ expect(@obj).to receive(:execute).and_return(true)
235
+ expect(@obj).to receive(:result).twice.and_return({'rows' => []})
236
+ expect(@obj.rows).to be_empty
219
237
  end
220
238
 
221
239
  it "should wrap rows in ViewRow class" do
222
- @obj.should_receive(:execute).and_return(true)
223
- @obj.should_receive(:result).twice.and_return({'rows' => [{:foo => :bar}]})
224
- CouchRest::Model::Designs::ViewRow.should_receive(:new).with({:foo => :bar}, @obj.model, DB)
240
+ expect(@obj).to receive(:execute).and_return(true)
241
+ expect(@obj).to receive(:result).twice.and_return({'rows' => [{:foo => :bar}]})
242
+ expect(CouchRest::Model::Designs::ViewRow).to receive(:new).with({:foo => :bar}, @obj.model, DB)
225
243
  @obj.rows
226
244
  end
227
245
 
@@ -250,24 +268,24 @@ describe "Design View" do
250
268
 
251
269
  describe "#all" do
252
270
  it "should ensure docs included and call docs" do
253
- @obj.should_receive(:include_docs!)
254
- @obj.should_receive(:docs)
271
+ expect(@obj).to receive(:include_docs!)
272
+ expect(@obj).to receive(:docs)
255
273
  @obj.all
256
274
  end
257
275
  it "should pass on a block" do
258
- block = lambda { }
259
- expect(@obj).to receive(:docs).with(&block)
260
- @obj.all(&block)
276
+ block = lambda { 'ok' }
277
+ expect(@obj).to receive(:docs) { block.call() }
278
+ expect(@obj.all(&block)).to eql('ok')
261
279
  end
262
280
  end
263
281
 
264
282
  describe "#docs" do
265
283
  it "should provide docs from rows" do
266
- @obj.should_receive(:rows).and_return([])
284
+ expect(@obj).to receive(:rows).and_return([])
267
285
  @obj.docs
268
286
  end
269
287
  it "should cache the results" do
270
- @obj.should_receive(:rows).once.and_return([])
288
+ expect(@obj).to receive(:rows).once.and_return([])
271
289
  @obj.docs
272
290
  @obj.docs
273
291
  end
@@ -296,369 +314,369 @@ describe "Design View" do
296
314
 
297
315
  describe "#first" do
298
316
  it "should provide the first result of loaded query" do
299
- @obj.should_receive(:result).and_return(true)
300
- @obj.should_receive(:all).and_return([:foo])
301
- @obj.first.should eql(:foo)
317
+ expect(@obj).to receive(:result).and_return(true)
318
+ expect(@obj).to receive(:all).and_return([:foo])
319
+ expect(@obj.first).to eql(:foo)
302
320
  end
303
321
  it "should perform a query if no results cached" do
304
322
  view = double('SubView')
305
- @obj.should_receive(:result).and_return(nil)
306
- @obj.should_receive(:limit).with(1).and_return(view)
307
- view.should_receive(:all).and_return([:foo])
308
- @obj.first.should eql(:foo)
323
+ expect(@obj).to receive(:result).and_return(nil)
324
+ expect(@obj).to receive(:limit).with(1).and_return(view)
325
+ expect(view).to receive(:all).and_return([:foo])
326
+ expect(@obj.first).to eql(:foo)
309
327
  end
310
328
  end
311
329
 
312
330
  describe "#last" do
313
331
  it "should provide the last result of loaded query" do
314
- @obj.should_receive(:result).and_return(true)
315
- @obj.should_receive(:all).and_return([:foo, :bar])
316
- @obj.first.should eql(:foo)
332
+ expect(@obj).to receive(:result).and_return(true)
333
+ expect(@obj).to receive(:all).and_return([:foo, :bar])
334
+ expect(@obj.first).to eql(:foo)
317
335
  end
318
336
  it "should perform a query if no results cached" do
319
337
  view = double('SubView')
320
- @obj.should_receive(:result).and_return(nil)
321
- @obj.should_receive(:limit).with(1).and_return(view)
322
- view.should_receive(:descending).and_return(view)
323
- view.should_receive(:all).and_return([:foo, :bar])
324
- @obj.last.should eql(:bar)
338
+ expect(@obj).to receive(:result).and_return(nil)
339
+ expect(@obj).to receive(:limit).with(1).and_return(view)
340
+ expect(view).to receive(:descending).and_return(view)
341
+ expect(view).to receive(:all).and_return([:foo, :bar])
342
+ expect(@obj.last).to eql(:bar)
325
343
  end
326
344
  end
327
345
 
328
346
  describe "#length" do
329
347
  it "should provide a length from the docs array" do
330
- @obj.should_receive(:docs).and_return([1, 2, 3])
331
- @obj.length.should eql(3)
348
+ expect(@obj).to receive(:docs).and_return([1, 2, 3])
349
+ expect(@obj.length).to eql(3)
332
350
  end
333
351
  end
334
352
 
335
353
  describe "#count" do
336
354
  it "should raise an error if view prepared for group" do
337
- @obj.should_receive(:query).and_return({:group => true})
338
- lambda { @obj.count }.should raise_error(/group/)
355
+ expect(@obj).to receive(:query).and_return({:group => true})
356
+ expect { @obj.count }.to raise_error(/group/)
339
357
  end
340
358
 
341
359
  it "should return first row value if reduce possible" do
342
360
  view = double("SubView")
343
361
  row = double("Row")
344
- @obj.should_receive(:can_reduce?).and_return(true)
345
- @obj.should_receive(:reduce).and_return(view)
346
- view.should_receive(:skip).with(0).and_return(view)
347
- view.should_receive(:limit).with(1).and_return(view)
348
- view.should_receive(:rows).and_return([row])
349
- row.should_receive(:value).and_return(2)
350
- @obj.count.should eql(2)
362
+ expect(@obj).to receive(:can_reduce?).and_return(true)
363
+ expect(@obj).to receive(:reduce).and_return(view)
364
+ expect(view).to receive(:skip).with(0).and_return(view)
365
+ expect(view).to receive(:limit).with(1).and_return(view)
366
+ expect(view).to receive(:rows).and_return([row])
367
+ expect(row).to receive(:value).and_return(2)
368
+ expect(@obj.count).to eql(2)
351
369
  end
352
370
  it "should return 0 if no rows and reduce possible" do
353
371
  view = double("SubView")
354
- @obj.should_receive(:can_reduce?).and_return(true)
355
- @obj.should_receive(:reduce).and_return(view)
356
- view.should_receive(:skip).with(0).and_return(view)
357
- view.should_receive(:limit).with(1).and_return(view)
358
- view.should_receive(:rows).and_return([])
359
- @obj.count.should eql(0)
372
+ expect(@obj).to receive(:can_reduce?).and_return(true)
373
+ expect(@obj).to receive(:reduce).and_return(view)
374
+ expect(view).to receive(:skip).with(0).and_return(view)
375
+ expect(view).to receive(:limit).with(1).and_return(view)
376
+ expect(view).to receive(:rows).and_return([])
377
+ expect(@obj.count).to eql(0)
360
378
  end
361
379
 
362
380
  it "should perform limit request for total_rows" do
363
381
  view = double("SubView")
364
- @obj.should_receive(:limit).with(0).and_return(view)
365
- view.should_receive(:total_rows).and_return(4)
366
- @obj.should_receive(:can_reduce?).and_return(false)
367
- @obj.count.should eql(4)
382
+ expect(@obj).to receive(:limit).with(0).and_return(view)
383
+ expect(view).to receive(:total_rows).and_return(4)
384
+ expect(@obj).to receive(:can_reduce?).and_return(false)
385
+ expect(@obj.count).to eql(4)
368
386
  end
369
387
  end
370
388
 
371
389
  describe "#empty?" do
372
390
  it "should check the #all method for any results" do
373
391
  all = double("All")
374
- all.should_receive(:empty?).and_return('win')
375
- @obj.should_receive(:all).and_return(all)
376
- @obj.empty?.should eql('win')
392
+ expect(all).to receive(:empty?).and_return('win')
393
+ expect(@obj).to receive(:all).and_return(all)
394
+ expect(@obj.empty?).to eql('win')
377
395
  end
378
396
  end
379
397
 
380
398
  describe "#each" do
381
399
  it "should call each method on all" do
382
- @obj.should_receive(:all).and_return([])
400
+ expect(@obj).to receive(:all).and_return([])
383
401
  @obj.each
384
402
  end
385
403
  it "should call each and pass block" do
386
404
  set = [:foo, :bar]
387
- @obj.should_receive(:all).and_return(set)
405
+ expect(@obj).to receive(:all).and_return(set)
388
406
  result = []
389
407
  @obj.each do |s|
390
408
  result << s
391
409
  end
392
- result.should eql(set)
410
+ expect(result).to eql(set)
393
411
  end
394
412
  end
395
413
 
396
414
  describe "#offset" do
397
415
  it "should excute" do
398
- @obj.should_receive(:execute).and_return({'offset' => 3})
399
- @obj.offset.should eql(3)
416
+ expect(@obj).to receive(:execute).and_return({'offset' => 3})
417
+ expect(@obj.offset).to eql(3)
400
418
  end
401
419
  end
402
420
 
403
421
  describe "#total_rows" do
404
422
  it "should excute" do
405
- @obj.should_receive(:execute).and_return({'total_rows' => 3})
406
- @obj.total_rows.should eql(3)
423
+ expect(@obj).to receive(:execute).and_return({'total_rows' => 3})
424
+ expect(@obj.total_rows).to eql(3)
407
425
  end
408
426
  end
409
427
 
410
428
  describe "#values" do
411
429
  it "should request each row and provide value" do
412
430
  row = double("Row")
413
- row.should_receive(:value).twice.and_return('foo')
414
- @obj.should_receive(:rows).and_return([row, row])
415
- @obj.values.should eql(['foo', 'foo'])
431
+ expect(row).to receive(:value).twice.and_return('foo')
432
+ expect(@obj).to receive(:rows).and_return([row, row])
433
+ expect(@obj.values).to eql(['foo', 'foo'])
416
434
  end
417
435
  end
418
436
 
419
437
  describe "#[]" do
420
438
  it "should execute and provide requested field" do
421
- @obj.should_receive(:execute).and_return({'total_rows' => 2})
422
- @obj['total_rows'].should eql(2)
439
+ expect(@obj).to receive(:execute).and_return({'total_rows' => 2})
440
+ expect(@obj['total_rows']).to eql(2)
423
441
  end
424
442
  end
425
443
 
426
444
  describe "#info" do
427
445
  it "should raise error" do
428
- lambda { @obj.info }.should raise_error
446
+ expect { @obj.info }.to raise_error(/Not yet implemented/)
429
447
  end
430
448
  end
431
449
 
432
450
  describe "#database" do
433
451
  it "should update query with value" do
434
- @obj.should_receive(:update_query).with({:database => 'foo'})
452
+ expect(@obj).to receive(:update_query).with({:database => 'foo'})
435
453
  @obj.database('foo')
436
454
  end
437
455
  end
438
456
 
439
457
  describe "#key" do
440
458
  it "should update query with value" do
441
- @obj.should_receive(:update_query).with({:key => 'foo'})
459
+ expect(@obj).to receive(:update_query).with({:key => 'foo'})
442
460
  @obj.key('foo')
443
461
  end
444
462
  it "should raise error if startkey set" do
445
463
  @obj.query[:startkey] = 'bar'
446
- lambda { @obj.key('foo') }.should raise_error
464
+ expect { @obj.key('foo') }.to raise_error(/View#key cannot be used/)
447
465
  end
448
466
  it "should raise error if endkey set" do
449
467
  @obj.query[:endkey] = 'bar'
450
- lambda { @obj.key('foo') }.should raise_error
468
+ expect { @obj.key('foo') }.to raise_error(/View#key cannot be used/)
451
469
  end
452
470
  it "should raise error if both startkey and endkey set" do
453
471
  @obj.query[:startkey] = 'bar'
454
472
  @obj.query[:endkey] = 'bar'
455
- lambda { @obj.key('foo') }.should raise_error
473
+ expect { @obj.key('foo') }.to raise_error(/View#key cannot be used/)
456
474
  end
457
475
  it "should raise error if keys set" do
458
476
  @obj.query[:keys] = 'bar'
459
- lambda { @obj.key('foo') }.should raise_error
477
+ expect { @obj.key('foo') }.to raise_error(/View#key cannot be used/)
460
478
  end
461
479
  end
462
480
 
463
481
  describe "#startkey" do
464
482
  it "should update query with value" do
465
- @obj.should_receive(:update_query).with({:startkey => 'foo'})
483
+ expect(@obj).to receive(:update_query).with({:startkey => 'foo'})
466
484
  @obj.startkey('foo')
467
485
  end
468
486
  it "should raise and error if key set" do
469
487
  @obj.query[:key] = 'bar'
470
- lambda { @obj.startkey('foo') }.should raise_error(/View#startkey/)
488
+ expect { @obj.startkey('foo') }.to raise_error(/View#startkey/)
471
489
  end
472
490
  it "should raise and error if keys set" do
473
491
  @obj.query[:keys] = 'bar'
474
- lambda { @obj.startkey('foo') }.should raise_error(/View#startkey/)
492
+ expect { @obj.startkey('foo') }.to raise_error(/View#startkey/)
475
493
  end
476
494
  end
477
495
 
478
496
  describe "#startkey_doc" do
479
497
  it "should update query with value" do
480
- @obj.should_receive(:update_query).with({:startkey_docid => 'foo'})
498
+ expect(@obj).to receive(:update_query).with({:startkey_docid => 'foo'})
481
499
  @obj.startkey_doc('foo')
482
500
  end
483
501
  it "should update query with object id if available" do
484
502
  doc = double("Document")
485
- doc.should_receive(:id).and_return(44)
486
- @obj.should_receive(:update_query).with({:startkey_docid => 44})
503
+ expect(doc).to receive(:id).and_return(44)
504
+ expect(@obj).to receive(:update_query).with({:startkey_docid => 44})
487
505
  @obj.startkey_doc(doc)
488
506
  end
489
507
  end
490
508
 
491
509
  describe "#endkey" do
492
510
  it "should update query with value" do
493
- @obj.should_receive(:update_query).with({:endkey => 'foo'})
511
+ expect(@obj).to receive(:update_query).with({:endkey => 'foo'})
494
512
  @obj.endkey('foo')
495
513
  end
496
514
  it "should raise and error if key set" do
497
515
  @obj.query[:key] = 'bar'
498
- lambda { @obj.endkey('foo') }.should raise_error(/View#endkey/)
516
+ expect { @obj.endkey('foo') }.to raise_error(/View#endkey/)
499
517
  end
500
518
  it "should raise and error if keys set" do
501
519
  @obj.query[:keys] = 'bar'
502
- lambda { @obj.endkey('foo') }.should raise_error(/View#endkey/)
520
+ expect { @obj.endkey('foo') }.to raise_error(/View#endkey/)
503
521
  end
504
522
  end
505
523
 
506
524
  describe "#endkey_doc" do
507
525
  it "should update query with value" do
508
- @obj.should_receive(:update_query).with({:endkey_docid => 'foo'})
526
+ expect(@obj).to receive(:update_query).with({:endkey_docid => 'foo'})
509
527
  @obj.endkey_doc('foo')
510
528
  end
511
529
  it "should update query with object id if available" do
512
530
  doc = double("Document")
513
- doc.should_receive(:id).and_return(44)
514
- @obj.should_receive(:update_query).with({:endkey_docid => 44})
531
+ expect(doc).to receive(:id).and_return(44)
532
+ expect(@obj).to receive(:update_query).with({:endkey_docid => 44})
515
533
  @obj.endkey_doc(doc)
516
534
  end
517
535
  end
518
536
 
519
537
  describe "#keys" do
520
538
  it "should update the query" do
521
- @obj.should_receive(:update_query).with({:keys => ['foo', 'bar']})
539
+ expect(@obj).to receive(:update_query).with({:keys => ['foo', 'bar']})
522
540
  @obj.keys(['foo', 'bar'])
523
541
  end
524
542
  it "should raise and error if key set" do
525
543
  @obj.query[:key] = 'bar'
526
- lambda { @obj.keys('foo') }.should raise_error(/View#keys/)
544
+ expect { @obj.keys('foo') }.to raise_error(/View#keys/)
527
545
  end
528
546
  it "should raise and error if startkey or endkey set" do
529
547
  @obj.query[:startkey] = 'bar'
530
- lambda { @obj.keys('foo') }.should raise_error(/View#keys/)
548
+ expect { @obj.keys('foo') }.to raise_error(/View#keys/)
531
549
  @obj.query.delete(:startkey)
532
550
  @obj.query[:endkey] = 'bar'
533
- lambda { @obj.keys('foo') }.should raise_error(/View#keys/)
551
+ expect { @obj.keys('foo') }.to raise_error(/View#keys/)
534
552
  end
535
553
  end
536
554
 
537
555
  describe "#keys (without parameters)" do
538
556
  it "should request each row and provide key value" do
539
557
  row = double("Row")
540
- row.should_receive(:key).twice.and_return('foo')
541
- @obj.should_receive(:rows).and_return([row, row])
542
- @obj.keys.should eql(['foo', 'foo'])
558
+ expect(row).to receive(:key).twice.and_return('foo')
559
+ expect(@obj).to receive(:rows).and_return([row, row])
560
+ expect(@obj.keys).to eql(['foo', 'foo'])
543
561
  end
544
562
  end
545
563
 
546
564
  describe "#descending" do
547
565
  it "should update query" do
548
- @obj.should_receive(:update_query).with({:descending => true})
566
+ expect(@obj).to receive(:update_query).with({:descending => true})
549
567
  @obj.descending
550
568
  end
551
569
  it "should reverse start and end keys if given" do
552
570
  @obj = @obj.startkey('a').endkey('z')
553
571
  @obj = @obj.descending
554
- @obj.query[:endkey].should eql('a')
555
- @obj.query[:startkey].should eql('z')
572
+ expect(@obj.query[:endkey]).to eql('a')
573
+ expect(@obj.query[:startkey]).to eql('z')
556
574
  end
557
575
  it "should reverse even if start or end nil" do
558
576
  @obj = @obj.startkey('a')
559
577
  @obj = @obj.descending
560
- @obj.query[:endkey].should eql('a')
561
- @obj.query[:startkey].should be_nil
578
+ expect(@obj.query[:endkey]).to eql('a')
579
+ expect(@obj.query[:startkey]).to be_nil
562
580
  end
563
581
  it "should reverse start_doc and end_doc keys if given" do
564
582
  @obj = @obj.startkey_doc('a').endkey_doc('z')
565
583
  @obj = @obj.descending
566
- @obj.query[:endkey_docid].should eql('a')
567
- @obj.query[:startkey_docid].should eql('z')
584
+ expect(@obj.query[:endkey_docid]).to eql('a')
585
+ expect(@obj.query[:startkey_docid]).to eql('z')
568
586
  end
569
587
  end
570
588
 
571
589
  describe "#limit" do
572
590
  it "should update query with value" do
573
- @obj.should_receive(:update_query).with({:limit => 3})
591
+ expect(@obj).to receive(:update_query).with({:limit => 3})
574
592
  @obj.limit(3)
575
593
  end
576
594
  end
577
595
 
578
596
  describe "#skip" do
579
- it "should update query with value" do
580
- @obj.should_receive(:update_query).with({:skip => 3})
597
+ it "should update query with value" do
598
+ expect(@obj).to receive(:update_query).with({:skip => 3})
581
599
  @obj.skip(3)
582
600
  end
583
- it "should update query with default value" do
584
- @obj.should_receive(:update_query).with({:skip => 0})
601
+ it "should update query with default value" do
602
+ expect(@obj).to receive(:update_query).with({:skip => 0})
585
603
  @obj.skip
586
604
  end
587
605
  end
588
606
 
589
607
  describe "#reduce" do
590
608
  it "should update query" do
591
- @obj.should_receive(:can_reduce?).and_return(true)
592
- @obj.should_receive(:update_query).with({:reduce => true, :delete => [:include_docs]})
609
+ expect(@obj).to receive(:can_reduce?).and_return(true)
610
+ expect(@obj).to receive(:update_query).with({:reduce => true, :delete => [:include_docs]})
593
611
  @obj.reduce
594
612
  end
595
613
  it "should raise error if query cannot be reduced" do
596
- @obj.should_receive(:can_reduce?).and_return(false)
597
- lambda { @obj.reduce }.should raise_error
614
+ expect(@obj).to receive(:can_reduce?).and_return(false)
615
+ expect { @obj.reduce }.to raise_error(/Cannot reduce a view without a reduce method/)
598
616
  end
599
617
  end
600
618
 
601
619
  describe "#group" do
602
620
  it "should update query" do
603
- @obj.should_receive(:query).and_return({:reduce => true})
604
- @obj.should_receive(:update_query).with({:group => true})
621
+ expect(@obj).to receive(:query).and_return({:reduce => true})
622
+ expect(@obj).to receive(:update_query).with({:group => true})
605
623
  @obj.group
606
624
  end
607
625
  it "should raise error if query not prepared for reduce" do
608
- @obj.should_receive(:query).and_return({:reduce => false})
609
- lambda { @obj.group }.should raise_error
626
+ expect(@obj).to receive(:query).and_return({:reduce => false})
627
+ expect { @obj.group }.to raise_error(/View#reduce must have been set before grouping is permitted/)
610
628
  end
611
629
  end
612
630
 
613
631
  describe "#group" do
614
632
  it "should update query" do
615
- @obj.should_receive(:query).and_return({:reduce => true})
616
- @obj.should_receive(:update_query).with({:group => true})
633
+ expect(@obj).to receive(:query).and_return({:reduce => true})
634
+ expect(@obj).to receive(:update_query).with({:group => true})
617
635
  @obj.group
618
636
  end
619
637
  it "should raise error if query not prepared for reduce" do
620
- @obj.should_receive(:query).and_return({:reduce => false})
621
- lambda { @obj.group }.should raise_error
638
+ expect(@obj).to receive(:query).and_return({:reduce => false})
639
+ expect { @obj.group }.to raise_error(/View#reduce must have been set before grouping is permitted/)
622
640
  end
623
641
  end
624
642
 
625
643
  describe "#group_level" do
626
644
  it "should update query" do
627
- @obj.should_receive(:group).and_return(@obj)
628
- @obj.should_receive(:update_query).with({:group_level => 3})
645
+ expect(@obj).to receive(:group).and_return(@obj)
646
+ expect(@obj).to receive(:update_query).with({:group_level => 3})
629
647
  @obj.group_level(3)
630
648
  end
631
649
  end
632
650
 
633
651
  describe "#stale" do
634
652
  it "should update query with ok" do
635
- @obj.should_receive(:update_query).with(:stale => 'ok')
653
+ expect(@obj).to receive(:update_query).with(:stale => 'ok')
636
654
  @obj.stale('ok')
637
655
  end
638
656
  it "should update query with update_after" do
639
- @obj.should_receive(:update_query).with(:stale => 'update_after')
657
+ expect(@obj).to receive(:update_query).with(:stale => 'update_after')
640
658
  @obj.stale('update_after')
641
659
  end
642
660
  it "should fail if anything else is provided" do
643
- lambda { @obj.stale('yes') }.should raise_error(/can only be set with/)
661
+ expect { @obj.stale('yes') }.to raise_error(/can only be set with/)
644
662
  end
645
663
  end
646
664
 
647
665
  describe "#include_docs" do
648
666
  it "should call include_docs! on new view" do
649
- @obj.should_receive(:update_query).and_return(@obj)
650
- @obj.should_receive(:include_docs!)
667
+ expect(@obj).to receive(:update_query).and_return(@obj)
668
+ expect(@obj).to receive(:include_docs!)
651
669
  @obj.include_docs
652
670
  end
653
671
  end
654
672
 
655
673
  describe "#reset!" do
656
674
  it "should empty all cached data" do
657
- @obj.should_receive(:result=).with(nil)
675
+ expect(@obj).to receive(:result=).with(nil)
658
676
  @obj.instance_exec { @rows = 'foo'; @docs = 'foo' }
659
677
  @obj.reset!
660
- @obj.instance_exec { @rows }.should be_nil
661
- @obj.instance_exec { @docs }.should be_nil
678
+ expect(@obj.instance_exec { @rows }).to be_nil
679
+ expect(@obj.instance_exec { @docs }).to be_nil
662
680
  end
663
681
  end
664
682
 
@@ -666,58 +684,58 @@ describe "Design View" do
666
684
 
667
685
  describe "#include_docs!" do
668
686
  it "should set query value" do
669
- @obj.should_receive(:result).and_return(false)
670
- @obj.should_not_receive(:reset!)
687
+ expect(@obj).to receive(:result).and_return(false)
688
+ expect(@obj).not_to receive(:reset!)
671
689
  @obj.send(:include_docs!)
672
- @obj.query[:include_docs].should be_true
690
+ expect(@obj.query[:include_docs]).to be_truthy
673
691
  end
674
692
  it "should reset if result and no docs" do
675
- @obj.should_receive(:result).and_return(true)
676
- @obj.should_receive(:include_docs?).and_return(false)
677
- @obj.should_receive(:reset!)
693
+ expect(@obj).to receive(:result).and_return(true)
694
+ expect(@obj).to receive(:include_docs?).and_return(false)
695
+ expect(@obj).to receive(:reset!)
678
696
  @obj.send(:include_docs!)
679
- @obj.query[:include_docs].should be_true
697
+ expect(@obj.query[:include_docs]).to be_truthy
680
698
  end
681
699
  it "should raise an error if view is reduced" do
682
700
  @obj.query[:reduce] = true
683
- lambda { @obj.send(:include_docs!) }.should raise_error
701
+ expect { @obj.send(:include_docs!) }.to raise_error(/Cannot include documents in view that has been reduced/)
684
702
  end
685
703
  end
686
704
 
687
705
  describe "#include_docs?" do
688
706
  it "should return true if set" do
689
- @obj.should_receive(:query).and_return({:include_docs => true})
690
- @obj.send(:include_docs?).should be_true
707
+ expect(@obj).to receive(:query).and_return({:include_docs => true})
708
+ expect(@obj.send(:include_docs?)).to be_truthy
691
709
  end
692
710
  it "should return false if not set" do
693
- @obj.should_receive(:query).and_return({})
694
- @obj.send(:include_docs?).should be_false
695
- @obj.should_receive(:query).and_return({:include_docs => false})
696
- @obj.send(:include_docs?).should be_false
711
+ expect(@obj).to receive(:query).and_return({})
712
+ expect(@obj.send(:include_docs?)).to be_falsey
713
+ expect(@obj).to receive(:query).and_return({:include_docs => false})
714
+ expect(@obj.send(:include_docs?)).to be_falsey
697
715
  end
698
716
  end
699
717
 
700
718
  describe "#update_query" do
701
719
  it "returns a new instance of view" do
702
- @obj.send(:update_query).object_id.should_not eql(@obj.object_id)
720
+ expect(@obj.send(:update_query).object_id).not_to eql(@obj.object_id)
703
721
  end
704
722
 
705
723
  it "returns a new instance of view with extra parameters" do
706
724
  new_obj = @obj.send(:update_query, {:foo => :bar})
707
- new_obj.query[:foo].should eql(:bar)
725
+ expect(new_obj.query[:foo]).to eql(:bar)
708
726
  end
709
727
  end
710
728
 
711
729
  describe "#can_reduce?" do
712
730
  it "should check and prove true" do
713
- @obj.should_receive(:name).and_return('test_view')
714
- @obj.should_receive(:design_doc).and_return({'views' => {'test_view' => {'reduce' => 'foo'}}})
715
- @obj.send(:can_reduce?).should be_true
731
+ expect(@obj).to receive(:name).and_return('test_view')
732
+ expect(@obj).to receive(:design_doc).and_return({'views' => {'test_view' => {'reduce' => 'foo'}}})
733
+ expect(@obj.send(:can_reduce?)).to be_truthy
716
734
  end
717
735
  it "should check and prove false" do
718
- @obj.should_receive(:name).and_return('test_view')
719
- @obj.should_receive(:design_doc).and_return({'views' => {'test_view' => {'reduce' => nil}}})
720
- @obj.send(:can_reduce?).should be_false
736
+ expect(@obj).to receive(:name).and_return('test_view')
737
+ expect(@obj).to receive(:design_doc).and_return({'views' => {'test_view' => {'reduce' => nil}}})
738
+ expect(@obj.send(:can_reduce?)).to be_falsey
721
739
  end
722
740
  end
723
741
 
@@ -725,48 +743,48 @@ describe "Design View" do
725
743
  before :each do
726
744
  # disable real execution!
727
745
  @design_doc = double("DesignDoc")
728
- @design_doc.stub(:view_on)
729
- @design_doc.stub(:sync)
730
- @obj.stub(:design_doc).and_return(@design_doc)
746
+ allow(@design_doc).to receive(:view_on)
747
+ allow(@design_doc).to receive(:sync)
748
+ allow(@obj).to receive(:design_doc).and_return(@design_doc)
731
749
  end
732
750
 
733
751
  it "should return previous result if set" do
734
752
  @obj.result = "foo"
735
- @obj.send(:execute).should eql('foo')
753
+ expect(@obj.send(:execute)).to eql('foo')
736
754
  end
737
755
 
738
756
  it "should raise issue if no database" do
739
- @obj.should_receive(:query).and_return({:database => nil})
757
+ expect(@obj).to receive(:query).and_return({:database => nil})
740
758
  model = double("SomeModel")
741
- model.should_receive(:database).and_return(nil)
742
- @obj.should_receive(:model).and_return(model)
743
- lambda { @obj.send(:execute) }.should raise_error
759
+ expect(model).to receive(:database).and_return(nil)
760
+ expect(@obj).to receive(:model).and_return(model)
761
+ expect { @obj.send(:execute) }.to raise_error(CouchRest::Model::DatabaseNotDefined)
744
762
  end
745
763
 
746
764
  it "should delete the reduce option if not going to be used" do
747
- @obj.should_receive(:can_reduce?).and_return(false)
748
- @obj.query.should_receive(:delete).with(:reduce)
765
+ expect(@obj).to receive(:can_reduce?).and_return(false)
766
+ expect(@obj.query).to receive(:delete).with(:reduce)
749
767
  @obj.send(:execute)
750
768
  end
751
769
 
752
770
  it "should call to save the design document" do
753
- @obj.should_receive(:can_reduce?).and_return(false)
754
- @design_doc.should_receive(:sync).with(DB)
771
+ expect(@obj).to receive(:can_reduce?).and_return(false)
772
+ expect(@design_doc).to receive(:sync).with(DB)
755
773
  @obj.send(:execute)
756
774
  end
757
775
 
758
776
  it "should populate the results" do
759
- @obj.should_receive(:can_reduce?).and_return(true)
760
- @design_doc.should_receive(:view_on).and_return('foos')
777
+ expect(@obj).to receive(:can_reduce?).and_return(true)
778
+ expect(@design_doc).to receive(:view_on).and_return('foos')
761
779
  @obj.send(:execute)
762
- @obj.result.should eql('foos')
780
+ expect(@obj.result).to eql('foos')
763
781
  end
764
782
 
765
783
  it "should not remove nil values from query" do
766
- @obj.should_receive(:can_reduce?).and_return(true)
767
- @obj.stub(:use_database).and_return(@mod.database)
784
+ expect(@obj).to receive(:can_reduce?).and_return(true)
785
+ allow(@obj).to receive(:use_database).and_return(@mod.database)
768
786
  @obj.query = {:reduce => true, :limit => nil, :skip => nil}
769
- @design_doc.should_receive(:view_on).with(@mod.database, 'test_view', {:reduce => true, :limit => nil, :skip => nil})
787
+ expect(@design_doc).to receive(:view_on).with(@mod.database, 'test_view', {:reduce => true, :limit => nil, :skip => nil})
770
788
  @obj.send(:execute)
771
789
  end
772
790
 
@@ -785,59 +803,59 @@ describe "Design View" do
785
803
 
786
804
  describe "#page" do
787
805
  it "should call limit and skip" do
788
- @obj.should_receive(:limit).with(25).and_return(@obj)
789
- @obj.should_receive(:skip).with(25).and_return(@obj)
806
+ expect(@obj).to receive(:limit).with(25).and_return(@obj)
807
+ expect(@obj).to receive(:skip).with(25).and_return(@obj)
790
808
  @obj.page(2)
791
809
  end
792
810
  end
793
811
 
794
812
  describe "#per" do
795
813
  it "should raise an error if page not called before hand" do
796
- lambda { @obj.per(12) }.should raise_error
814
+ expect { @obj.per(12) }.to raise_error(/View#page must be called before #per/)
797
815
  end
798
816
  it "should not do anything if number less than or eql 0" do
799
817
  view = @obj.page(1)
800
- view.per(0).should eql(view)
818
+ expect(view.per(0)).to eql(view)
801
819
  end
802
820
  it "should set limit and update skip" do
803
821
  view = @obj.page(2).per(10)
804
- view.query[:skip].should eql(10)
805
- view.query[:limit].should eql(10)
822
+ expect(view.query[:skip]).to eql(10)
823
+ expect(view.query[:limit]).to eql(10)
806
824
  end
807
825
  end
808
826
 
809
827
  describe "#total_count" do
810
828
  it "set limit and skip to nill and perform count" do
811
- @obj.should_receive(:limit).with(nil).and_return(@obj)
812
- @obj.should_receive(:skip).with(nil).and_return(@obj)
813
- @obj.should_receive(:count).and_return(5)
814
- @obj.total_count.should eql(5)
815
- @obj.total_count.should eql(5) # Second to test caching
829
+ expect(@obj).to receive(:limit).with(nil).and_return(@obj)
830
+ expect(@obj).to receive(:skip).with(nil).and_return(@obj)
831
+ expect(@obj).to receive(:count).and_return(5)
832
+ expect(@obj.total_count).to eql(5)
833
+ expect(@obj.total_count).to eql(5) # Second to test caching
816
834
  end
817
835
  end
818
836
 
819
837
  describe "#total_pages" do
820
838
  it "should use total_count and limit_value" do
821
- @obj.should_receive(:total_count).and_return(200)
822
- @obj.should_receive(:limit_value).and_return(25)
823
- @obj.total_pages.should eql(8)
839
+ expect(@obj).to receive(:total_count).and_return(200)
840
+ expect(@obj).to receive(:limit_value).and_return(25)
841
+ expect(@obj.total_pages).to eql(8)
824
842
  end
825
843
  end
826
844
 
827
845
  # `num_pages` aliases to `total_pages` for compatibility for Kaminari '< 0.14'
828
846
  describe "#num_pages" do
829
847
  it "should use total_count and limit_value" do
830
- @obj.should_receive(:total_count).and_return(200)
831
- @obj.should_receive(:limit_value).and_return(25)
832
- @obj.num_pages.should eql(8)
848
+ expect(@obj).to receive(:total_count).and_return(200)
849
+ expect(@obj).to receive(:limit_value).and_return(25)
850
+ expect(@obj.num_pages).to eql(8)
833
851
  end
834
852
  end
835
853
 
836
854
  describe "#current_page" do
837
855
  it "should use offset and limit" do
838
- @obj.should_receive(:offset_value).and_return(25)
839
- @obj.should_receive(:limit_value).and_return(25)
840
- @obj.current_page.should eql(2)
856
+ expect(@obj).to receive(:offset_value).and_return(25)
857
+ expect(@obj).to receive(:limit_value).and_return(25)
858
+ expect(@obj.current_page).to eql(2)
841
859
  end
842
860
  end
843
861
  end
@@ -852,19 +870,19 @@ describe "Design View" do
852
870
 
853
871
  let :model do
854
872
  m = double()
855
- m.stub(:database).and_return(DB)
873
+ allow(m).to receive(:database).and_return(DB)
856
874
  m
857
875
  end
858
876
 
859
877
  describe "intialize" do
860
878
  it "should store reference to model" do
861
879
  obj = @klass.new({}, model)
862
- obj.model.should eql(model)
880
+ expect(obj.model).to eql(model)
863
881
  end
864
882
  it "should copy details from hash" do
865
883
  obj = @klass.new({:foo => :bar, :test => :example}, model)
866
- obj[:foo].should eql(:bar)
867
- obj[:test].should eql(:example)
884
+ expect(obj[:foo]).to eql(:bar)
885
+ expect(obj[:test]).to eql(:example)
868
886
  end
869
887
  end
870
888
 
@@ -874,7 +892,7 @@ describe "Design View" do
874
892
 
875
893
  it "should provide id" do
876
894
  obj = @klass.new({'id' => '123456'}, model)
877
- obj.id.should eql('123456')
895
+ expect(obj.id).to eql('123456')
878
896
  end
879
897
 
880
898
  it "may be instantiated with a database" do
@@ -889,24 +907,24 @@ describe "Design View" do
889
907
 
890
908
  it "should provide key" do
891
909
  obj = @klass.new({'key' => 'thekey'}, model)
892
- obj.key.should eql('thekey')
910
+ expect(obj.key).to eql('thekey')
893
911
  end
894
912
 
895
913
  it "should provide the value" do
896
914
  obj = @klass.new({'value' => 'thevalue'}, model)
897
- obj.value.should eql('thevalue')
915
+ expect(obj.value).to eql('thevalue')
898
916
  end
899
917
 
900
918
  it "should provide the raw document" do
901
919
  obj = @klass.new({'doc' => 'thedoc'}, model)
902
- obj.raw_doc.should eql('thedoc')
920
+ expect(obj.raw_doc).to eql('thedoc')
903
921
  end
904
922
 
905
923
  it "should instantiate a new document" do
906
924
  hash = {'doc' => {'_id' => '12345', 'name' => 'sam'}}
907
925
  obj = @klass.new(hash, DesignViewModel)
908
926
  doc = double('DesignViewDoc')
909
- doc.stub(:database).and_return(DB)
927
+ allow(doc).to receive(:database).and_return(DB)
910
928
  expect(obj.model).to receive(:build_from_database).with(hash['doc']).and_return(doc)
911
929
  expect(obj.doc).to eql(doc)
912
930
  end
@@ -915,31 +933,31 @@ describe "Design View" do
915
933
  hash = {'id' => '12345', 'value' => 5}
916
934
  obj = @klass.new(hash, DesignViewModel)
917
935
  doc = double('DesignViewModel')
918
- doc.stub(:database).and_return(DB)
919
- obj.model.should_receive(:get).with('12345', DB).and_return(doc)
920
- obj.doc.should eql(doc)
936
+ allow(doc).to receive(:database).and_return(DB)
937
+ expect(obj.model).to receive(:get).with('12345', DB).and_return(doc)
938
+ expect(obj.doc).to eql(doc)
921
939
  end
922
940
 
923
941
  it "should try to load linked document if available" do
924
942
  hash = {'id' => '12345', 'value' => {'_id' => '54321'}}
925
943
  obj = @klass.new(hash, DesignViewModel)
926
944
  doc = double('DesignViewModel')
927
- doc.stub(:database).and_return(DB)
928
- obj.model.should_receive(:get).with('54321', DB).and_return(doc)
929
- obj.doc.should eql(doc)
945
+ allow(doc).to receive(:database).and_return(DB)
946
+ expect(obj.model).to receive(:get).with('54321', DB).and_return(doc)
947
+ expect(obj.doc).to eql(doc)
930
948
  end
931
949
 
932
950
  it "should try to return nil for document if none available" do
933
951
  hash = {'value' => 23} # simulate reduce
934
952
  obj = @klass.new(hash, DesignViewModel)
935
953
  doc = double('DesignViewModel')
936
- obj.model.should_not_receive(:get)
937
- obj.doc.should be_nil
954
+ expect(obj.model).not_to receive(:get)
955
+ expect(obj.doc).to be_nil
938
956
  end
939
957
 
940
958
 
941
959
  end
942
-
960
+
943
961
  end
944
962
 
945
963
 
@@ -957,53 +975,53 @@ describe "Design View" do
957
975
 
958
976
  describe "loading documents" do
959
977
  it "should return first" do
960
- DesignViewModel.by_name.first.name.should eql("Judith")
978
+ expect(DesignViewModel.by_name.first.name).to eql("Judith")
961
979
  end
962
980
 
963
981
  it "should return last" do
964
- DesignViewModel.by_name.last.name.should eql("Vilma")
982
+ expect(DesignViewModel.by_name.last.name).to eql("Vilma")
965
983
  end
966
984
 
967
985
  it "should allow multiple results" do
968
986
  view = DesignViewModel.by_name.limit(3)
969
- view.total_rows.should eql(5)
970
- view.last.name.should eql("Peter")
971
- view.all.length.should eql(3)
987
+ expect(view.total_rows).to eql(5)
988
+ expect(view.last.name).to eql("Peter")
989
+ expect(view.all.length).to eql(3)
972
990
  end
973
991
 
974
992
  it "should not return document if nil key provided" do
975
- DesignViewModel.by_name.key(nil).first.should be_nil
993
+ expect(DesignViewModel.by_name.key(nil).first).to be_nil
976
994
  end
977
995
  end
978
996
 
979
997
  describe "index information" do
980
998
  it "should provide total_rows" do
981
- DesignViewModel.by_name.total_rows.should eql(5)
999
+ expect(DesignViewModel.by_name.total_rows).to eql(5)
982
1000
  end
983
1001
  it "should provide total_rows" do
984
- DesignViewModel.by_name.total_rows.should eql(5)
1002
+ expect(DesignViewModel.by_name.total_rows).to eql(5)
985
1003
  end
986
1004
  it "should provide an offset" do
987
- DesignViewModel.by_name.offset.should eql(0)
1005
+ expect(DesignViewModel.by_name.offset).to eql(0)
988
1006
  end
989
1007
  it "should provide a set of keys" do
990
- DesignViewModel.by_name.limit(2).keys.should eql(["Judith", "Lorena"])
1008
+ expect(DesignViewModel.by_name.limit(2).keys).to eql(["Judith", "Lorena"])
991
1009
  end
992
1010
  end
993
1011
 
994
1012
  describe "viewing" do
995
1013
  it "should load views with no reduce method" do
996
1014
  docs = DesignViewModel.by_just_name.all
997
- docs.length.should eql(5)
1015
+ expect(docs.length).to eql(5)
998
1016
  end
999
1017
  it "should load documents by specific keys" do
1000
1018
  docs = DesignViewModel.by_name.keys(["Judith", "Peter"]).all
1001
- docs[0].name.should eql("Judith")
1002
- docs[1].name.should eql("Peter")
1019
+ expect(docs[0].name).to eql("Judith")
1020
+ expect(docs[1].name).to eql("Peter")
1003
1021
  end
1004
1022
  it "should provide count even if limit or skip set" do
1005
1023
  docs = DesignViewModel.by_name.limit(20).skip(2)
1006
- docs.count.should eql(5)
1024
+ expect(docs.count).to eql(5)
1007
1025
  end
1008
1026
  end
1009
1027
 
@@ -1016,24 +1034,51 @@ describe "Design View" do
1016
1034
  end
1017
1035
 
1018
1036
  it "should calculate number of pages" do
1019
- @view.total_pages.should eql(2)
1037
+ expect(@view.total_pages).to eql(2)
1020
1038
  end
1021
1039
  it "should return results from first page" do
1022
- @view.all.first.name.should eql('Judith')
1023
- @view.all.last.name.should eql('Peter')
1040
+ expect(@view.all.first.name).to eql('Judith')
1041
+ expect(@view.all.last.name).to eql('Peter')
1024
1042
  end
1025
1043
  it "should return results from second page" do
1026
- @view.page(2).all.first.name.should eql('Sam')
1027
- @view.page(2).all.last.name.should eql('Vilma')
1044
+ expect(@view.page(2).all.first.name).to eql('Sam')
1045
+ expect(@view.page(2).all.last.name).to eql('Vilma')
1028
1046
  end
1029
1047
 
1030
1048
  it "should allow overriding per page count" do
1031
1049
  @view = @view.per(10)
1032
- @view.total_pages.should eql(1)
1033
- @view.all.last.name.should eql('Vilma')
1050
+ expect(@view.total_pages).to eql(1)
1051
+ expect(@view.all.last.name).to eql('Vilma')
1034
1052
  end
1035
1053
  end
1036
1054
 
1055
+ describe "concurrent view accesses" do
1056
+
1057
+ # NOTE: must use `DesignViewModel2` instead of `DesignViewModel` to mimic
1058
+ # a "cold" start of a multi-threaded application (as the checksum is
1059
+ # stored at the class level)
1060
+ class DesignViewModel2 < CouchRest::Model::Base
1061
+ use_database DB
1062
+ property :name
1063
+
1064
+ design do
1065
+ view :by_name
1066
+ end
1067
+ end
1068
+
1069
+ it "should not conflict" do
1070
+ expect {
1071
+ threads = 2.times.map {
1072
+ Thread.new {
1073
+ DesignViewModel2.by_name.page(1).to_a
1074
+ }
1075
+ }
1076
+ threads.each(&:join)
1077
+ }.to_not raise_error
1078
+ end
1079
+
1080
+ end
1081
+
1037
1082
  end
1038
1083
 
1039
1084