Bullet 是什么?

自动侦测 N+1 Query, Table Scan, Counter Cache的实用工具,
Github 地址:https://github.com/flyerhzm/bullet

安装

gem 'bullet' 必须添加在gem 'rails'gem 'mongoid'之后

Gemfile
gem 'bullet', group: 'development'

也可以直接放在group :development do里面

Gemfile
group :development do
  # Access an IRB console on exception pages or by using <%= console %> anywhere in the code.

  gem 'web-console', '>= 3.3.0'
  gem 'listen', '~> 3.0.5'
  # Spring speeds up development by keeping your application running in the background. Read more: https://github.com/rails/spring

  gem 'spring'
  gem 'spring-watcher-listen', '~> 2.0.0'

  gem 'bullet' 
end

配置configuration

Bullet是不会自己检测到错误的,必须配置。
config/environments/development.rb文件的最后一个end上方加入以下代码

config/environments/development.rb
config.after_initialize do
  Bullet.enable = true
  Bullet.alert = true
  Bullet.bullet_logger = true
  Bullet.console = true
  Bullet.growl = true
  Bullet.xmpp = { :account  => 'bullets_account@jabber.org',
                  :password => 'bullets_password_for_jabber',
                  :receiver => 'your_account@jabber.org',
                  :show_online_status => true }
  Bullet.rails_logger = true
  Bullet.honeybadger = true
  Bullet.bugsnag = true
  Bullet.airbrake = true
  Bullet.rollbar = true
  Bullet.add_footer = true
  Bullet.stacktrace_includes = [ 'your_gem', 'your_middleware' ]
  Bullet.stacktrace_excludes = [ 'their_gem', 'their_middleware' ]
  Bullet.slack = { webhook_url: 'http://some.slack.url', channel: '#default', username: 'notifier' }
end

这些功能其实不需要全部安装,只要选择几个需要的就可以了。如果全部安装,就会不停地报错

删除不需要的bullet, 只安装以下的功能,rails s就不会报错

config/environments/development.rb
config.after_initialize do
  Bullet.enable = true
  Bullet.alert = true
  Bullet.bullet_logger = true
  Bullet.console = true
  Bullet.rails_logger = true
  Bullet.add_footer = true
end

使用效果

遇到页面中有 N+1 Query 的问题,就会有弹窗提示。我用rails101专案进行测试。

根据提示,找到bug的位置

修改代码如下

groups_controller.rb
-    def index
-        @groups = Group.all             
-    end

+    def index
+        @groups = Group.includes(:user).all
+    end   

再执行rails s,不会出现弹窗
再打开一个讨论组,又出现弹窗报错

找到bug的位置

修改代码

groups_controller.rb
- def show
-   @group = Group.find(params[:id])    
-   @posts = @group.posts.recent.paginate(:page => params[:page], :per_page => 5)
- end

+ def show
+   @group = Group.find(params[:id])  
+   @posts = @group.posts.includes(:user).recent.paginate(:page => params[:page], :per_page =>   5)
+ end   

没有修改groups_controller.rb代码前,cache次数很多


log/bullet.log 保存报错记录