Smart way to disable/enable logs on demand in Rails - ruby-on-rails

I'm running a Rails app (v 3.1.10) on a Heroku Cedar stack with Papertrail add-on going crazy because of the size of the logs.
My app is really verbose and the logs are getting huge (really huge):
Sometimes because I serialize a lots of data in one field and that makes a huge SQL request. In my model I have many:
serialize :a_game_data, Hash
serialize :another_game_data, Hash
serialize :a_big_set_of_game_data, Hash
[...]
Thanks to my AS3 Flash app working with bigs sets of json...
Sometimes because there's a lots of partials to render:
Rendered shared/_flash_message.html.erb (0.1ms)
Rendered shared/_header_cart_info.html.erb (2.7ms)
Rendered layouts/_header.html.erb (19.4ms)
[...]
It's not the big issue here, but I've added this case too because Jamiew handle it, see below...
Sometimes because there's lots of sql queries on the same page:
User Load (2.2ms) SELECT "users".* FROM "users" WHERE "users"."id" = 1 LIMIT 1
Course Load (5.3ms) SELECT "courses".* FROM "courses" WHERE (id = '1' OR pass_token = NULL)
Session Load (1.3ms) SELECT "sessions".* FROM "sessions" WHERE "sessions"."id" = 1 LIMIT 1
Training Load (1.3ms) SELECT "trainings".* FROM "trainings" WHERE "trainings"."id" = 1 LIMIT 1
[...]
It's a big (too) complex App we've got here... yeah...
Sometimes because there's a lots of params:
Parameters: {"_myapp_session"=>"BkkiJTBhYWI1MUVlaVdtbE9Eb1Y2I5BjsAVEkiEF9jc3JmX3Rva2VlYVWZyM2I0dEZaR1YwNXFjZhZTQ1uBjsARkkiUkiD3Nlc3Npb25faWQGOgZFRhcmRlbi51c2yN1poVm8vdWo3YTlrdUZzVTA9BjsARkkiH3dAh7CMTQ0Yzc4ZDJmYzg5ZjZjOGQ5NVyLmFkbWluX3VzZXIua2V5BjsAVFsISSIOQWRtaW5Vc2VyBjsARlsGaQZJIiIkMmEkMTAkcmgvQ2Rwc0lrYzFEbGJFRG9jMnZvdQY7AFRJIhl3YXJkZW4udXNlci51c2VyLmtleQY7AFRbCEkiCVVzZXIGOwBGWwZpBkkiIiQyYSQxMCRBUFBST2w0aWYxQmhHUVd0b0V5TjFPBjsAVA==--e4b53a73f6b622cfe7550b2ee12678712e2973c7", "authenticity_token"=>"EeiWmlODoYXUfr3b4tFZGV05qr7ZhVo/uj7a9kuFsU0=", "utf8"=>"✓", "locale"=>"fr", "id"=>"1", "a"=>1, "a"=>1, "a"=>1, "a"=>1, "a"=>1, "a"=>1, [...] Hey! You've reach the end of the line but it's not the end of the parameters...}
The AS3 Flash app send big json data to the controller...
I didn't mention the (in)famous "Assets pipeline logging problem" because now I'm using the quiet_assets gem to handle this:
https://github.com/evrone/quiet_assets
So... what did I try?
1: Dennis Reimann's middleware solution:
http://dennisreimann.de/blog/silencing-the-rails-log-on-a-per-action-basis/
2: Spagalocco's gem (inspired by solution #1):
https://github.com/spagalloco/silencer
3: jamiew's monkeypatches (inspired by solution #1 + a bonus):
https://gist.github.com/1558325
Nothing is really working as expected but it's getting close.
I would rather use a method in my ApplicationController like this:
def custom_logging(opts={}, show_logs=true)
disable_logging unless show_logs
remove_sql_requests_from_logs if opts[:remove_sql_requests]
remove_rendered_from_logs if opts[:remove_rendered]
remove_params_from_logs if opts[:remove_params]
[...]
end
...and call it in any controller method: custom_logging({:remove_sql_requests=>1, :remove_rendered=>1})
You got the idea.
So, is there any good resource online to handle this?
Many thanks for your advices...

I"m the author of the silencer gem mentioned above. Are you looking to filter logging in general or for a particular action? The silencer gem handles the latter problem. While you can certainly use it in different ways, it's mostly intended for particular actions.
It sounds like what you are looking for less verbose logging. I would recommend you take a look at lograge. I use that in production in most of my Rails apps and have found it to be quite useful.
If you need something more specialized, you may want to look at implementing your own LogSubscriber which is essentially the lograge solution.

Set your log level in the Heroku enviroment
View your current log level:
heroku config
You most likely have "Info", which is just a lot of noise
Change it to warn or error
heroku config:add LOG_LEVEL=WARN
Also, when viewing the logs, only specify the "app" server
heroku logs --source app
I personally, append --tail to see the logs live.
heroku logs --source app --tail

Related

How to remove Sunspot indexed data after removing model indexing?

I'm using Rails with Sunspot gem and Websolr for Solr hosting. Let's say I have a Solr indexed ActiveRecord model like this:
class User < ActiveRecord::Base
searchable do
text :name
end
end
Now I want to remove indexing from this model, so I just remove this indexing code (searchable block). Will the indexed data be removed automatically from Solr? I assume not and that I need to remove/reindex in manually. I can reindex everything like this:
Sunspot.index
Sunspot.commit
But reindexing my whole database will be slow. Is there another - faster way to stop indexing 1 model? I don't see any interface in Websolr to look through and delete records from the index and I can't seem to find any information on how to remove models from indexing with Sunspot.
I can reindex everything like this:
No, you can't, if you need to reindex again then open Rails console by typing rails c and then
=> Model.index
# User Load (15.6ms) SELECT "users".* FROM "users" ORDER BY "users"."id" ASC LIMIT $1 [["LIMIT", 50]]
# [2018-02-27 18:45:04 +0600] Start Indexing
# D, [2018-02-27T18:45:05.439714 #15296] DEBUG -- : SOLR Request (762.4ms) [ path=update parameters={} ]
And for the removing indexed data then try to the following
curl http://localhost:8982/solr/default/update?commit=true -d '<delete><query>*:*</query></delete>'
Let's describe on the url part
localhost: is the hostname.
8982: port number where your Solr server running if you confusing what is your port number then open rails console and type this puts Sunspot.config.inspect it will show your port number.
/solr/default/update: this is the path where your command execute.
?commit=true -d: That is the instruction.
'<delete><query>*:*</query></delete>': that is the method.
I have found this here but it's not working for me because there are port number and path different, I have edited my own way and it's working perfectly.
I think it will help.

Debugging rails tests

Testing has been the thing I've avoided until I realized that with well written tests I can avoid having to enter console and running a string of commands over and over again. The big issue I'm having, however, is that when a test fails, I can't see much data to use to debug with. For example, when I'm testing models I need to see the models attributes, and I need to control when it's been built, created, and saved, and a way to detect these states. With rails fixtures and plain vanilla tests this is annoying to do.
How can I make debugging fixtures and rails tests easier? Is there a way to display more console-like information when a test fails? Which testing tools can I use to debug more easily? After all, debugging the tests themselves is a huge waste of time, and the biggest obstacle to using them in the first place.
Thanks!
Debugging your tests is not very different from debugging your code.
Rails already comes with byebug gem (uncomment it, if necessary):
group :development, :test do
gem 'byebug'
end
Now you are ready to put
debugger
line anywhere in your code.
Byebug supports many additional features, which you can find here: https://github.com/deivid-rodriguez/byebug
Also check https://github.com/deivid-rodriguez/pry-byebug project which provides even better experience for debugging.
Logging helps a lot to investigate and fix issues. Not only in test but also when you deploy it on production. You can log state of your models and other useful info. Also standard rails logging logs SQL that is send to the database so you can easily see what's going on there. SQL logging is on by default in dev and test and looks similar to this:
[2015-09-24 23:19:36 ledger DEBUG]: [1m[36m (0.2ms)[0m [1mBEGIN[0m
[2015-09-24 23:19:36 ledger DEBUG]: [1m[35mSQL (2.1ms)[0m INSERT INTO "projections_tags" ("ledger_id", "tag_id", "name", "authorized_user_ids") VALUES ($1, $2, $3, $4) RETURNING "id" [["ledger_id", "ea9a68c5-c7c8-4964-b078-45bfc93d41ef"], ["tag_id", 9], ["name", "test"], ["authorized_user_ids", "{1}"]]
[2015-09-24 23:19:36 ledger DEBUG]: [1m[36m (0.4ms)[0m [1mCOMMIT[0m
I'm using log4r as a logging library since it gives more control over the log output.
I also don't like debugging but in some cases it really helps. In this case byebug is your friend.
And of corse rails console and rails dbconsole

rails save dangerous attribute srror

I'm getting the following error
i created a new scaffold bid with few fields
when i tried to access localhost:3000/bids/new
i get following error
ActiveRecord::DangerousAttributeError in BidsController#new
save is defined by ActiveRecord
in server side i see this result:
Started GET "/bids/new" for 127.0.0.1 at 2013-09-07 12:52:43 +0530
Processing by BidsController#new as HTML
Refinery::Role Load (0.4ms) SELECT "refinery_roles".* FROM "refinery_roles" WHERE "refinery_roles"."title" = 'Refinery' LIMIT 1
Refinery::User Load (0.3ms) SELECT "refinery_users".* FROM "refinery_users" INNER JOIN "refinery_roles_users" ON "refinery_users"."id" = "refinery_roles_users"."user_id" WHERE "refinery_roles_users"."role_id" = 1
Completed 500 Internal Server Error in 779ms
ActiveRecord::DangerousAttributeError (save is defined by ActiveRecord):
app/controllers/bids_controller.rb:27:in `new'
app/controllers/bids_controller.rb:27:in `new'
what am i missing or is refinerycms mounted at / is overriding functions?
please help me
It Seems, you have defined some reserved ActiveRecord's attributes, If you did so, than you either have to change those or try something else. Just add a gem in your gemfile and the gem will take care of name collisions automatically.
gem 'safe_attributes'
hope it will help. Thanks.
I have solved my problem,
The problem is not with refinery cms
i created a field with name save:boolean
i changed it to save_x:boolean and now it works fine

Rails logger configuration - show the code line that makes a query to the database

I have built a quite big rails application. Now I have a lot of queries on some pages. I'd really like the rails development log to show what line in my code that made the query request so I easy could remove some.
This is what I want.
[called from ProjectsController.rb line 32]CACHE (0.0ms) SELECT "firms".* FROM "firms" WHERE "firms"."subdomain" = 'testing' LIMIT 1
Is there a tag to put in the config/environments/development.rb file
This would be great!
config.log_tags = [:code_line_call]
A more lightweight solution is Active Record Query Tracer
Which does exactly what you are looking for.
I did not find a way to get the code line in the log.
The solution was Miniprofiler
It is a great tool for finding sql requests in your code
Ryan Bates made a railscast about it
railscasts 368-miniprofiler

rails create error

I have a threaded Post using Ancestry.
When replying to a Post from another user I get :
on the line :
#post = current_user.posts.new(params[:post])
Started POST "/posts.js" for 127.0.0.1
at Tue Jun 07 13:50:19 +0300 2011
Processing by PostsController#create
as JS Parameters: {"commit"=>"Post",
"post"=>{"body"=>"a",
"parent_id"=>"5",
"discussion_id"=>"1"},
"authenticity_token"=>"RUra0Ndv67cgaGshBS5yCJMq5V6WG6OuZiqDbbWP5cc=",
"utf8"=>"✓"} User Load (0.2ms)
SELECT "users".* FROM "users" WHERE
("users"."id" = 33) LIMIT 1 Post
Load (0.2ms) SELECT "posts".* FROM
"posts" WHERE ("posts".user_id = 33)
AND ("posts"."id" = 5) LIMIT 1
Completed in 238ms
ActiveRecord::RecordNotFound (Couldn't
find Post with ID=5 [WHERE
("posts".user_id = 33)]):
app/controllers/posts_controller.rb:28:in
`create'
How can I debug it ?
My first pass would be to open rails console (at the prompt type 'rails console') and then try the following:
>> x = Post.find(5)
If you find it check the user_id on that record. Does it actually exist? If so, that's good to know.
Next I would take the SQL in your output above and run it manually in whatever db you use. If you're using SQLite3 you can do:
>> sqlite3 db/development.sqlite3
If it exists then it's a fair point to scratch your head. I suspect you will find that it's not there.
Is the link to reply to the post manually created in your view? Are you certain it's being built correctly--the two ids of interest are indeed what you intended them to be?
If it's correctly built then I would simply use the ruby debugger in your controller and begin stepping through code. If you're not familiar with the ruby debugger, you can get the gem as described in your Gemfile and then once it's in your gemset you can add this line of code where you want to breakpoint your code:
require 'ruby-debug'; debugger
Then you're free to explore as necessary.

Resources