bullet 2.2.1 → 2.3.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (80) hide show
  1. data/.gitignore +1 -0
  2. data/.travis.yml +4 -1
  3. data/Gemfile +3 -2
  4. data/Gemfile.lock +85 -69
  5. data/Guardfile +8 -0
  6. data/lib/bullet.rb +13 -8
  7. data/lib/bullet/action_controller2.rb +4 -4
  8. data/lib/bullet/active_record2.rb +5 -6
  9. data/lib/bullet/active_record3.rb +2 -3
  10. data/lib/bullet/active_record31.rb +6 -8
  11. data/lib/bullet/detector/association.rb +27 -53
  12. data/lib/bullet/detector/counter.rb +34 -29
  13. data/lib/bullet/detector/n_plus_one_query.rb +47 -28
  14. data/lib/bullet/detector/unused_eager_association.rb +31 -30
  15. data/lib/bullet/notification/base.rb +14 -12
  16. data/lib/bullet/notification/n_plus_one_query.rb +6 -10
  17. data/lib/bullet/notification/unused_eager_loading.rb +1 -2
  18. data/lib/bullet/notification_collector.rb +1 -2
  19. data/lib/bullet/rack.rb +6 -3
  20. data/lib/bullet/registry/association.rb +4 -6
  21. data/lib/bullet/registry/base.rb +10 -7
  22. data/lib/bullet/registry/object.rb +6 -6
  23. data/lib/bullet/version.rb +1 -1
  24. data/perf/benchmark.rb +30 -12
  25. data/spec/bullet/detector/association_spec.rb +90 -0
  26. data/spec/bullet/detector/base_spec.rb +14 -0
  27. data/spec/bullet/detector/counter_spec.rb +65 -0
  28. data/spec/bullet/detector/n_plus_one_query_spec.rb +94 -0
  29. data/spec/bullet/detector/unused_eager_association_spec.rb +62 -0
  30. data/spec/bullet/notification/base_spec.rb +67 -0
  31. data/spec/bullet/notification/counter_cache_spec.rb +12 -0
  32. data/spec/bullet/notification/n_plus_one_query_spec.rb +13 -0
  33. data/spec/bullet/notification/unused_eager_loading_spec.rb +12 -0
  34. data/spec/bullet/notification_collector_spec.rb +32 -0
  35. data/spec/bullet/rack_spec.rb +80 -24
  36. data/spec/bullet/registry/association_spec.rb +26 -0
  37. data/spec/bullet/registry/base_spec.rb +44 -0
  38. data/spec/bullet/registry/object_spec.rb +25 -0
  39. data/spec/integration/association_for_chris_spec.rb +37 -0
  40. data/spec/integration/association_for_peschkaj_spec.rb +26 -0
  41. data/spec/{bullet → integration}/association_spec.rb +1 -359
  42. data/spec/integration/counter_spec.rb +37 -0
  43. data/spec/models/address.rb +3 -0
  44. data/spec/models/author.rb +3 -0
  45. data/spec/models/base_user.rb +5 -0
  46. data/spec/models/category.rb +7 -0
  47. data/spec/models/city.rb +3 -0
  48. data/spec/models/client.rb +4 -0
  49. data/spec/models/comment.rb +4 -0
  50. data/spec/models/company.rb +3 -0
  51. data/spec/models/contact.rb +3 -0
  52. data/spec/models/country.rb +3 -0
  53. data/spec/models/deal.rb +4 -0
  54. data/spec/models/document.rb +5 -0
  55. data/spec/models/email.rb +3 -0
  56. data/spec/models/entry.rb +3 -0
  57. data/spec/models/firm.rb +4 -0
  58. data/spec/models/folder.rb +2 -0
  59. data/spec/models/hotel.rb +4 -0
  60. data/spec/models/location.rb +3 -0
  61. data/spec/models/newspaper.rb +3 -0
  62. data/spec/models/page.rb +2 -0
  63. data/spec/models/person.rb +3 -0
  64. data/spec/models/pet.rb +3 -0
  65. data/spec/models/post.rb +11 -0
  66. data/spec/models/relationship.rb +4 -0
  67. data/spec/models/student.rb +3 -0
  68. data/spec/models/submission.rb +4 -0
  69. data/spec/models/teacher.rb +3 -0
  70. data/spec/models/user.rb +4 -0
  71. data/spec/models/writer.rb +2 -0
  72. data/spec/spec_helper.rb +16 -106
  73. data/spec/support/bullet_ext.rb +55 -0
  74. data/spec/support/rack_double.rb +55 -0
  75. data/spec/support/seed.rb +256 -0
  76. metadata +104 -14
  77. data/.watchr +0 -24
  78. data/spec/bullet/association_for_chris_spec.rb +0 -96
  79. data/spec/bullet/association_for_peschkaj_spec.rb +0 -86
  80. data/spec/bullet/counter_spec.rb +0 -136
@@ -1,96 +0,0 @@
1
- require File.dirname(__FILE__) + '/../spec_helper'
2
-
3
- ActiveRecord::Base.establish_connection(:adapter => 'sqlite3', :database => ':memory:')
4
- # This test is just used for http://github.com/flyerhzm/bullet/issues/#issue/14
5
- describe Bullet::Detector::Association do
6
-
7
- describe "for chris" do
8
- def setup_db
9
- ActiveRecord::Schema.define(:version => 1) do
10
- create_table :locations do |t|
11
- t.column :name, :string
12
- end
13
-
14
- create_table :hotels do |t|
15
- t.column :name, :string
16
- t.column :location_id, :integer
17
- end
18
-
19
- create_table :deals do |t|
20
- t.column :name, :string
21
- t.column :hotel_id, :integer
22
- end
23
- end
24
- end
25
-
26
- def teardown_db
27
- ActiveRecord::Base.connection.tables.each do |table|
28
- ActiveRecord::Base.connection.drop_table(table)
29
- end
30
- end
31
-
32
- class Location < ActiveRecord::Base
33
- has_many :hotels
34
- end
35
-
36
- class Hotel < ActiveRecord::Base
37
- belongs_to :location
38
- has_many :deals
39
- end
40
-
41
- class Deal < ActiveRecord::Base
42
- belongs_to :hotel
43
- has_one :location, :through => :hotel
44
- end
45
-
46
- before(:all) do
47
- setup_db
48
-
49
- location1 = Location.create(:name => "location1")
50
- location2 = Location.create(:name => "location2")
51
-
52
- hotel1 = location1.hotels.create(:name => "hotel1")
53
- hotel2 = location1.hotels.create(:name => "hotel2")
54
- hotel3 = location2.hotels.create(:name => "hotel3")
55
- hotel4 = location2.hotels.create(:name => "hotel4")
56
-
57
- deal1 = hotel1.deals.create(:name => "deal1")
58
- deal2 = hotel2.deals.create(:name => "deal2")
59
- deal3 = hotel3.deals.create(:name => "deal3")
60
- deal4 = hotel4.deals.create(:name => "deal4")
61
- end
62
-
63
- after(:all) do
64
- teardown_db
65
- end
66
-
67
- before(:each) do
68
- Bullet.start_request
69
- end
70
-
71
- after(:each) do
72
- Bullet.end_request
73
- end
74
-
75
- it "should detect unpreload association from deal to hotel" do
76
- Deal.all.each do |deal|
77
- deal.hotel.location.name
78
- end
79
- Bullet::Detector::Association.should be_detecting_unpreloaded_association_for(Deal, :hotel)
80
- end
81
-
82
- it "should detect unpreload association from hotel to location" do
83
- Deal.includes(:hotel).each do |deal|
84
- deal.hotel.location.name
85
- end
86
- Bullet::Detector::Association.should be_detecting_unpreloaded_association_for(Hotel, :location)
87
- end
88
-
89
- it "should not detect unpreload association" do
90
- Deal.includes({:hotel => :location}).each do |deal|
91
- deal.hotel.location.name
92
- end
93
- Bullet::Detector::Association.should_not be_has_unused_preload_associations
94
- end
95
- end
96
- end
@@ -1,86 +0,0 @@
1
- require File.dirname(__FILE__) + '/../spec_helper'
2
-
3
- ActiveRecord::Base.establish_connection(:adapter => 'sqlite3', :database => ':memory:')
4
- # This test is just used for http://github.com/flyerhzm/bullet/issues#issue/20
5
- describe Bullet::Detector::Association do
6
-
7
- describe "for peschkaj" do
8
- def setup_db
9
- ActiveRecord::Schema.define(:version => 1) do
10
- create_table :categories do |t|
11
- t.column :name, :string
12
- end
13
-
14
- create_table :submissions do |t|
15
- t.column :name, :string
16
- t.column :category_id, :integer
17
- t.column :user_id, :integer
18
- end
19
-
20
- create_table :users do |t|
21
- t.column :name, :string
22
- t.column :category_id, :integer
23
- end
24
- end
25
- end
26
-
27
- def teardown_db
28
- ActiveRecord::Base.connection.tables.each do |table|
29
- ActiveRecord::Base.connection.drop_table(table)
30
- end
31
- end
32
-
33
- class Category < ActiveRecord::Base
34
- has_many :submissions
35
- has_many :users
36
- end
37
-
38
- class Submission < ActiveRecord::Base
39
- belongs_to :category
40
- belongs_to :user
41
- end
42
-
43
- class User < ActiveRecord::Base
44
- has_one :submission
45
- belongs_to :category
46
- end
47
-
48
- before(:all) do
49
- setup_db
50
-
51
- category1 = Category.create(:name => "category1")
52
- category2 = Category.create(:name => "category2")
53
-
54
- user1 = User.create(:name => 'user1', :category => category1)
55
- user2 = User.create(:name => 'user2', :category => category1)
56
-
57
- submission1 = category1.submissions.create(:name => "submission1", :user => user1)
58
- submission2 = category1.submissions.create(:name => "submission2", :user => user2)
59
- submission3 = category2.submissions.create(:name => "submission3", :user => user1)
60
- submission4 = category2.submissions.create(:name => "submission4", :user => user2)
61
- end
62
-
63
- after(:all) do
64
- teardown_db
65
- end
66
-
67
- before(:each) do
68
- Bullet.start_request
69
- end
70
-
71
- after(:each) do
72
- Bullet.end_request
73
- end
74
-
75
- it "should not detect unused preload associations" do
76
- category = Category.includes({:submissions => :user}).order("id DESC").find_by_name('category1')
77
- category.submissions.map do |submission|
78
- submission.name
79
- submission.user.name
80
- end
81
- Bullet::Detector::UnusedEagerAssociation.check_unused_preload_associations
82
- Bullet::Detector::Association.should_not be_unused_preload_associations_for(Category, :submissions)
83
- Bullet::Detector::Association.should_not be_unused_preload_associations_for(Submission, :user)
84
- end
85
- end
86
- end
@@ -1,136 +0,0 @@
1
- require File.dirname(__FILE__) + '/../spec_helper'
2
-
3
- ActiveRecord::Base.establish_connection(:adapter => 'sqlite3', :database => ':memory:')
4
-
5
- describe Bullet::Detector::Counter do
6
- def setup_db
7
- ActiveRecord::Schema.define(:version => 1) do
8
- create_table :countries do |t|
9
- t.string :name
10
- end
11
-
12
- create_table :cities do |t|
13
- t.string :name
14
- t.integer :country_id
15
- end
16
- end
17
- end
18
-
19
- def teardown_db
20
- ActiveRecord::Base.connection.tables.each do |table|
21
- ActiveRecord::Base.connection.drop_table(table)
22
- end
23
- end
24
-
25
- class Country < ActiveRecord::Base
26
- has_many :cities
27
- end
28
-
29
- class City < ActiveRecord::Base
30
- belongs_to :country
31
- end
32
-
33
- before(:all) do
34
- setup_db
35
-
36
- country1 = Country.create(:name => 'first')
37
- country2 = Country.create(:name => 'second')
38
-
39
- country1.cities.create(:name => 'first')
40
- country1.cities.create(:name => 'second')
41
- country2.cities.create(:name => 'third')
42
- country2.cities.create(:name => 'fourth')
43
- end
44
-
45
- after(:all) do
46
- teardown_db
47
- end
48
-
49
- before(:each) do
50
- Bullet.start_request
51
- end
52
-
53
- after(:each) do
54
- Bullet.end_request
55
- end
56
-
57
- it "should need counter cache with all cities" do
58
- Country.all.each do |country|
59
- country.cities.size
60
- end
61
- Bullet.collected_counter_cache_notifications.should_not be_empty
62
- end
63
-
64
- it "should not need coounter cache with only one object" do
65
- Country.first.cities.size
66
- Bullet.collected_counter_cache_notifications.should be_empty
67
- end
68
-
69
- it "should not need counter cache with part of cities" do
70
- Country.all.each do |country|
71
- country.cities.where(:name => 'first').size
72
- end
73
- Bullet.collected_counter_cache_notifications.should be_empty
74
- end
75
- end
76
-
77
- describe Bullet::Detector::Counter do
78
- def setup_db
79
- ActiveRecord::Schema.define(:version => 1) do
80
- create_table :people do |t|
81
- t.string :name
82
- t.integer :pets_count
83
- end
84
-
85
- create_table :pets do |t|
86
- t.string :name
87
- t.integer :person_id
88
- end
89
- end
90
- end
91
-
92
- def teardown_db
93
- ActiveRecord::Base.connection.tables.each do |table|
94
- ActiveRecord::Base.connection.drop_table(table)
95
- end
96
- end
97
-
98
- class Person < ActiveRecord::Base
99
- has_many :pets
100
- end
101
-
102
- class Pet < ActiveRecord::Base
103
- belongs_to :person, :counter_cache => true
104
- end
105
-
106
- before(:all) do
107
- setup_db
108
-
109
- person1 = Person.create(:name => 'first')
110
- person2 = Person.create(:name => 'second')
111
-
112
- person1.pets.create(:name => 'first')
113
- person1.pets.create(:name => 'second')
114
- person2.pets.create(:name => 'third')
115
- person2.pets.create(:name => 'fourth')
116
- end
117
-
118
- after(:all) do
119
- teardown_db
120
- end
121
-
122
- before(:each) do
123
- Bullet.start_request
124
- end
125
-
126
- after(:each) do
127
- Bullet.end_request
128
- end
129
-
130
- it "should not need counter cache" do
131
- Person.all.each do |person|
132
- person.pets.size
133
- end
134
- Bullet.collected_counter_cache_notifications.should be_empty
135
- end
136
- end