bullet 6.0.2 → 7.0.3
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.github/workflows/main.yml +82 -0
- data/CHANGELOG.md +52 -0
- data/Gemfile.rails-6.0 +1 -1
- data/Gemfile.rails-6.1 +15 -0
- data/Gemfile.rails-7.0 +10 -0
- data/README.md +39 -25
- data/lib/bullet/active_job.rb +1 -3
- data/lib/bullet/active_record4.rb +9 -23
- data/lib/bullet/active_record41.rb +8 -19
- data/lib/bullet/active_record42.rb +9 -16
- data/lib/bullet/active_record5.rb +188 -170
- data/lib/bullet/active_record52.rb +182 -162
- data/lib/bullet/active_record60.rb +191 -178
- data/lib/bullet/active_record61.rb +272 -0
- data/lib/bullet/active_record70.rb +275 -0
- data/lib/bullet/bullet_xhr.js +18 -23
- data/lib/bullet/dependency.rb +52 -34
- data/lib/bullet/detector/association.rb +24 -18
- data/lib/bullet/detector/counter_cache.rb +12 -8
- data/lib/bullet/detector/n_plus_one_query.rb +20 -10
- data/lib/bullet/detector/unused_eager_loading.rb +7 -4
- data/lib/bullet/mongoid4x.rb +3 -7
- data/lib/bullet/mongoid5x.rb +3 -7
- data/lib/bullet/mongoid6x.rb +3 -7
- data/lib/bullet/mongoid7x.rb +26 -13
- data/lib/bullet/notification/base.rb +14 -18
- data/lib/bullet/notification/n_plus_one_query.rb +2 -4
- data/lib/bullet/notification/unused_eager_loading.rb +2 -4
- data/lib/bullet/notification.rb +2 -1
- data/lib/bullet/rack.rb +28 -17
- data/lib/bullet/stack_trace_filter.rb +10 -17
- data/lib/bullet/version.rb +1 -1
- data/lib/bullet.rb +52 -42
- data/lib/generators/bullet/install_generator.rb +22 -23
- data/perf/benchmark.rb +11 -14
- data/spec/bullet/detector/counter_cache_spec.rb +6 -6
- data/spec/bullet/detector/n_plus_one_query_spec.rb +8 -4
- data/spec/bullet/detector/unused_eager_loading_spec.rb +25 -8
- data/spec/bullet/ext/object_spec.rb +1 -1
- data/spec/bullet/notification/base_spec.rb +5 -7
- data/spec/bullet/notification/n_plus_one_query_spec.rb +16 -3
- data/spec/bullet/notification/unused_eager_loading_spec.rb +5 -1
- data/spec/bullet/rack_spec.rb +154 -13
- data/spec/bullet/registry/association_spec.rb +2 -2
- data/spec/bullet/registry/base_spec.rb +1 -1
- data/spec/bullet_spec.rb +25 -44
- data/spec/integration/active_record/association_spec.rb +104 -130
- data/spec/integration/counter_cache_spec.rb +14 -34
- data/spec/integration/mongoid/association_spec.rb +19 -33
- data/spec/models/attachment.rb +5 -0
- data/spec/models/deal.rb +5 -0
- data/spec/models/post.rb +2 -0
- data/spec/models/role.rb +7 -0
- data/spec/models/submission.rb +1 -0
- data/spec/models/user.rb +2 -0
- data/spec/spec_helper.rb +4 -10
- data/spec/support/bullet_ext.rb +8 -9
- data/spec/support/mongo_seed.rb +3 -16
- data/spec/support/sqlite_seed.rb +38 -0
- data/test.sh +2 -0
- metadata +17 -7
- data/.travis.yml +0 -31
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: ad1f81292cc89778a41c6dd178bbfb6342fe1b69c4e57c3fdad0d8003d97b525
|
4
|
+
data.tar.gz: 5c1c8113f6e03ecdb449bce5e12273b969f29c323a5bb802c13c0539ea439a69
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 1f0d4d73910f96ab8c6ae5b6b1bc58de547c2c32a7c689c2984778465dae29d2c2cae81c23699b3848d2eaef30223db66bcca6ccb421b9078d5616f497421d45
|
7
|
+
data.tar.gz: 3b9001966918da22bfe7b2960526ac0db471a75e79e7939b099bebe3dde1fb27ea69b1afbdec0fcc98a6cb4260b845b5551a1a07cec036207c885be4e14ef7b9
|
@@ -0,0 +1,82 @@
|
|
1
|
+
# This workflow uses actions that are not certified by GitHub.
|
2
|
+
# They are provided by a third-party and are governed by
|
3
|
+
# separate terms of service, privacy policy, and support
|
4
|
+
# documentation.
|
5
|
+
# This workflow will download a prebuilt Ruby version, install dependencies and run tests with Rake
|
6
|
+
# For more information see: https://github.com/marketplace/actions/setup-ruby-jruby-and-truffleruby
|
7
|
+
|
8
|
+
name: CI
|
9
|
+
|
10
|
+
on:
|
11
|
+
push:
|
12
|
+
branches: [ master ]
|
13
|
+
pull_request:
|
14
|
+
branches: [ master ]
|
15
|
+
|
16
|
+
jobs:
|
17
|
+
test_rails_4:
|
18
|
+
runs-on: ubuntu-latest
|
19
|
+
strategy:
|
20
|
+
matrix:
|
21
|
+
gemfile: ['Gemfile.rails-4.0', 'Gemfile.rails-4.1', 'Gemfile.rails-4.2']
|
22
|
+
env: # $BUNDLE_GEMFILE must be set at the job level, so it is set for all steps
|
23
|
+
BUNDLE_GEMFILE: ${{ github.workspace }}/${{ matrix.gemfile }}
|
24
|
+
steps:
|
25
|
+
- uses: actions/checkout@v2
|
26
|
+
- name: Set up Ruby
|
27
|
+
uses: ruby/setup-ruby@v1
|
28
|
+
with:
|
29
|
+
ruby-version: 2.3
|
30
|
+
bundler: 1
|
31
|
+
bundler-cache: true
|
32
|
+
- name: Run tests
|
33
|
+
run: bundle exec rake
|
34
|
+
test_rails_5:
|
35
|
+
runs-on: ubuntu-latest
|
36
|
+
strategy:
|
37
|
+
matrix:
|
38
|
+
gemfile: ['Gemfile.rails-5.0', 'Gemfile.rails-5.1', 'Gemfile.rails-5.2']
|
39
|
+
env: # $BUNDLE_GEMFILE must be set at the job level, so it is set for all steps
|
40
|
+
BUNDLE_GEMFILE: ${{ github.workspace }}/${{ matrix.gemfile }}
|
41
|
+
steps:
|
42
|
+
- uses: actions/checkout@v2
|
43
|
+
- name: Set up Ruby
|
44
|
+
uses: ruby/setup-ruby@v1
|
45
|
+
with:
|
46
|
+
ruby-version: 2.5
|
47
|
+
bundler: 1
|
48
|
+
bundler-cache: true
|
49
|
+
- name: Run tests
|
50
|
+
run: bundle exec rake
|
51
|
+
test_rails_6:
|
52
|
+
runs-on: ubuntu-latest
|
53
|
+
strategy:
|
54
|
+
matrix:
|
55
|
+
gemfile: ['Gemfile.rails-6.0', 'Gemfile.rails-6.1']
|
56
|
+
env: # $BUNDLE_GEMFILE must be set at the job level, so it is set for all steps
|
57
|
+
BUNDLE_GEMFILE: ${{ github.workspace }}/${{ matrix.gemfile }}
|
58
|
+
steps:
|
59
|
+
- uses: actions/checkout@v2
|
60
|
+
- name: Set up Ruby
|
61
|
+
uses: ruby/setup-ruby@v1
|
62
|
+
with:
|
63
|
+
ruby-version: 2.7
|
64
|
+
bundler-cache: true
|
65
|
+
- name: Run tests
|
66
|
+
run: bundle exec rake
|
67
|
+
test_rails_7:
|
68
|
+
runs-on: ubuntu-latest
|
69
|
+
strategy:
|
70
|
+
matrix:
|
71
|
+
gemfile: ['Gemfile.rails-7.0']
|
72
|
+
env: # $BUNDLE_GEMFILE must be set at the job level, so it is set for all steps
|
73
|
+
BUNDLE_GEMFILE: ${{ github.workspace }}/${{ matrix.gemfile }}
|
74
|
+
steps:
|
75
|
+
- uses: actions/checkout@v2
|
76
|
+
- name: Set up Ruby
|
77
|
+
uses: ruby/setup-ruby@v1
|
78
|
+
with:
|
79
|
+
ruby-version: 3.1
|
80
|
+
bundler-cache: true
|
81
|
+
- name: Run tests
|
82
|
+
run: bundle exec rake
|
data/CHANGELOG.md
CHANGED
@@ -1,5 +1,57 @@
|
|
1
1
|
## Next Release
|
2
2
|
|
3
|
+
## 7.0.3 (08/13/2022)
|
4
|
+
|
5
|
+
* Replace `Array()` with `Array.wrap()`
|
6
|
+
|
7
|
+
## 7.0.2 (05/31/2022)
|
8
|
+
|
9
|
+
* Drop growl support
|
10
|
+
* Do not check html tag in Bullet::Rack anymore
|
11
|
+
|
12
|
+
## 7.0.1 (01/15/2022)
|
13
|
+
|
14
|
+
* Get rid of *_whitelist methods
|
15
|
+
* Hack ActiveRecord::Associations::Preloader::Batch in rails 7
|
16
|
+
|
17
|
+
## 7.0.0 (12/18/2021)
|
18
|
+
|
19
|
+
* Support rails 7
|
20
|
+
* Fix Mongoid 7 view iteration
|
21
|
+
* Move CI from Travis to Github Actions
|
22
|
+
|
23
|
+
## 6.1.5 (08/16/2021)
|
24
|
+
|
25
|
+
* Rename whitelist to safelist
|
26
|
+
* Fix onload called twice
|
27
|
+
* Support Rack::Files::Iterator responses
|
28
|
+
* Ensure HABTM associations are not incorrectly labeled n+1
|
29
|
+
|
30
|
+
## 6.1.4 (02/26/2021)
|
31
|
+
|
32
|
+
* Added an option to stop adding HTTP headers to API requests
|
33
|
+
|
34
|
+
## 6.1.3 (01/21/2021)
|
35
|
+
|
36
|
+
* Consider ThroughAssociation at SingularAssociation like CollectionAssociation
|
37
|
+
* Add xhr_script only when add_footer is enabled
|
38
|
+
|
39
|
+
## 6.1.2 (12/12/2020)
|
40
|
+
|
41
|
+
* Revert "Make whitelist thread safe"
|
42
|
+
|
43
|
+
## 6.1.1 (12/12/2020)
|
44
|
+
|
45
|
+
* Add support Rails 6.1
|
46
|
+
* Make whitelist thread safe
|
47
|
+
|
48
|
+
## 6.1.0 (12/28/2019)
|
49
|
+
|
50
|
+
* Add skip_html_injection flag
|
51
|
+
* Remove writer hack in active_record6
|
52
|
+
* Use modern includes syntax in warnings
|
53
|
+
* Fix warning: The last argument is used as the keyword parameter
|
54
|
+
|
3
55
|
## 6.0.2 (08/20/2019)
|
4
56
|
|
5
57
|
* Fully support Rails 6.0
|
data/Gemfile.rails-6.0
CHANGED
data/Gemfile.rails-6.1
ADDED
@@ -0,0 +1,15 @@
|
|
1
|
+
source "https://rubygems.org"
|
2
|
+
|
3
|
+
gemspec
|
4
|
+
|
5
|
+
gem 'rails', '~> 6.1.0'
|
6
|
+
gem 'sqlite3'
|
7
|
+
gem 'activerecord-jdbcsqlite3-adapter', platforms: [:jruby]
|
8
|
+
gem 'activerecord-import'
|
9
|
+
|
10
|
+
gem "rspec"
|
11
|
+
|
12
|
+
platforms :rbx do
|
13
|
+
gem 'rubysl', '~> 2.0'
|
14
|
+
gem 'rubinius-developer_tools'
|
15
|
+
end
|
data/Gemfile.rails-7.0
ADDED
data/README.md
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
# Bullet
|
2
2
|
|
3
|
-
|
4
|
-
[![
|
3
|
+
![Main workflow](https://github.com/flyerhzm/bullet/actions/workflows/main.yml/badge.svg)
|
4
|
+
[![Gem Version](https://badge.fury.io/rb/bullet.svg)](http://badge.fury.io/rb/bullet)
|
5
5
|
[![AwesomeCode Status for flyerhzm/bullet](https://awesomecode.io/projects/6755235b-e2c1-459e-bf92-b8b13d0c0472/status)](https://awesomecode.io/repos/flyerhzm/bullet)
|
6
6
|
[![Coderwall Endorse](http://api.coderwall.com/flyerhzm/endorsecount.png)](http://coderwall.com/flyerhzm)
|
7
7
|
|
@@ -37,12 +37,19 @@ or add it into a Gemfile (Bundler):
|
|
37
37
|
gem 'bullet', group: 'development'
|
38
38
|
```
|
39
39
|
|
40
|
+
enable the Bullet gem with generate command
|
41
|
+
|
42
|
+
```ruby
|
43
|
+
bundle exec rails g bullet:install
|
44
|
+
```
|
45
|
+
The generate command will auto generate the default configuration and may ask to include in the test environment as well. See below for custom configuration.
|
46
|
+
|
40
47
|
**Note**: make sure `bullet` gem is added after activerecord (rails) and
|
41
48
|
mongoid.
|
42
49
|
|
43
50
|
## Configuration
|
44
51
|
|
45
|
-
Bullet won't
|
52
|
+
Bullet won't enable any notification systems unless you tell it to explicitly. Append to
|
46
53
|
`config/environments/development.rb` initializer with the following code:
|
47
54
|
|
48
55
|
```ruby
|
@@ -52,7 +59,6 @@ config.after_initialize do
|
|
52
59
|
Bullet.alert = true
|
53
60
|
Bullet.bullet_logger = true
|
54
61
|
Bullet.console = true
|
55
|
-
Bullet.growl = true
|
56
62
|
Bullet.xmpp = { :account => 'bullets_account@jabber.org',
|
57
63
|
:password => 'bullets_password_for_jabber',
|
58
64
|
:receiver => 'your_account@jabber.org',
|
@@ -60,9 +66,11 @@ config.after_initialize do
|
|
60
66
|
Bullet.rails_logger = true
|
61
67
|
Bullet.honeybadger = true
|
62
68
|
Bullet.bugsnag = true
|
69
|
+
Bullet.appsignal = true
|
63
70
|
Bullet.airbrake = true
|
64
71
|
Bullet.rollbar = true
|
65
72
|
Bullet.add_footer = true
|
73
|
+
Bullet.skip_html_injection = false
|
66
74
|
Bullet.stacktrace_includes = [ 'your_gem', 'your_middleware' ]
|
67
75
|
Bullet.stacktrace_excludes = [ 'their_gem', 'their_middleware', ['my_file.rb', 'my_method'], ['my_file.rb', 16..20] ]
|
68
76
|
Bullet.slack = { webhook_url: 'http://some.slack.url', channel: '#default', username: 'notifier' }
|
@@ -76,15 +84,17 @@ The code above will enable all of the Bullet notification systems:
|
|
76
84
|
* `Bullet.alert`: pop up a JavaScript alert in the browser
|
77
85
|
* `Bullet.bullet_logger`: log to the Bullet log file (Rails.root/log/bullet.log)
|
78
86
|
* `Bullet.console`: log warnings to your browser's console.log (Safari/Webkit browsers or Firefox w/Firebug installed)
|
79
|
-
* `Bullet.growl`: pop up Growl warnings if your system has Growl installed. Requires a little bit of configuration
|
80
87
|
* `Bullet.xmpp`: send XMPP/Jabber notifications to the receiver indicated. Note that the code will currently not handle the adding of contacts, so you will need to make both accounts indicated know each other manually before you will receive any notifications. If you restart the development server frequently, the 'coming online' sound for the Bullet account may start to annoy - in this case set :show_online_status to false; you will still get notifications, but the Bullet account won't announce it's online status anymore.
|
81
88
|
* `Bullet.rails_logger`: add warnings directly to the Rails log
|
82
89
|
* `Bullet.honeybadger`: add notifications to Honeybadger
|
83
90
|
* `Bullet.bugsnag`: add notifications to bugsnag
|
84
91
|
* `Bullet.airbrake`: add notifications to airbrake
|
92
|
+
* `Bullet.appsignal`: add notifications to AppSignal
|
85
93
|
* `Bullet.rollbar`: add notifications to rollbar
|
86
94
|
* `Bullet.sentry`: add notifications to sentry
|
87
95
|
* `Bullet.add_footer`: adds the details in the bottom left corner of the page. Double click the footer or use close button to hide footer.
|
96
|
+
* `Bullet.skip_html_injection`: prevents Bullet from injecting code into the returned HTML. This must be false for receiving alerts, showing the footer or console logging.
|
97
|
+
* `Bullet.skip_http_headers`: don't add headers to API requests, and remove the javascript that relies on them. Note that this prevents bullet from logging warnings to the browser console or updating the footer.
|
88
98
|
* `Bullet.stacktrace_includes`: include paths with any of these substrings in the stack trace, even if they are not in your main app
|
89
99
|
* `Bullet.stacktrace_excludes`: ignore paths with any of these substrings in the stack trace, even if they are not in your main app.
|
90
100
|
Each item can be a string (match substring), a regex, or an array where the first item is a path to match, and the second
|
@@ -109,15 +119,15 @@ Bullet.unused_eager_loading_enable = false
|
|
109
119
|
Bullet.counter_cache_enable = false
|
110
120
|
```
|
111
121
|
|
112
|
-
##
|
122
|
+
## Safe list
|
113
123
|
|
114
124
|
Sometimes Bullet may notify you of query problems you don't care to fix, or
|
115
|
-
which come from outside your code. You can
|
125
|
+
which come from outside your code. You can add them to a safe list to ignore them:
|
116
126
|
|
117
127
|
```ruby
|
118
|
-
Bullet.
|
119
|
-
Bullet.
|
120
|
-
Bullet.
|
128
|
+
Bullet.add_safelist :type => :n_plus_one_query, :class_name => "Post", :association => :comments
|
129
|
+
Bullet.add_safelist :type => :unused_eager_loading, :class_name => "Post", :association => :comments
|
130
|
+
Bullet.add_safelist :type => :counter_cache, :class_name => "Country", :association => :cities
|
121
131
|
```
|
122
132
|
|
123
133
|
If you want to skip bullet in some specific controller actions, you can
|
@@ -144,25 +154,26 @@ The Bullet log `log/bullet.log` will look something like this:
|
|
144
154
|
* N+1 Query:
|
145
155
|
|
146
156
|
```
|
147
|
-
2009-08-25 20:40:17[INFO]
|
148
|
-
|
149
|
-
|
150
|
-
|
151
|
-
/Users/richard/Downloads/test/app/views/posts/index.html.erb:8:in `each'
|
152
|
-
/Users/richard/Downloads/test/app/
|
153
|
-
/Users/richard/Downloads/test/app/controllers/posts_controller.rb:7:in `index'
|
157
|
+
2009-08-25 20:40:17[INFO] USE eager loading detected:
|
158
|
+
Post => [:comments]·
|
159
|
+
Add to your query: .includes([:comments])
|
160
|
+
2009-08-25 20:40:17[INFO] Call stack
|
161
|
+
/Users/richard/Downloads/test/app/views/posts/index.html.erb:8:in `each'
|
162
|
+
/Users/richard/Downloads/test/app/controllers/posts_controller.rb:7:in `index'
|
154
163
|
```
|
155
164
|
|
156
|
-
The first
|
165
|
+
The first log entry is a notification that N+1 queries have been encountered. The remaining entry is a stack trace so you can find exactly where the queries were invoked in your code, and fix them.
|
157
166
|
|
158
167
|
* Unused eager loading:
|
159
168
|
|
160
169
|
```
|
161
|
-
2009-08-25 20:53:56[INFO]
|
162
|
-
|
170
|
+
2009-08-25 20:53:56[INFO] AVOID eager loading detected
|
171
|
+
Post => [:comments]·
|
172
|
+
Remove from your query: .includes([:comments])
|
173
|
+
2009-08-25 20:53:56[INFO] Call stack
|
163
174
|
```
|
164
175
|
|
165
|
-
These
|
176
|
+
These lines are notifications that unused eager loadings have been encountered.
|
166
177
|
|
167
178
|
* Need counter cache:
|
168
179
|
|
@@ -171,10 +182,14 @@ These two lines are notifications that unused eager loadings have been encounter
|
|
171
182
|
Post => [:comments]
|
172
183
|
```
|
173
184
|
|
174
|
-
##
|
185
|
+
## XMPP/Jabber and Airbrake Support
|
175
186
|
|
176
187
|
see [https://github.com/flyerhzm/uniform_notifier](https://github.com/flyerhzm/uniform_notifier)
|
177
188
|
|
189
|
+
## Growl Support
|
190
|
+
|
191
|
+
Growl support is dropped from uniform_notifier 1.16.0, if you still want it, please use uniform_notifier 1.15.0.
|
192
|
+
|
178
193
|
## Important
|
179
194
|
|
180
195
|
If you find Bullet does not work for you, *please disable your browser's cache*.
|
@@ -258,8 +273,7 @@ Bullet outputs some details info, to enable debug mode, set
|
|
258
273
|
## Demo
|
259
274
|
|
260
275
|
Bullet is designed to function as you browse through your application in development. To see it in action,
|
261
|
-
you can
|
262
|
-
follow these steps to create, detect, and fix example query problems.
|
276
|
+
you can follow these steps to create, detect, and fix example query problems.
|
263
277
|
|
264
278
|
1\. Create an example application
|
265
279
|
|
@@ -470,4 +484,4 @@ Meanwhile, there's a line appended to `log/bullet.log`
|
|
470
484
|
Post => [:comments]
|
471
485
|
```
|
472
486
|
|
473
|
-
Copyright (c) 2009 -
|
487
|
+
Copyright (c) 2009 - 2022 Richard Huang (flyerhzm@gmail.com), released under the MIT license
|
data/lib/bullet/active_job.rb
CHANGED
@@ -5,7 +5,7 @@ module Bullet
|
|
5
5
|
def self.enable
|
6
6
|
require 'active_record'
|
7
7
|
::ActiveRecord::Base.class_eval do
|
8
|
-
class <<self
|
8
|
+
class << self
|
9
9
|
alias_method :origin_find_by_sql, :find_by_sql
|
10
10
|
def find_by_sql(sql, binds = [])
|
11
11
|
result = origin_find_by_sql(sql, binds)
|
@@ -49,9 +49,7 @@ module Bullet
|
|
49
49
|
|
50
50
|
::ActiveRecord::Persistence.class_eval do
|
51
51
|
def _create_record_with_bullet(*args)
|
52
|
-
_create_record_without_bullet(*args).tap
|
53
|
-
Bullet::Detector::NPlusOneQuery.add_impossible_object(self)
|
54
|
-
end
|
52
|
+
_create_record_without_bullet(*args).tap { Bullet::Detector::NPlusOneQuery.add_impossible_object(self) }
|
55
53
|
end
|
56
54
|
alias_method_chain :_create_record, :bullet
|
57
55
|
end
|
@@ -62,13 +60,12 @@ module Bullet
|
|
62
60
|
alias_method :origin_initialize, :initialize
|
63
61
|
def initialize(records, associations, preload_scope = nil)
|
64
62
|
origin_initialize(records, associations, preload_scope)
|
63
|
+
|
65
64
|
if Bullet.start?
|
66
65
|
records = [records].flatten.compact.uniq
|
67
66
|
return if records.empty?
|
68
67
|
|
69
|
-
records.each
|
70
|
-
Bullet::Detector::Association.add_object_associations(record, associations)
|
71
|
-
end
|
68
|
+
records.each { |record| Bullet::Detector::Association.add_object_associations(record, associations) }
|
72
69
|
Bullet::Detector::UnusedEagerLoading.add_eager_loadings(records, associations)
|
73
70
|
end
|
74
71
|
end
|
@@ -81,9 +78,7 @@ module Bullet
|
|
81
78
|
records = origin_find_with_associations
|
82
79
|
if Bullet.start?
|
83
80
|
associations = (eager_load_values + includes_values).uniq
|
84
|
-
records.each
|
85
|
-
Bullet::Detector::Association.add_object_associations(record, associations)
|
86
|
-
end
|
81
|
+
records.each { |record| Bullet::Detector::Association.add_object_associations(record, associations) }
|
87
82
|
Bullet::Detector::UnusedEagerLoading.add_eager_loadings(records, associations)
|
88
83
|
end
|
89
84
|
records
|
@@ -128,17 +123,13 @@ module Bullet
|
|
128
123
|
# call one to many associations
|
129
124
|
alias_method :origin_load_target, :load_target
|
130
125
|
def load_target
|
131
|
-
if Bullet.start?
|
132
|
-
Bullet::Detector::NPlusOneQuery.call_association(@owner, @reflection.name)
|
133
|
-
end
|
126
|
+
Bullet::Detector::NPlusOneQuery.call_association(@owner, @reflection.name) if Bullet.start?
|
134
127
|
origin_load_target
|
135
128
|
end
|
136
129
|
|
137
130
|
alias_method :origin_include?, :include?
|
138
131
|
def include?(object)
|
139
|
-
if Bullet.start?
|
140
|
-
Bullet::Detector::NPlusOneQuery.call_association(@owner, @reflection.name)
|
141
|
-
end
|
132
|
+
Bullet::Detector::NPlusOneQuery.call_association(@owner, @reflection.name) if Bullet.start?
|
142
133
|
origin_include?(object)
|
143
134
|
end
|
144
135
|
end
|
@@ -156,9 +147,7 @@ module Bullet
|
|
156
147
|
::ActiveRecord::Associations::HasAndBelongsToManyAssociation.class_eval do
|
157
148
|
alias_method :origin_empty?, :empty?
|
158
149
|
def empty?
|
159
|
-
if Bullet.start? && !loaded?
|
160
|
-
Bullet::Detector::NPlusOneQuery.call_association(@owner, @reflection.name)
|
161
|
-
end
|
150
|
+
Bullet::Detector::NPlusOneQuery.call_association(@owner, @reflection.name) if Bullet.start? && !loaded?
|
162
151
|
origin_empty?
|
163
152
|
end
|
164
153
|
end
|
@@ -183,12 +172,9 @@ module Bullet
|
|
183
172
|
|
184
173
|
def has_cached_counter?(reflection = reflection())
|
185
174
|
result = origin_has_cached_counter?(reflection)
|
186
|
-
if Bullet.start? && !result
|
187
|
-
Bullet::Detector::CounterCache.add_counter_cache(owner, reflection.name)
|
188
|
-
end
|
175
|
+
Bullet::Detector::CounterCache.add_counter_cache(owner, reflection.name) if Bullet.start? && !result
|
189
176
|
result
|
190
177
|
end
|
191
|
-
|
192
178
|
end
|
193
179
|
end
|
194
180
|
end
|
@@ -5,7 +5,7 @@ module Bullet
|
|
5
5
|
def self.enable
|
6
6
|
require 'active_record'
|
7
7
|
::ActiveRecord::Base.class_eval do
|
8
|
-
class <<self
|
8
|
+
class << self
|
9
9
|
alias_method :origin_find_by_sql, :find_by_sql
|
10
10
|
def find_by_sql(sql, binds = [])
|
11
11
|
result = origin_find_by_sql(sql, binds)
|
@@ -30,6 +30,7 @@ module Bullet
|
|
30
30
|
|
31
31
|
::ActiveRecord::Relation.class_eval do
|
32
32
|
alias_method :origin_to_a, :to_a
|
33
|
+
|
33
34
|
# if select a collection of objects, then these objects have possible to cause N+1 query.
|
34
35
|
# if select only one object, then the only one object has impossible to cause N+1 query.
|
35
36
|
def to_a
|
@@ -51,9 +52,7 @@ module Bullet
|
|
51
52
|
|
52
53
|
::ActiveRecord::Persistence.class_eval do
|
53
54
|
def _create_record_with_bullet(*args)
|
54
|
-
_create_record_without_bullet(*args).tap
|
55
|
-
Bullet::Detector::NPlusOneQuery.add_impossible_object(self)
|
56
|
-
end
|
55
|
+
_create_record_without_bullet(*args).tap { Bullet::Detector::NPlusOneQuery.add_impossible_object(self) }
|
57
56
|
end
|
58
57
|
alias_method_chain :_create_record, :bullet
|
59
58
|
end
|
@@ -65,9 +64,7 @@ module Bullet
|
|
65
64
|
if Bullet.start?
|
66
65
|
records.compact!
|
67
66
|
if records.first.class.name !~ /^HABTM_/
|
68
|
-
records.each
|
69
|
-
Bullet::Detector::Association.add_object_associations(record, association)
|
70
|
-
end
|
67
|
+
records.each { |record| Bullet::Detector::Association.add_object_associations(record, association) }
|
71
68
|
Bullet::Detector::UnusedEagerLoading.add_eager_loadings(records, association)
|
72
69
|
end
|
73
70
|
end
|
@@ -84,9 +81,7 @@ module Bullet
|
|
84
81
|
records = origin_find_with_associations
|
85
82
|
if Bullet.start?
|
86
83
|
associations = (eager_load_values + includes_values).uniq
|
87
|
-
records.each
|
88
|
-
Bullet::Detector::Association.add_object_associations(record, associations)
|
89
|
-
end
|
84
|
+
records.each { |record| Bullet::Detector::Association.add_object_associations(record, associations) }
|
90
85
|
Bullet::Detector::UnusedEagerLoading.add_eager_loadings(records, associations)
|
91
86
|
end
|
92
87
|
records
|
@@ -131,9 +126,7 @@ module Bullet
|
|
131
126
|
# call one to many associations
|
132
127
|
alias_method :origin_load_target, :load_target
|
133
128
|
def load_target
|
134
|
-
if Bullet.start?
|
135
|
-
Bullet::Detector::NPlusOneQuery.call_association(@owner, @reflection.name) unless @inversed
|
136
|
-
end
|
129
|
+
Bullet::Detector::NPlusOneQuery.call_association(@owner, @reflection.name) if Bullet.start? && !@inversed
|
137
130
|
origin_load_target
|
138
131
|
end
|
139
132
|
|
@@ -147,9 +140,7 @@ module Bullet
|
|
147
140
|
|
148
141
|
alias_method :origin_include?, :include?
|
149
142
|
def include?(object)
|
150
|
-
if Bullet.start?
|
151
|
-
Bullet::Detector::NPlusOneQuery.call_association(@owner, @reflection.name)
|
152
|
-
end
|
143
|
+
Bullet::Detector::NPlusOneQuery.call_association(@owner, @reflection.name) if Bullet.start?
|
153
144
|
origin_include?(object)
|
154
145
|
end
|
155
146
|
end
|
@@ -173,9 +164,7 @@ module Bullet
|
|
173
164
|
alias_method :origin_count_records, :count_records
|
174
165
|
def count_records
|
175
166
|
result = has_cached_counter?
|
176
|
-
if Bullet.start? && !result
|
177
|
-
Bullet::Detector::CounterCache.add_counter_cache(@owner, @reflection.name)
|
178
|
-
end
|
167
|
+
Bullet::Detector::CounterCache.add_counter_cache(@owner, @reflection.name) if Bullet.start? && !result
|
179
168
|
origin_count_records
|
180
169
|
end
|
181
170
|
end
|
@@ -5,7 +5,7 @@ module Bullet
|
|
5
5
|
def self.enable
|
6
6
|
require 'active_record'
|
7
7
|
::ActiveRecord::Base.class_eval do
|
8
|
-
class <<self
|
8
|
+
class << self
|
9
9
|
alias_method :origin_find, :find
|
10
10
|
def find(*args)
|
11
11
|
result = origin_find(*args)
|
@@ -45,15 +45,14 @@ module Bullet
|
|
45
45
|
|
46
46
|
::ActiveRecord::Persistence.class_eval do
|
47
47
|
def _create_record_with_bullet(*args)
|
48
|
-
_create_record_without_bullet(*args).tap
|
49
|
-
Bullet::Detector::NPlusOneQuery.add_impossible_object(self)
|
50
|
-
end
|
48
|
+
_create_record_without_bullet(*args).tap { Bullet::Detector::NPlusOneQuery.add_impossible_object(self) }
|
51
49
|
end
|
52
50
|
alias_method_chain :_create_record, :bullet
|
53
51
|
end
|
54
52
|
|
55
53
|
::ActiveRecord::Relation.class_eval do
|
56
54
|
alias_method :origin_to_a, :to_a
|
55
|
+
|
57
56
|
# if select a collection of objects, then these objects have possible to cause N+1 query.
|
58
57
|
# if select only one object, then the only one object has impossible to cause N+1 query.
|
59
58
|
def to_a
|
@@ -80,9 +79,7 @@ module Bullet
|
|
80
79
|
if Bullet.start?
|
81
80
|
records.compact!
|
82
81
|
if records.first.class.name !~ /^HABTM_/
|
83
|
-
records.each
|
84
|
-
Bullet::Detector::Association.add_object_associations(record, association)
|
85
|
-
end
|
82
|
+
records.each { |record| Bullet::Detector::Association.add_object_associations(record, association) }
|
86
83
|
Bullet::Detector::UnusedEagerLoading.add_eager_loadings(records, association)
|
87
84
|
end
|
88
85
|
end
|
@@ -99,9 +96,7 @@ module Bullet
|
|
99
96
|
records = origin_find_with_associations
|
100
97
|
if Bullet.start?
|
101
98
|
associations = (eager_load_values + includes_values).uniq
|
102
|
-
records.each
|
103
|
-
Bullet::Detector::Association.add_object_associations(record, associations)
|
104
|
-
end
|
99
|
+
records.each { |record| Bullet::Detector::Association.add_object_associations(record, associations) }
|
105
100
|
Bullet::Detector::UnusedEagerLoading.add_eager_loadings(records, associations)
|
106
101
|
end
|
107
102
|
records
|
@@ -195,9 +190,7 @@ module Bullet
|
|
195
190
|
|
196
191
|
alias_method :origin_include?, :include?
|
197
192
|
def include?(object)
|
198
|
-
if Bullet.start?
|
199
|
-
Bullet::Detector::NPlusOneQuery.call_association(@owner, @reflection.name)
|
200
|
-
end
|
193
|
+
Bullet::Detector::NPlusOneQuery.call_association(@owner, @reflection.name) if Bullet.start?
|
201
194
|
origin_include?(object)
|
202
195
|
end
|
203
196
|
end
|
@@ -207,9 +200,11 @@ module Bullet
|
|
207
200
|
alias_method :origin_reader, :reader
|
208
201
|
def reader(force_reload = false)
|
209
202
|
result = origin_reader(force_reload)
|
203
|
+
|
210
204
|
if Bullet.start?
|
211
205
|
if @owner.class.name !~ /^HABTM_/ && !@inversed
|
212
206
|
Bullet::Detector::NPlusOneQuery.call_association(@owner, @reflection.name)
|
207
|
+
|
213
208
|
if Bullet::Detector::NPlusOneQuery.impossible?(@owner)
|
214
209
|
Bullet::Detector::NPlusOneQuery.add_impossible_object(result) if result
|
215
210
|
else
|
@@ -234,9 +229,7 @@ module Bullet
|
|
234
229
|
alias_method :origin_count_records, :count_records
|
235
230
|
def count_records
|
236
231
|
result = has_cached_counter?
|
237
|
-
if Bullet.start? && !result
|
238
|
-
Bullet::Detector::CounterCache.add_counter_cache(@owner, @reflection.name)
|
239
|
-
end
|
232
|
+
Bullet::Detector::CounterCache.add_counter_cache(@owner, @reflection.name) if Bullet.start? && !result
|
240
233
|
origin_count_records
|
241
234
|
end
|
242
235
|
end
|