I am using Rails 3.2.x and Thin 1.5.0 and when initially loading my app, after not loading it for say 24 hours, it takes VERY long. At first I thought it was just my macbook - because it was in sleep mode and the first time it was just taking forever for whatever reason.
But, I realized that it does the same on Heroku and it also does the same for other people. Like when they haven't visited the Heroku site for a while, the first time they load it (not EVERY single time, but some times) it takes FOREVER.
According to the log, it seems that the compilation of my stylesheets take forever. What I am confused about though, is when I push to Heroku it should compile the assets during the push...right? So, in theory, that shouldn't be what is slowing it down in production. Or am I missing something?
Although, in recent times, Heroku has been rejecting pushes so I have had to enable this:
# Don't initialize app on pre-compile
config.assets.initialize_on_precompile = false
So I am not sure if that is what is contributing to it.
Started GET "/" for 127.0.0.1 at 2013-02-19 02:44:14 -0500
Processing by HomeController#index as HTML
Category Load (56.6ms) SELECT "categories".* FROM "categories" LIMIT 6
EXPLAIN (14.6ms) EXPLAIN QUERY PLAN SELECT "categories".* FROM "categories" LIMIT 6
EXPLAIN for: SELECT "categories".* FROM "categories" LIMIT 6
0|0|0|SCAN TABLE categories (~1000000 rows)
Banner Load (44.4ms) SELECT "banners".* FROM "banners" INNER JOIN "banner_types" ON "banner_types"."id" = "banners"."banner_type_id" WHERE (banner_types.name = 'Featured')
Banner Load (0.3ms) SELECT "banners".* FROM "banners" INNER JOIN "banner_types" ON "banner_types"."id" = "banners"."banner_type_id" WHERE (banner_types.name = 'Side')
Product Load (3.4ms) SELECT "products".* FROM "products"
Vendor Load (15.9ms) SELECT "vendors".* FROM "vendors"
User Load (50.0ms) SELECT "users".* FROM "users"
EXPLAIN (0.1ms) EXPLAIN QUERY PLAN SELECT "users".* FROM "users"
EXPLAIN for: SELECT "users".* FROM "users"
0|0|0|SCAN TABLE users (~1000000 rows)
Vendor Load (0.3ms) SELECT "vendors".* FROM "vendors" WHERE "vendors"."id" = 12 LIMIT 1
Vendor Load (0.2ms) SELECT "vendors".* FROM "vendors" WHERE "vendors"."id" = 11 LIMIT 1
Vendor Load (0.2ms) SELECT "vendors".* FROM "vendors" WHERE "vendors"."id" = 10 LIMIT 1
CACHE (0.0ms) SELECT "vendors".* FROM "vendors" WHERE "vendors"."id" = 12 LIMIT 1
CACHE (0.0ms) SELECT "vendors".* FROM "vendors" WHERE "vendors"."id" = 12 LIMIT 1
CACHE (0.0ms) SELECT "vendors".* FROM "vendors" WHERE "vendors"."id" = 10 LIMIT 1
Rendered home/_popular_products.html.erb (303.0ms)
Rendered home/_popular_stores.html.erb (2.4ms)
Rendered home/index.html.erb within layouts/application (570.6ms)
Compiled main.css (20360ms) (pid 86898)
Compiled application.css (2366ms) (pid 86898)
Rendered layouts/_login_nav.html.erb (1.0ms)
Rendered layouts/_navigation.html.erb (1.7ms)
Rendered layouts/_header.html.erb (47.3ms)
Rendered layouts/_messages.html.erb (0.2ms)
Rendered layouts/_footer.html.erb (0.5ms)
Completed 200 OK in 38402ms (Views: 30707.1ms | ActiveRecord: 1830.8ms)
Thoughts?
Edit 1:
Please note that this question hasn't been adequately answered. The responses both talk about the issue on Heroku - which is part of the question. However, they fail to address this issue happening in development.
Heroku will spin down your app to save resources, if it's not accessed for a certain amount of time. Thus the slowness is caused by having to start up the entire app again.
See Dyno Idling on https://devcenter.heroku.com/articles/dynos for more information.
To get around this, you can use services such as the New Relic addon, that will ping your app every so often, to stop the spin down.
You also should be compiling your assets on deploy, not on demand. Heroku should do this by default - what did you change to stop it happening?
If you only have 1 dyno on Heroku (free plan) then it will go idle after a while to save resources. Then when someone accesses your app after a while it will start up again.
So the first person to access your app will have to wait for a while.
Related
I am using rails to develop a social website for posting, tagging etc. I am also using a gem public_activity and this is used to render the page. While loading the page, sometimes the post are shown twice when there is only some posts. But when I see the log of server I found queries are repeated twice ie, taken data from both database and cache and resulting in loading those posts twice.
Server log
SELECT `posts`.* FROM `posts` WHERE `posts`.`id` = 836 LIMIT 1
CACHE (0.0ms) SELECT `posts`.* FROM `posts` WHERE `posts`.`id` = 836 LIMIT 1 [["id", 836]]
Please help to solve the issue . Thanks in advance.
I'm creating a large xml output using rails and there are a lot of urls generated by rails. There are so called items and enclosures. Every item may have one enclosure. So I'm using has_one and belongs_to relation in my model.
I'm using
enclosure_url(item.enclosure, format: :json)
for generating the url.
What I expect: Rails should generate the url based on the id which is stored in the items table.
What now happens is, that rails is fetching each single enclosure from the database which is slowing down my system.
Enclosure Load (2.6ms) SELECT "enclosures".* FROM "enclosures" WHERE "enclosures"."id" = ? LIMIT 1 [["id", 11107]]
Enclosure Load (3.1ms) SELECT "enclosures".* FROM "enclosures" WHERE "enclosures"."id" = ? LIMIT 1 [["id", 11108]]
Enclosure Load (0.7ms) SELECT "enclosures".* FROM "enclosures" WHERE "enclosures"."id" = ? LIMIT 1 [["id", 11109]]
Enclosure Load (1.5ms) SELECT "enclosures".* FROM "enclosures" WHERE "enclosures"."id" = ? LIMIT 1 [["id", 11110]]
Enclosure Load (6.8ms) SELECT "enclosures".* FROM "enclosures" WHERE "enclosures"."id" = ? LIMIT 1 [["id", 11111]]
Is there any trick stopping rails doing this or do I have to generate my url myself?
IMO you have two options:
1) Use includes to load all enclosures in one query:
#items = Item.where(...).includes(:enclosure)
2) Pass the id of the enclosure to the url builder instead of the object:
enclosure_url(id: item.enclosure_id)
I would prefer the first option, because it ensures that the object you are linking to actually exists.
I created a dataTable used for viewing Subjects that I enter. For some reason, even though I can still enter subjects (and they are saved into the database), only 30 records can be shown on the table. I can't find anywhere that explicitly limits the table to 30 line items.
I'm looking for advice on where to look, or reasons why my table would be limited. I'll post code as requested.
Thank you for your time.
EDIT.
So I checked the logs, as you said, and sure enough I see it right there:
Started GET "/screening_log" for 127.0.0.1 at 2014-08-25 13:21:58 -0700
Processing by SubjectsController#screening_log as HTML
[1m[35mUser Load (0.3ms)[0m SELECT "users".* FROM "users" WHERE "users"."id" = 1 LIMIT 1
[1m[36mSubject Load (0.4ms)[0m [1mSELECT "subjects".* FROM "subjects" LIMIT 30 OFFSET 0[0m
[1m[35m (0.2ms)[0m SELECT COUNT(*) FROM "subjects"
Rendered subjects/screening_log.html.erb within layouts/application (14.8ms)
Rendered layouts/_shim.html.erb (0.0ms)
Rendered layouts/_header.html.erb (1.4ms)
Rendered layouts/_footer.html.erb (0.2ms)
Completed 200 OK in 21.3ms (Views: 19.4ms | ActiveRecord: 0.9ms)
Limit 30. I'm trying to find where the database is called right now. It's not in SubjectsController, which is confusing to me. But I'll keep looking. Thank you for the advice!
EDIT 2.
As a side note, if I type Subject.all in the console, it's limited by 30.
If you are using pagination, then the default value is '30' if you don't set it with .per_page(num)
It's part of the will_paginate API, see this link for details: will_paginate API.
I just upgraded my app to rails 3.1 and now whenever I run tests I get a ton of SQL output in my terminal.
For example:
(1.0ms) TRUNCATE TABLE `users`;
(0.1ms) SET FOREIGN_KEY_CHECKS = 1
. Company Load (0.3ms) SELECT `companies`.* FROM `companies` LIMIT 1
Sector Load (0.3ms) SELECT `sectors`.* FROM `sectors` WHERE `sectors`.`name` = 'General' LIMIT 1
(0.1ms) BEGIN
(0.3ms) SELECT 1 FROM `sectors` WHERE `sectors`.`name` = BINARY 'General 63' LIMIT 1
SQL (0.2ms) INSERT INTO `sectors` (`created_at`, `name`, `price_in_cents`, `updated_at`) VALUES ('2011-09-13 20:46:48', 'General 63', 0, '2011-09-13 20:46:48')
(0.3ms) COMMIT
Is there any way to disable this?
I'm using rspec instafail and I can't seem them anymore because its flooded with SQL output.
I tried adding what was in this article but it didnt help: http://tesoriere.com/2011/05/28/rails-3.1---sql-logging-to-stdout-during-testing--with-rspec--test-unit--or-cucumber-/
Have you tried setting the config.log_level in your environments/test.rb?
config.log_level = :error
That would be the easiest solution, unless there's a reason it's not working.
I am brand new to RoR land, coming from 20 years of non-dynamic languages, and working on an app I did not originate, and still trying to get my head around all the things that happen through convention (i.e. 'magic' until you know what caused it) and trying to debug an issue.
My question isn't specific to the problem I'm tracking down, but rather wanting to know this; is this debug output really telling me that 10 separate calls are happening to SQL?
Processing OwnersController#stest (for 127.0.0.1 at 2011-06-20 11:08:26) [GET]
Parameters: {"action"=>"stest", "controller"=>"owners"}
User Columns (4.8ms) SHOW FIELDS FROM `users`
User Load (0.4ms) SELECT * FROM `users` WHERE (`users`.`id` = 45241) LIMIT 1
Owner Columns (4.8ms) SHOW FIELDS FROM `users`
Provider Load (121.6ms) SELECT * FROM `providers` WHERE (`providers`.owner_id = 45241) LIMIT 1
Provider Columns (4.1ms) SHOW FIELDS FROM `providers`
FeedItem Load (43.2ms) SELECT * FROM `feed_items` WHERE (((4 & item_id) > 0)) AND ((feed_items.created_at >= '2011-06-13 15:08:27') AND (feed_items.event = 5)) GROUP BY initiator_type, initiator_id ORDER BY id ASC
Rendering template within layouts/front_end
Rendering owners/stest
FeedItem Columns (2.0ms) SHOW FIELDS FROM `feed_items`
User Load (0.4ms) SELECT * FROM `users` WHERE (`users`.`id` = 45268)
Parent Columns (4.7ms) SHOW FIELDS FROM `users`
Rendered feed_items/_user_saved_provider_search (23.4ms)
User Load (0.4ms) SELECT * FROM `users` WHERE (`users`.`id` = 45269)
Rendered feed_items/_user_saved_provider_search (4.3ms)
User Load (0.4ms) SELECT * FROM `users` WHERE (`users`.`id` = 45236)
Rendered feed_items/_user_saved_provider_search (3.7ms)
InHome Columns (3.7ms) SHOW FIELDS FROM `providers`
ZipCode Load (32.5ms) SELECT * FROM `zip_codes` WHERE (`zip_codes`.`city` = 'Plano') LIMIT 1
City Columns (3.1ms) SHOW FIELDS FROM `cities`
City Load (0.4ms) SELECT * FROM `cities` WHERE (`cities`.`name` = 'Plano') LIMIT 1
CACHE (0.0ms) SELECT * FROM `zip_codes` WHERE (`zip_codes`.`city` = 'Plano') LIMIT 1
CACHE (0.0ms) SELECT * FROM `cities` WHERE (`cities`.`name` = 'Plano') LIMIT 1
Rendered layouts/_extra_links (1.7ms)
Completed in 552ms (View: 81, DB: 230) | 200 OK [http://0.0.0.0/owners/stest]
By my count there are 8 Queries, 7 Describes and 2 Cached queries.
If your dealing with an application that is actually being bottlenecked by database queries there are a few ways to optimize the number of queries generated. Setting up scopes and using includes can reduce the number of queries when fetching models across relations.
Rails also won't normally issue the same query twice, instead it caches it, hence why the lines start with CACHE for those last two queries.