views:

576

answers:

2

I'm interested in testing the performance of my django apps as I go, what is the best way to get line by line performance data?

note: Googling this returns lots of people benchmarking django itself. I'm not looking for a benchmarks of django, I'm trying to test the performance of the django apps that I'm writing :)

Thanks!

edit: By "line by line" I just mean timing individual functions, db calls, etc to find out where the bottlenecks are on a very granular level

+5  A: 

There's two layers to this. We have most of #1 in place for our testing. We're about to start on #2.

  1. Django in isolation. The ordinary Django unit tests works well here. Create some tests that cycle through a few (less than 6) "typical" use cases. Get this, post that, etc. Collect timing data. This isn't real web performance, but it's an easy-to-work with test scenario that you can use for tuning.

  2. Your whole web stack. In this case, you need a regular server running Squid, Apache, Django, MySQL, whatever. You need a second computer(s) to act a client exercise your web site through urllib2, doing a few (less than 6) "typical" use cases. Get this, post that, etc. Collect timing data. This still isn't "real" web performance, because it isn't through the internet, but it's as close as you're going to get without a really elaborate setup.

Note that the #2 (end-to-end) includes a great deal of caching for performance. If your client scripts are doing similar work, caching will be really beneficial. if your client scripts do unique things each time, caching will be less beneficial.

The hardest part is determining what the "typical" workload is. This isn't functional testing, so the workload doesn't have to include everything. Also, the more concurrent sessions your client is running, the slower it becomes. Don't struggle trying to optimize your server when your test client is the slowest part of the processing.


Edit

If "line-by-line" means "profiling", well, you've got to get a Python profiler running.

http://www.python.org/doc/2.5.2/lib/profile.html

Note that there's plenty of caching in the Django ORM layer. So running a view function a half-dozen times to get a meaningful set of measurements isn't sensible. You have to run a "typical" set of operations and then find hot-spots in the profile.

Generally, your application is easy to optimize -- you shouldn't be doing much. Your view functions should be short and have no processing to speak of. Your form and model method functions, similarly, should be very short.

S.Lott
thanks, I was referring to number 1 mostly... I suspected unittest might be the answer!btw... S. Lott you've been answering almost every question I post, It is very much appreciated :)I'm a senior in college and I've learned so much on stack overflow
Jiaaro
Thanks for the kind words.
S.Lott
+4  A: 

One way to get line by line performance data (profiling) your Django app is to use a WSGI middleware component like repoze.profile.

Assuming you are using mod_wsgi with Apache you can insert repoze.profile into your app like this:

...
application = django.core.handlers.wsgi.WSGIHandler()
...
from repoze.profile.profiler import AccumulatingProfileMiddleware
application = AccumulatingProfileMiddleware(
    application,
    log_filename='/path/to/logs/profile.log',
    discard_first_request=True,
    flush_at_shutdown=True,
    path='/_profile'
)

And now you can point your browser to /_profile to view your profile data. Of course this won't work with mod_python or the internal Django server.

Van Gale
does anything like that exist for mod_python?
Jiaaro
It's just calling the standard Python profiler (see http://docs.python.org/library/profile.html) so there probably is a way, but I'm sure there's no motivation for anyone to package it up nicely as mod_python is dead.
Van Gale
I should also add that, after looking at the output again, it actually isn't line-by-line performance data. It's a log with the amount of time spent executing each method/function, which is close but not exactly the same as line-by-line.
Van Gale