On Tue, Apr 8, 2008 at 9:46 AM, Jonathan Rochkind <[log in to unmask]> wrote:

>  I'm not really sure how to start.  The fact that I really need to
>  include examination of things that happen during view rendering (helper
>  methods, but possibly also db access that might unwise be in the view
>  code itself) makes me especially confused. Most of the stuff I find on
>  the web on this topic is about determining which actions take up most of
>  your apps time, or determining how many concurrent users your app can
>  handle. Neither of those is what I need to do! I need to get into the
>  guts of an already identified action, and figure out how to speed it up.

First thing, I'd look at the Rails log. It'll tell you how much time
you're spending in database and rendering, at least -- though it won't
report on 'business logic time', which can be quite large, especially
if you're getting lots of ActiveRecord objects (hint: don't do that).

If that suggests that your queries are slow, the Rails Query Analyzer
plugin will show you *a lot* of what's happening, query-wise. It needs
MySQL -- but the standard development log will at least tell you every
query run (and how long those queries take...?)... so you can use your
own database's query analyzer and see what they're up to.

A few very loose performance rules of thumb:

* Making AR objects is expensive. Cutting down the number of objects
in a collection with more selective SQL is almost always better than
filtering with ruby.

* And if your queries are slow... index, index, index. Try rewriting
with subqueries. Or without subqueries. The MySQL query optimizer can
be a fickle beast.

* Make development as close to production as is reasonable. Don't
assume that things that are fast (or slow) in sqlite are fast in
mysql, or in postgres.

* Put off getting collections as long as you can (for example, don't
do @articles = @person.articles in your controller; just use
@person.articles in your view). This will make fragment caching way,
way easier.

* If you need to iterate over a lot of AR objects, it can be a lot
better to do it in small batches -- AR doesn't support cursors and
will (un)happily load 1,000,000 objects into memory.